NetSurf
gui.c
Go to the documentation of this file.
1/*
2 * Copyright 2008-2024 Chris Young <chris@unsatisfactorysoftware.co.uk>
3 *
4 * This file is part of NetSurf, http://www.netsurf-browser.org/
5 *
6 * NetSurf is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; version 2 of the License.
9 *
10 * NetSurf is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program. If not, see <http://www.gnu.org/licenses/>.
17 */
18
19
20#ifdef __amigaos4__
21/* Custom StringView class */
24#endif
25
26/* AmigaOS libraries */
27#ifdef __amigaos4__
28#include <proto/application.h>
29#endif
30#include <proto/asl.h>
31#include <proto/datatypes.h>
32#include <proto/diskfont.h>
33#include <proto/dos.h>
34#include <proto/exec.h>
35#include <proto/graphics.h>
36#include <proto/icon.h>
37#include <proto/intuition.h>
38#include <proto/keymap.h>
39#include <proto/layers.h>
40#include <proto/locale.h>
41#include <proto/utility.h>
42#include <proto/wb.h>
43
44#ifdef WITH_AMISSL
45/* AmiSSL needs everything to use bsdsocket.library directly to avoid problems */
46#include <proto/bsdsocket.h>
47#define waitselect WaitSelect
48#endif
49
50/* Other OS includes */
51#include <datatypes/textclass.h>
52#include <devices/inputevent.h>
53#include <graphics/gfxbase.h>
54#include <graphics/rpattr.h>
55#ifdef __amigaos4__
56#include <diskfont/diskfonttag.h>
57#include <graphics/blitattr.h>
58#include <intuition/gui.h>
59#include <libraries/application.h>
60#include <libraries/keymap.h>
61#endif
62#include <intuition/icclass.h>
63#include <intuition/screens.h>
64#include <libraries/gadtools.h>
65#include <workbench/workbench.h>
66
67/* ReAction libraries */
68#include <proto/bevel.h>
69#include <proto/bitmap.h>
70#include <proto/button.h>
71#include <proto/chooser.h>
72#include <proto/clicktab.h>
73#include <proto/label.h>
74#include <proto/layout.h>
75#include <proto/listbrowser.h>
76#include <proto/scroller.h>
77#include <proto/space.h>
78#include <proto/speedbar.h>
79#include <proto/string.h>
80#include <proto/window.h>
81
82#include <classes/window.h>
83#include <gadgets/button.h>
84#include <gadgets/chooser.h>
85#include <gadgets/clicktab.h>
86#include <gadgets/layout.h>
87#include <gadgets/listbrowser.h>
88#include <gadgets/scroller.h>
89#include <gadgets/space.h>
90#include <gadgets/speedbar.h>
91#include <gadgets/string.h>
92#include <images/bevel.h>
93#include <images/bitmap.h>
94#include <images/label.h>
95
96#include <reaction/reaction_macros.h>
97
98/* newlib includes */
99#include <math.h>
100#include <string.h>
101#include <stdlib.h>
102#include <limits.h>
103
104/* NetSurf core includes */
105#include "utils/log.h"
106#include "utils/messages.h"
107#include "utils/nsoption.h"
108#include "utils/utf8.h"
109#include "utils/utils.h"
110#include "utils/nsurl.h"
111#include "utils/file.h"
112#include "netsurf/window.h"
113#include "netsurf/fetch.h"
114#include "netsurf/misc.h"
115#include "netsurf/mouse.h"
116#include "netsurf/netsurf.h"
117#include "netsurf/content.h"
119#include "netsurf/cookie_db.h"
120#include "netsurf/url_db.h"
121#include "netsurf/keypress.h"
123#include "content/fetch.h"
125#include "desktop/hotlist.h"
126#include "desktop/version.h"
128#include "desktop/searchweb.h"
129
130/* NetSurf Amiga platform includes */
131#include "amiga/gui.h"
132#include "amiga/arexx.h"
133#include "amiga/bitmap.h"
134#include "amiga/clipboard.h"
135#include "amiga/cookies.h"
136#include "amiga/ctxmenu.h"
137#include "amiga/datatypes.h"
138#include "amiga/download.h"
139#include "amiga/drag.h"
140#include "amiga/file.h"
141#include "amiga/filetype.h"
142#include "amiga/font.h"
143#include "amiga/gui_options.h"
144#include "amiga/help.h"
145#include "amiga/history.h"
146#include "amiga/history_local.h"
147#include "amiga/hotlist.h"
148#include "amiga/icon.h"
149#include "amiga/launch.h"
150#include "amiga/libs.h"
151#include "amiga/memory.h"
152#include "amiga/menu.h"
153#include "amiga/misc.h"
154#include "amiga/nsoption.h"
155#include "amiga/pageinfo.h"
156#include "amiga/plotters.h"
157#include "amiga/plugin_hack.h"
158#include "amiga/print.h"
159#include "amiga/schedule.h"
160#include "amiga/search.h"
161#include "amiga/selectmenu.h"
162#include "amiga/theme.h"
163#include "amiga/utf8.h"
164#include "amiga/corewindow.h"
165
166#define AMINS_SCROLLERPEN NUMDRIPENS
167#define NSA_KBD_SCROLL_PX 10
168#define NSA_MAX_HOTLIST_BUTTON_LEN 20
169
170#define SCROLL_TOP INT_MIN
171#define SCROLL_PAGE_UP (INT_MIN + 1)
172#define SCROLL_PAGE_DOWN (INT_MAX - 1)
173#define SCROLL_BOTTOM (INT_MAX)
174
175/* Extra mouse button defines to match those in intuition/intuition.h */
176#define SIDEDOWN (IECODE_4TH_BUTTON)
177#define SIDEUP (IECODE_4TH_BUTTON | IECODE_UP_PREFIX)
178#define EXTRADOWN (IECODE_5TH_BUTTON)
179#define EXTRAUP (IECODE_5TH_BUTTON | IECODE_UP_PREFIX)
180
181/* Left OR Right Shift/Alt keys */
182#define NSA_QUAL_SHIFT (IEQUALIFIER_RSHIFT | IEQUALIFIER_LSHIFT)
183#define NSA_QUAL_ALT (IEQUALIFIER_RALT | IEQUALIFIER_LALT)
184
185#ifdef __amigaos4__
186#define NSA_STATUS_TEXT GA_Text
187#else
188#define NSA_STATUS_TEXT STRINGA_TextVal
189#endif
190
191#ifdef __amigaos4__
192#define BOOL_MISMATCH(a,b) ((a == FALSE) && (b != FALSE)) || ((a != FALSE) && (b == FALSE))
193#else
194#define BOOL_MISMATCH(a,b) (1)
195#endif
196
197extern struct gui_utf8_table *amiga_utf8_table;
198
199enum
200{
245
248 struct Window *win;
249 Object *restrict objects[GID_LAST];
250 struct gui_window *gw; /* currently-displayed gui_window */
253 struct List tab_list;
254 ULONG tabs;
255 ULONG next_tab;
256 struct Node *last_new_tab;
257 struct Hook scrollerhook;
262 ULONG oldh;
263 ULONG oldv;
264 int temp;
267 struct ami_menu_data *menu_data[AMI_MENU_AREXX_MAX + 1]; /* only for GadTools menus */
271 struct List *web_search_list;
272 Object *search_bm;
273 char *restrict svbuffer;
274 char *restrict status;
275 char *restrict wintitle;
276 char icontitle[24];
277 char *restrict helphints[GID_LAST];
279 struct timeval lastclick;
280 struct AppIcon *appicon; /* iconify appicon */
281 struct DiskObject *dobj; /* iconify appicon */
282 struct Hook favicon_hook;
283 struct Hook throbber_hook;
284 struct Hook browser_hook;
285 struct Hook *ctxmenu_hook;
286 Object *restrict history_ctxmenu[2];
289 struct IBox *ptr_lock;
290 struct AppWindow *appwin;
291 struct MinList *shared_pens;
293 struct Menu *imenu; /* Intuition menu */
294 bool closed; /* Window has been closed (via menu) */
295};
296
298{
300 int tab;
301 struct Node *tab_node;
302 int c_x; /* Caret X posn */
303 int c_y; /* Caret Y posn */
304 int c_w; /* Caret width */
305 int c_h; /* Caret height */
310 struct List dllist;
313 char *tabtitle;
315 struct MinList *deferred_rects;
317 struct ColumnInfo *logcolumns;
318 struct List loglist;
319};
320
322 struct List *sblist;
324 int items;
325};
326
327static struct MinList *window_list = NULL;
328static struct Screen *scrn = NULL;
329static struct MsgPort *sport = NULL;
330static struct gui_window *cur_gw = NULL;
331
332static bool ami_quit = false;
333
334static struct MsgPort *schedulermsgport = NULL;
335static struct MsgPort *appport;
336#ifdef __amigaos4__
337static Class *urlStringClass;
338#endif
339
340static BOOL locked_screen = FALSE;
341static int screen_signal = -1;
342static bool win_destroyed;
343static STRPTR nsscreentitle;
344static struct gui_globals *browserglob = NULL;
345
346static struct MsgPort *applibport = NULL;
347static uint32 ami_appid = 0;
348static ULONG applibsig = 0;
349static ULONG rxsig = 0;
350static struct Hook newprefs_hook;
351
352static STRPTR temp_homepage_url = NULL;
353static bool cli_force = false;
354
355#define USERS_DIR "PROGDIR:Users"
356static char *users_dir = NULL;
357static char *current_user_dir;
359
360static const __attribute__((used)) char *stack_cookie = "\0$STACK:196608\0";
361
362const char * const versvn;
363const char * const verdate;
364
365static void ami_switch_tab(struct gui_window_2 *gwin, bool redraw);
366static void ami_change_tab(struct gui_window_2 *gwin, int direction);
367static void ami_get_hscroll_pos(struct gui_window_2 *gwin, ULONG *xs);
368static void ami_get_vscroll_pos(struct gui_window_2 *gwin, ULONG *ys);
369static void ami_quit_netsurf_delayed(void);
370static Object *ami_gui_splash_open(void);
371static void ami_gui_splash_close(Object *win_obj);
372static bool ami_gui_map_filename(char **remapped, const char *restrict path,
373 const char *restrict file, const char *restrict map);
374static void ami_gui_window_update_box_deferred(struct gui_window *g, bool draw);
375static void ami_do_redraw(struct gui_window_2 *g);
376static void ami_schedule_redraw_remove(struct gui_window_2 *gwin);
377
378static bool gui_window_get_scroll(struct gui_window *g, int *restrict sx, int *restrict sy);
379static nserror gui_window_set_scroll(struct gui_window *g, const struct rect *rect);
380static void gui_window_remove_caret(struct gui_window *g);
381static void gui_window_place_caret(struct gui_window *g, int x, int y, int height, const struct rect *clip);
382
383HOOKF(uint32, ami_set_favicon_render_hook, APTR, space, struct gpRender *);
384HOOKF(uint32, ami_set_throbber_render_hook, APTR, space, struct gpRender *);
385HOOKF(uint32, ami_gui_browser_render_hook, APTR, space, struct gpRender *);
386
387/* accessors for default options - user option is updated if it is set as per default */
388#define nsoption_default_set_int(OPTION, VALUE) \
389 if (nsoptions_default[NSOPTION_##OPTION].value.i == nsoptions[NSOPTION_##OPTION].value.i) \
390 nsoptions[NSOPTION_##OPTION].value.i = VALUE; \
391 nsoptions_default[NSOPTION_##OPTION].value.i = VALUE
392
393/* Functions documented in gui.h */
394struct MsgPort *ami_gui_get_shared_msgport(void)
395{
396 assert(sport != NULL);
397 return sport;
398}
399
401{
402 return cur_gw;
403}
404
405struct Screen *ami_gui_get_screen(void)
406{
407 return scrn;
408}
409
410struct MinList *ami_gui_get_window_list(void)
411{
412 assert(window_list != NULL);
413 return window_list;
414}
415
416void ami_gui_beep(void)
417{
418 DisplayBeep(scrn);
419}
420
422{
423 assert(gw != NULL);
424 return gw->bw;
425}
426
428{
429 assert(gwin != NULL);
430 return ami_gui_get_browser_window(gwin->gw);
431}
432
433struct List *ami_gui_get_download_list(struct gui_window *gw)
434{
435 assert(gw != NULL);
436 return &gw->dllist;
437}
438
440{
441 assert(gw != NULL);
442 return gw->shared;
443}
444
446{
447 assert(gwin != NULL);
448 return gwin->gw;
449}
450
451const char *ami_gui_get_win_title(struct gui_window *gw)
452{
453 assert(gw != NULL);
454 assert(gw->shared != NULL);
455 return (const char *)gw->shared->wintitle;
456}
457
458const char *ami_gui_get_tab_title(struct gui_window *gw)
459{
460 assert(gw != NULL);
461 return (const char *)gw->tabtitle;
462}
463
464struct Node *ami_gui_get_tab_node(struct gui_window *gw)
465{
466 assert(gw != NULL);
467 return gw->tab_node;
468}
469
471{
472 assert(gwin != NULL);
473 return gwin->tabs;
474}
475
476struct List *ami_gui2_get_tab_list(struct gui_window_2 *gwin)
477{
478 assert(gwin != NULL);
479 return &gwin->tab_list;
480}
481
483{
484 assert(gw != NULL);
485 return gw->favicon;
486}
487
489{
490 assert(gw != NULL);
491 return gw->hw;
492}
493
495{
496 assert(gw != NULL);
497 gw->hw = hw;
498}
499
501{
502 /* This needs to be in gui_window_2 as it is shared amongst tabs (I think),
503 * it just happens that the find code only knows of the gui_window
504 */
505 assert(gw != NULL);
506 assert(gw->shared != NULL);
507 gw->shared->searchwin = fw;
508}
509
511{
512 assert(gw != NULL);
513 return gw->throbbing;
514}
515
516void ami_gui_set_throbbing(struct gui_window *gw, bool throbbing)
517{
518 assert(gw != NULL);
519 gw->throbbing = throbbing;
520}
521
523{
524 assert(gw != NULL);
525 assert(gw->shared != NULL);
526 return gw->shared->throbber_frame;
527}
528
530{
531 assert(gw != NULL);
532 assert(gw->shared != NULL);
533 gw->shared->throbber_frame = frame;
534}
535
536Object *ami_gui2_get_object(struct gui_window_2 *gwin, int object_type)
537{
538 ULONG obj = 0;
539
540 assert(gwin != NULL);
541
542 switch(object_type) {
543 case AMI_WIN_MAIN:
544 obj = OID_MAIN;
545 break;
546
547 case AMI_GAD_THROBBER:
548 obj = GID_THROBBER;
549 break;
550
551 case AMI_GAD_TABS:
552 obj = GID_TABS;
553 break;
554
555 case AMI_GAD_URL:
556 obj = GID_URL;
557 break;
558
559 case AMI_GAD_SEARCH:
560 obj = GID_SEARCHSTRING;
561 break;
562
563 default:
564 return NULL;
565 break;
566 }
567
568 return gwin->objects[obj];
569}
570
571
572struct Window *ami_gui2_get_window(struct gui_window_2 *gwin)
573{
574 assert(gwin != NULL);
575 return gwin->win;
576}
577
578struct Window *ami_gui_get_window(struct gui_window *gw)
579{
580 assert(gw != NULL);
581 return ami_gui2_get_window(gw->shared);
582}
583
584struct Menu *ami_gui_get_menu(struct gui_window *gw)
585{
586 assert(gw != NULL);
587 assert(gw->shared != NULL);
588 return gw->shared->imenu;
589}
590
591void ami_gui2_set_menu(struct gui_window_2 *gwin, struct Menu *menu)
592{
593 if(menu != NULL) {
594 gwin->imenu = menu;
595 } else {
597 }
598}
599
601{
602 assert(gwin != NULL);
603 return gwin->menu_data;
604}
605
607{
608 assert(gwin != NULL);
609 gwin->temp = temp;
610}
611
613{
614 assert(gwin != NULL);
615 return gwin->temp;
616}
617
618Object *ami_gui2_get_ctxmenu_history(struct gui_window_2 *gwin, ULONG direction)
619{
620 assert(gwin != NULL);
621 return gwin->history_ctxmenu[direction];
622}
623
624void ami_gui2_set_ctxmenu_history(struct gui_window_2 *gwin, ULONG direction, Object *ctx_hist)
625{
626 assert(gwin != NULL);
627 gwin->history_ctxmenu[direction] = ctx_hist;
628}
629
630void ami_gui2_set_closed(struct gui_window_2 *gwin, bool closed)
631{
632 assert(gwin != NULL);
633 gwin->closed = closed;
634}
635
636void ami_gui2_set_new_content(struct gui_window_2 *gwin, bool new_content)
637{
638 assert(gwin != NULL);
639 gwin->new_content = new_content;
640}
641
642/** undocumented, or internal, or documented elsewhere **/
643
644#ifdef __amigaos4__
645static void *ami_find_gwin_by_id(struct Window *win, uint32 type)
646{
647 struct nsObject *node, *nnode;
648 struct gui_window_2 *gwin;
649
651 {
652 node = (struct nsObject *)GetHead((struct List *)window_list);
653
654 do
655 {
656 nnode=(struct nsObject *)GetSucc((struct Node *)node);
657
658 if(node->Type == type)
659 {
660 gwin = node->objstruct;
661 if(win == ami_gui2_get_window(gwin)) return gwin;
662 }
663 } while((node = nnode));
664 }
665 return NULL;
666}
667
669{
670 struct Layer *layer;
671 struct Screen *scrn = ami_gui_get_screen();
672
673 LockLayerInfo(&scrn->LayerInfo);
674
675 layer = WhichLayer(&scrn->LayerInfo, scrn->MouseX, scrn->MouseY);
676
677 UnlockLayerInfo(&scrn->LayerInfo);
678
679 if(layer) return ami_find_gwin_by_id(layer->Window, type);
680 else return NULL;
681}
682#else
683/**\todo check if OS4 version of this function will build on OS3, even if it isn't called */
685{
686 return NULL;
687}
688#endif
689
690void ami_set_pointer(struct gui_window_2 *gwin, gui_pointer_shape shape, bool update)
691{
692 if(gwin->mouse_pointer == shape) return;
694 if(update == true) gwin->mouse_pointer = shape;
695}
696
697/* reset the mouse pointer back to what NetSurf last set it as */
699{
701}
702
703
704STRPTR ami_locale_langs(int *codeset)
705{
706 struct Locale *locale;
707 STRPTR acceptlangs = NULL;
708 char *remapped = NULL;
709
710 if((locale = OpenLocale(NULL)))
711 {
712 if(codeset != NULL) *codeset = locale->loc_CodeSet;
713
714 for(int i = 0; i < 10; i++)
715 {
716 if(locale->loc_PrefLanguages[i])
717 {
718 if(ami_gui_map_filename(&remapped, "PROGDIR:Resources",
719 locale->loc_PrefLanguages[i], "LangNames"))
720 {
721 if(acceptlangs)
722 {
723 STRPTR acceptlangs2 = acceptlangs;
724 acceptlangs = ASPrintf("%s, %s",acceptlangs2, remapped);
725 FreeVec(acceptlangs2);
726 acceptlangs2 = NULL;
727 }
728 else
729 {
730 acceptlangs = ASPrintf("%s", remapped);
731 }
732 }
733 if(remapped != NULL) free(remapped);
734 }
735 else
736 {
737 continue;
738 }
739 }
740 CloseLocale(locale);
741 }
742 return acceptlangs;
743}
744
745static bool ami_gui_map_filename(char **remapped, const char *restrict path,
746 const char *restrict file, const char *restrict map)
747{
748 BPTR fh = 0;
749 char *mapfile = NULL;
750 size_t mapfile_size = 0;
751 char buffer[1024];
752 char *restrict realfname;
753 bool found = false;
754
755 netsurf_mkpath(&mapfile, &mapfile_size, 2, path, map);
756
757 if(mapfile == NULL) return false;
758
759 fh = FOpen(mapfile, MODE_OLDFILE, 0);
760 if(fh)
761 {
762 while(FGets(fh, buffer, 1024) != 0)
763 {
764 if((buffer[0] == '#') ||
765 (buffer[0] == '\n') ||
766 (buffer[0] == '\0')) continue;
767
768 realfname = strchr(buffer, ':');
769 if(realfname)
770 {
771 if(strncmp(buffer, file, strlen(file)) == 0)
772 {
773 if(realfname[strlen(realfname)-1] == '\n')
774 realfname[strlen(realfname)-1] = '\0';
775 *remapped = strdup(realfname + 1);
776 found = true;
777 break;
778 }
779 }
780 }
781 FClose(fh);
782 }
783
784 if(found == false) *remapped = strdup(file);
785 else NSLOG(netsurf, INFO,
786 "Remapped %s to %s in path %s using %s", file,
787 *remapped, path, map);
788
789 free(mapfile);
790
791 return found;
792}
793
794static bool ami_gui_check_resource(char *fullpath, const char *file)
795{
796 bool found = false;
797 char *remapped;
798 BPTR lock = 0;
799 size_t fullpath_len = 1024;
800
801 ami_gui_map_filename(&remapped, fullpath, file, "Resource.map");
802 netsurf_mkpath(&fullpath, &fullpath_len, 2, fullpath, remapped);
803
804 lock = Lock(fullpath, ACCESS_READ);
805 if(lock) {
806 UnLock(lock);
807 found = true;
808 }
809
810 if(found) NSLOG(netsurf, INFO, "Found %s", fullpath);
811 free(remapped);
812
813 return found;
814}
815
816bool ami_locate_resource(char *fullpath, const char *file)
817{
818 struct Locale *locale;
819 int i;
820 bool found = false;
821 char *remapped = NULL;
822 size_t fullpath_len = 1024;
823
824 /* Check NetSurf user data area first */
825
826 if(current_user_dir != NULL) {
827 strcpy(fullpath, current_user_dir);
828 found = ami_gui_check_resource(fullpath, file);
829 if(found) return true;
830 }
831
832 /* Check current theme directory */
833 if(nsoption_charp(theme)) {
834 strcpy(fullpath, nsoption_charp(theme));
835 found = ami_gui_check_resource(fullpath, file);
836 if(found) return true;
837 }
838
839 /* If not found, start on the user's preferred languages */
840
841 locale = OpenLocale(NULL);
842
843 for(i=0;i<10;i++) {
844 strcpy(fullpath, "PROGDIR:Resources/");
845
846 if(locale->loc_PrefLanguages[i]) {
847 if(ami_gui_map_filename(&remapped, "PROGDIR:Resources",
848 locale->loc_PrefLanguages[i], "LangNames") == true) {
849 netsurf_mkpath(&fullpath, &fullpath_len, 2, fullpath, remapped);
850 found = ami_gui_check_resource(fullpath, file);
851 free(remapped);
852 }
853 } else {
854 continue;
855 }
856
857 if(found) break;
858 }
859
860 if(!found) {
861 /* If not found yet, check in PROGDIR:Resources/en,
862 * might not be in user's preferred languages */
863
864 strcpy(fullpath, "PROGDIR:Resources/en/");
865 found = ami_gui_check_resource(fullpath, file);
866 }
867
868 CloseLocale(locale);
869
870 if(!found) {
871 /* Lastly check directly in PROGDIR:Resources */
872
873 strcpy(fullpath, "PROGDIR:Resources/");
874 found = ami_gui_check_resource(fullpath, file);
875 }
876
877 return found;
878}
879
880static void ami_gui_resources_free(void)
881{
884
888}
889
890static bool ami_gui_resources_open(void)
891{
892#ifdef __amigaos4__
893 urlStringClass = MakeStringClass();
894#endif
895
897 ASO_NoTrack, FALSE,
898 TAG_DONE))) return false;
899
901 ASO_NoTrack, FALSE,
902 TAG_DONE))) return false;
903
905 ASO_NoTrack, FALSE,
906 TAG_DONE))) return false;
907
909 ami_misc_fatal_error("Failed to initialise scheduler");
910 return false;
911 }
912
914
915 return true;
916}
917
918static UWORD ami_system_colour_scrollbar_fgpen(struct DrawInfo *drinfo)
919{
920 LONG scrollerfillpen = FALSE;
921#ifdef __amigaos4__
922 GetGUIAttrs(NULL, drinfo, GUIA_PropKnobColor, &scrollerfillpen, TAG_DONE);
923
924 if(scrollerfillpen) return FILLPEN;
925 else return FOREGROUNDPEN;
926#else
927 return FILLPEN;
928#endif
929
930}
931
932/**
933 * set option from pen
934 */
935static nserror
937 enum nsoption_e option,
938 struct Screen *screen,
939 colour def_colour)
940{
941 ULONG colr[3];
942 struct DrawInfo *drinfo;
943
944 if((option < NSOPTION_SYS_COLOUR_START) ||
945 (option > NSOPTION_SYS_COLOUR_END) ||
946 (nsoptions[option].type != OPTION_COLOUR)) {
948 }
949
950 if(screen != NULL) {
951 drinfo = GetScreenDrawInfo(screen);
952 if(drinfo != NULL) {
953
955
956 /* Get the colour of the pen being used for "pen" */
957 GetRGB32(screen->ViewPort.ColorMap, drinfo->dri_Pens[pen], 1, (ULONG *)&colr);
958
959 /* convert it to a color */
960 def_colour = ((colr[0] & 0xff000000) >> 24) |
961 ((colr[1] & 0xff000000) >> 16) |
962 ((colr[2] & 0xff000000) >> 8);
963
964 FreeScreenDrawInfo(screen, drinfo);
965 }
966 }
967
968 if (nsoptions_default[option].value.c == nsoptions[option].value.c)
969 nsoptions[option].value.c = def_colour;
970 nsoptions_default[option].value.c = def_colour;
971
972 return NSERROR_OK;
973}
974
975/* exported interface documented in amiga/gui.h */
977{
978 if(nsscreentitle == NULL) {
979 nsscreentitle = ASPrintf("NetSurf %s", netsurf_version);
980 /* If this fails it will be NULL, which means we'll get the screen's
981 * default titlebar text instead - so no need to check for error. */
982 }
983
984 return nsscreentitle;
985}
986
987static void ami_set_screen_defaults(struct Screen *screen)
988{
989 /* various window size/position defaults */
990 int width = screen->Width / 2;
991 int height = screen->Height / 2;
992 int top = (screen->Height / 2) - (height / 2);
993 int left = (screen->Width / 2) - (width / 2);
994
995 nsoption_default_set_int(cookies_window_ypos, top);
996 nsoption_default_set_int(cookies_window_xpos, left);
997 nsoption_default_set_int(cookies_window_xsize, width);
998 nsoption_default_set_int(cookies_window_ysize, height);
999
1000 nsoption_default_set_int(history_window_ypos, top);
1001 nsoption_default_set_int(history_window_xpos, left);
1002 nsoption_default_set_int(history_window_xsize, width);
1003 nsoption_default_set_int(history_window_ysize, height);
1004
1005 nsoption_default_set_int(hotlist_window_ypos, top);
1006 nsoption_default_set_int(hotlist_window_xpos, left);
1007 nsoption_default_set_int(hotlist_window_xsize, width);
1008 nsoption_default_set_int(hotlist_window_ysize, height);
1009
1010
1011 nsoption_default_set_int(window_x, 0);
1012 nsoption_default_set_int(window_y, screen->BarHeight + 1);
1013 nsoption_default_set_int(window_width, screen->Width);
1014 nsoption_default_set_int(window_height, screen->Height - screen->BarHeight - 1);
1015
1016#ifdef __amigaos4__
1017 nsoption_default_set_int(redraw_tile_size_x, screen->Width);
1018 nsoption_default_set_int(redraw_tile_size_y, screen->Height);
1019
1020 /* set system colours for amiga ui */
1021 colour_option_from_pen(FILLPEN, NSOPTION_sys_colour_ActiveBorder, screen, 0x00000000);
1022 colour_option_from_pen(FILLPEN, NSOPTION_sys_colour_ActiveCaption, screen, 0x00dddddd);
1023 colour_option_from_pen(BACKGROUNDPEN, NSOPTION_sys_colour_AppWorkspace, screen, 0x00eeeeee);
1024 colour_option_from_pen(BACKGROUNDPEN, NSOPTION_sys_colour_Background, screen, 0x00aa0000);
1025 colour_option_from_pen(FOREGROUNDPEN, NSOPTION_sys_colour_ButtonFace, screen, 0x00aaaaaa);
1026 colour_option_from_pen(FORESHINEPEN, NSOPTION_sys_colour_ButtonHighlight, screen, 0x00cccccc);
1027 colour_option_from_pen(FORESHADOWPEN, NSOPTION_sys_colour_ButtonShadow, screen, 0x00bbbbbb);
1028 colour_option_from_pen(TEXTPEN, NSOPTION_sys_colour_ButtonText, screen, 0x00000000);
1029 colour_option_from_pen(FILLTEXTPEN, NSOPTION_sys_colour_CaptionText, screen, 0x00000000);
1030 colour_option_from_pen(DISABLEDTEXTPEN, NSOPTION_sys_colour_GrayText, screen, 0x00777777);
1031 colour_option_from_pen(SELECTPEN, NSOPTION_sys_colour_Highlight, screen, 0x00ee0000);
1032 colour_option_from_pen(SELECTTEXTPEN, NSOPTION_sys_colour_HighlightText, screen, 0x00000000);
1033 colour_option_from_pen(INACTIVEFILLPEN, NSOPTION_sys_colour_InactiveBorder, screen, 0x00000000);
1034 colour_option_from_pen(INACTIVEFILLPEN, NSOPTION_sys_colour_InactiveCaption, screen, 0x00ffffff);
1035 colour_option_from_pen(INACTIVEFILLTEXTPEN, NSOPTION_sys_colour_InactiveCaptionText, screen, 0x00cccccc);
1036 colour_option_from_pen(BACKGROUNDPEN, NSOPTION_sys_colour_InfoBackground, screen, 0x00aaaaaa);/* This is wrong, HelpHint backgrounds are pale yellow but doesn't seem to be a DrawInfo pen defined for it. */
1037 colour_option_from_pen(TEXTPEN, NSOPTION_sys_colour_InfoText, screen, 0x00000000);
1038 colour_option_from_pen(MENUBACKGROUNDPEN, NSOPTION_sys_colour_Menu, screen, 0x00aaaaaa);
1039 colour_option_from_pen(MENUTEXTPEN, NSOPTION_sys_colour_MenuText, screen, 0x00000000);
1040 colour_option_from_pen(AMINS_SCROLLERPEN, NSOPTION_sys_colour_Scrollbar, screen, 0x00aaaaaa);
1041 colour_option_from_pen(FORESHADOWPEN, NSOPTION_sys_colour_ThreeDDarkShadow, screen, 0x00555555);
1042 colour_option_from_pen(FOREGROUNDPEN, NSOPTION_sys_colour_ThreeDFace, screen, 0x00dddddd);
1043 colour_option_from_pen(FORESHINEPEN, NSOPTION_sys_colour_ThreeDHighlight, screen, 0x00aaaaaa);
1044 colour_option_from_pen(HALFSHINEPEN, NSOPTION_sys_colour_ThreeDLightShadow, screen, 0x00999999);
1045 colour_option_from_pen(HALFSHADOWPEN, NSOPTION_sys_colour_ThreeDShadow, screen, 0x00777777);
1046 colour_option_from_pen(BACKGROUNDPEN, NSOPTION_sys_colour_Window, screen, 0x00aaaaaa);
1047 colour_option_from_pen(INACTIVEFILLPEN, NSOPTION_sys_colour_WindowFrame, screen, 0x00000000);
1048 colour_option_from_pen(TEXTPEN, NSOPTION_sys_colour_WindowText, screen, 0x00000000);
1049#else
1050 nsoption_default_set_int(redraw_tile_size_x, 100);
1051 nsoption_default_set_int(redraw_tile_size_y, 100);
1052#endif
1053}
1054
1055
1056/**
1057 * Set option defaults for amiga frontend
1058 *
1059 * @param defaults The option table to update.
1060 * @return error status.
1061 */
1063{
1064 STRPTR tempacceptlangs;
1065 char temp[1024];
1066 int codeset = 0;
1067
1068 /* The following line disables the popupmenu.class select menu.
1069 ** It's not recommended to use it!
1070 */
1071 nsoption_set_bool(core_select_menu, true);
1072
1073 /* ClickTab < 53 doesn't work with the auto show/hide tab-bar (for reasons forgotten) */
1074 if(ClickTabBase->lib_Version < 53)
1075 nsoption_set_bool(tab_always_show, true);
1076
1077 if((!nsoption_charp(accept_language)) ||
1078 (nsoption_charp(accept_language)[0] == '\0') ||
1079 (nsoption_bool(accept_lang_locale) == true))
1080 {
1081 if((tempacceptlangs = ami_locale_langs(&codeset)))
1082 {
1083 nsoption_set_charp(accept_language,
1084 (char *)strdup(tempacceptlangs));
1085 FreeVec(tempacceptlangs);
1086 }
1087 }
1088
1089 /* Some OS-specific overrides */
1090#ifdef __amigaos4__
1091 if(!LIB_IS_AT_LEAST((struct Library *)SysBase, 53, 89)) {
1092 /* Disable ExtMem usage pre-OS4.1FEU1 */
1093 nsoption_set_bool(use_extmem, false);
1094 }
1095
1096 if(codeset == 0) codeset = 4; /* ISO-8859-1 */
1097 const char *encname = (const char *)ObtainCharsetInfo(DFCS_NUMBER, codeset,
1098 DFCS_MIMENAME);
1099 nsoption_set_charp(local_charset, strdup(encname));
1100 nsoption_set_int(local_codeset, codeset);
1101#else
1102 nsoption_set_bool(download_notify, false);
1103 nsoption_set_bool(font_antialiasing, false);
1104 nsoption_set_bool(truecolour_mouse_pointers, false);
1105 nsoption_set_bool(use_openurl_lib, true);
1106 nsoption_set_bool(bitmap_fonts, true);
1107#endif
1108
1109 sprintf(temp, "%s/Cookies", current_user_dir);
1110 nsoption_setnull_charp(cookie_file,
1111 (char *)strdup(temp));
1112
1113 sprintf(temp, "%s/Hotlist", current_user_dir);
1114 nsoption_setnull_charp(hotlist_file,
1115 (char *)strdup(temp));
1116
1117 sprintf(temp, "%s/URLdb", current_user_dir);
1118 nsoption_setnull_charp(url_file,
1119 (char *)strdup(temp));
1120
1121 sprintf(temp, "%s/FontGlyphCache", current_user_dir);
1122 nsoption_setnull_charp(font_unicode_file,
1123 (char *)strdup(temp));
1124
1125 nsoption_setnull_charp(ca_bundle,
1126 (char *)strdup("PROGDIR:Resources/ca-bundle"));
1127
1128 /* font defaults */
1129#ifdef __amigaos4__
1130 nsoption_setnull_charp(font_sans, (char *)strdup("DejaVu Sans"));
1131 nsoption_setnull_charp(font_serif, (char *)strdup("DejaVu Serif"));
1132 nsoption_setnull_charp(font_mono, (char *)strdup("DejaVu Sans Mono"));
1133 nsoption_setnull_charp(font_cursive, (char *)strdup("DejaVu Sans"));
1134 nsoption_setnull_charp(font_fantasy, (char *)strdup("DejaVu Serif"));
1135#else
1136 nsoption_setnull_charp(font_sans, (char *)strdup("helvetica"));
1137 nsoption_setnull_charp(font_serif, (char *)strdup("times"));
1138 nsoption_setnull_charp(font_mono, (char *)strdup("topaz"));
1139 nsoption_setnull_charp(font_cursive, (char *)strdup("garnet"));
1140 nsoption_setnull_charp(font_fantasy, (char *)strdup("emerald"));
1141/* Default CG fonts for OS3 - these work with use_diskfont both on and off,
1142 however they are slow in both cases. The bitmap fonts don't work when
1143 use_diskfont is off. The bitmap fonts performance on 68k is far superior,
1144 so default to those for now whilst testing.
1145 \todo maybe add some buttons to the prefs GUI to toggle?
1146 nsoption_setnull_charp(font_sans, (char *)strdup("CGTriumvirate"));
1147 nsoption_setnull_charp(font_serif, (char *)strdup("CGTimes"));
1148 nsoption_setnull_charp(font_mono, (char *)strdup("LetterGothic"));
1149 nsoption_setnull_charp(font_cursive, (char *)strdup("CGTriumvirate"));
1150 nsoption_setnull_charp(font_fantasy, (char *)strdup("CGTimes"));
1151*/
1152#endif
1153
1154 if (nsoption_charp(font_unicode) == NULL)
1155 {
1156 BPTR lock = 0;
1157 /* Search for some likely candidates */
1158
1159 if((lock = Lock("FONTS:Code2000.otag", ACCESS_READ)))
1160 {
1161 UnLock(lock);
1162 nsoption_set_charp(font_unicode,
1163 (char *)strdup("Code2000"));
1164 }
1165 else if((lock = Lock("FONTS:Bitstream Cyberbit.otag", ACCESS_READ)))
1166 {
1167 UnLock(lock);
1168 nsoption_set_charp(font_unicode,
1169 (char *)strdup("Bitstream Cyberbit"));
1170 }
1171 }
1172
1173 if (nsoption_charp(font_surrogate) == NULL) {
1174 BPTR lock = 0;
1175 /* Search for some likely candidates -
1176 * Ideally we should pick a font during the scan process which announces it
1177 * contains UCR_SURROGATES, but nothing appears to have the tag.
1178 */
1179 if((lock = Lock("FONTS:Symbola.otag", ACCESS_READ))) {
1180 UnLock(lock);
1181 nsoption_set_charp(font_surrogate,
1182 (char *)strdup("Symbola"));
1183 }
1184 }
1185
1186 return NSERROR_OK;
1187}
1188
1189static void ami_amiupdate(void)
1190{
1191 /* Create AppPath location for AmiUpdate use */
1192
1193 BPTR lock = 0;
1194
1195 if(((lock = Lock("ENVARC:AppPaths",SHARED_LOCK)) == 0))
1196 {
1197 lock = CreateDir("ENVARC:AppPaths");
1198 }
1199
1200 UnLock(lock);
1201
1202 if((lock = Lock("PROGDIR:", ACCESS_READ)))
1203 {
1204 char filename[1024];
1205 BPTR amiupdatefh;
1206
1207 DevNameFromLock(lock, (STRPTR)&filename, 1024L, DN_FULLPATH);
1208
1209 if((amiupdatefh = FOpen("ENVARC:AppPaths/NetSurf", MODE_NEWFILE, 0))) {
1210 FPuts(amiupdatefh, (CONST_STRPTR)&filename);
1211 FClose(amiupdatefh);
1212 }
1213
1214 UnLock(lock);
1215 }
1216}
1217
1218static nsurl *gui_get_resource_url(const char *path)
1219{
1220 char buf[1024];
1221 nsurl *url = NULL;
1222
1223 if(ami_locate_resource(buf, path) == false)
1224 return NULL;
1225
1226 netsurf_path_to_nsurl(buf, &url);
1227
1228 return url;
1229}
1230
1231HOOKF(void, ami_gui_newprefs_hook, APTR, window, APTR)
1232{
1234}
1235
1236static void ami_openscreen(void)
1237{
1238 ULONG id = 0;
1239 ULONG compositing;
1240
1241 if (nsoption_int(screen_compositing) == -1)
1242 compositing = ~0UL;
1243 else compositing = nsoption_int(screen_compositing);
1244
1245 if (nsoption_charp(pubscreen_name) == NULL)
1246 {
1247 if((nsoption_charp(screen_modeid)) &&
1248 (strncmp(nsoption_charp(screen_modeid), "0x", 2) == 0))
1249 {
1250 id = strtoul(nsoption_charp(screen_modeid), NULL, 0);
1251 }
1252 else
1253 {
1254 struct ScreenModeRequester *screenmodereq = NULL;
1255
1256 if((screenmodereq = AllocAslRequest(ASL_ScreenModeRequest,NULL))) {
1257 if(AslRequestTags(screenmodereq,
1258 ASLSM_MinDepth, 0,
1259 ASLSM_MaxDepth, 32,
1260 TAG_DONE))
1261 {
1262 char *modeid = malloc(20);
1263 id = screenmodereq->sm_DisplayID;
1264 sprintf(modeid, "0x%lx", id);
1265 nsoption_set_charp(screen_modeid, modeid);
1267 }
1268 FreeAslRequest(screenmodereq);
1269 }
1270 }
1271
1272 if(screen_signal == -1) screen_signal = AllocSignal(-1);
1273 NSLOG(netsurf, INFO, "Screen signal %d", screen_signal);
1274 scrn = OpenScreenTags(NULL,
1275 /**\todo specify screen depth */
1276 SA_DisplayID, id,
1277 SA_Title, ami_gui_get_screen_title(),
1278 SA_Type, PUBLICSCREEN,
1279 SA_PubName, "NetSurf",
1280 SA_PubSig, screen_signal,
1281 SA_PubTask, FindTask(0),
1282 SA_LikeWorkbench, TRUE,
1283 SA_Compositing, compositing,
1284 TAG_DONE);
1285
1286 if(scrn)
1287 {
1288 PubScreenStatus(scrn,0);
1289 }
1290 else
1291 {
1292 FreeSignal(screen_signal);
1293 screen_signal = -1;
1294
1295 if((scrn = LockPubScreen("NetSurf")))
1296 {
1297 locked_screen = TRUE;
1298 }
1299 else
1300 {
1301 nsoption_set_charp(pubscreen_name,
1302 strdup("Workbench"));
1303 }
1304 }
1305 }
1306
1307 if (nsoption_charp(pubscreen_name) != NULL)
1308 {
1309 scrn = LockPubScreen(nsoption_charp(pubscreen_name));
1310
1311 if(scrn == NULL)
1312 {
1313 scrn = LockPubScreen("Workbench");
1314 }
1315 locked_screen = TRUE;
1316 }
1317
1321}
1322
1323static void ami_openscreenfirst(void)
1324{
1326 if(browserglob == NULL) browserglob = ami_plot_ra_alloc(0, 0, false, false);
1328}
1329
1330static struct RDArgs *ami_gui_commandline(int *restrict argc, char ** argv,
1331 int *restrict nargc, char ** nargv)
1332{
1333 struct RDArgs *args;
1334 CONST_STRPTR template = "-v/S,NSOPTS/M,URL/K,USERSDIR/K,FORCE/S";
1335 long rarray[] = {0,0,0,0,0};
1336 enum
1337 {
1338 A_VERBOSE, /* ignored */
1339 A_NSOPTS, /* ignored */
1340 A_URL,
1341 A_USERSDIR,
1342 A_FORCE
1343 };
1344
1345 if(*argc == 0) return NULL; // argc==0 is started from wb
1346
1347 if((args = ReadArgs(template, rarray, NULL))) {
1348 if(rarray[A_URL]) {
1349 NSLOG(netsurf, INFO,
1350 "URL %s specified on command line",
1351 (char *)rarray[A_URL]);
1352 temp_homepage_url = strdup((char *)rarray[A_URL]); /**\todo allow IDNs */
1353 }
1354
1355 if(rarray[A_USERSDIR]) {
1356 NSLOG(netsurf, INFO,
1357 "USERSDIR %s specified on command line",
1358 (char *)rarray[A_USERSDIR]);
1359 users_dir = ASPrintf("%s", rarray[A_USERSDIR]);
1360 }
1361
1362 if(rarray[A_FORCE]) {
1363 NSLOG(netsurf, INFO,
1364 "FORCE specified on command line");
1365 cli_force = true;
1366 }
1367
1368 if(rarray[A_NSOPTS]) {
1369 /* The NSOPTS/M parameter specified in the ReadArgs template is
1370 * special. The /M means it collects all arguments that can't
1371 * be assigned to any other parameter, and stores them in an
1372 * array. We collect these and pass them as a fake argc/argv
1373 * to nsoption_commandline().
1374 * This trickery is necessary because if ReadArgs() is called
1375 * first, nsoption_commandline() can no longer parse (fetch?)
1376 * the arguments. If nsoption_commandline() is called first,
1377 * then ReadArgs cannot fetch the arguments.
1378 *\todo this was totally broken so to stop startup crashing
1379 * has been temporarily removed (core cli not called when func
1380 * returns NULL).
1381 */
1382 }
1383 } else {
1384 NSLOG(netsurf, INFO, "ReadArgs failed to parse command line");
1385 }
1386
1387 FreeArgs(args);
1388 return NULL;
1389}
1390
1391static char *ami_gui_read_tooltypes(struct WBArg *wbarg)
1392{
1393 struct DiskObject *dobj;
1394 STRPTR *toolarray;
1395 char *s;
1396 char *current_user = NULL;
1397
1398 if((*wbarg->wa_Name) && (dobj = GetDiskObject(wbarg->wa_Name))) {
1399 toolarray = (STRPTR *)dobj->do_ToolTypes;
1400
1401 if((s = (char *)FindToolType(toolarray,"USERSDIR"))) users_dir = ASPrintf("%s", s);
1402 if((s = (char *)FindToolType(toolarray,"USER"))) current_user = ASPrintf("%s", s);
1403
1404 FreeDiskObject(dobj);
1405 }
1406 return current_user;
1407}
1408
1409static STRPTR ami_gui_read_all_tooltypes(int argc, char **argv)
1410{
1411 struct WBStartup *WBenchMsg;
1412 struct WBArg *wbarg;
1413 char i = 0;
1414 char *current_user = NULL;
1415 char *cur_user = NULL;
1416
1417 if(argc == 0) { /* Started from WB */
1418 WBenchMsg = (struct WBStartup *)argv;
1419 for(i = 0, wbarg = WBenchMsg->sm_ArgList; i < WBenchMsg->sm_NumArgs; i++,wbarg++) {
1420 LONG olddir =-1;
1421 if((wbarg->wa_Lock) && (*wbarg->wa_Name))
1422 olddir = SetCurrentDir(wbarg->wa_Lock);
1423
1424 cur_user = ami_gui_read_tooltypes(wbarg);
1425 if(cur_user != NULL) {
1426 if(current_user != NULL) FreeVec(current_user);
1427 current_user = cur_user;
1428 }
1429
1430 if(olddir !=-1) SetCurrentDir(olddir);
1431 }
1432 }
1433
1434 return current_user;
1435}
1436
1437static void gui_init2(int argc, char** argv)
1438{
1439 struct Screen *screen;
1440 BOOL notalreadyrunning;
1441 nsurl *url;
1442 nserror error;
1443 struct browser_window *bw = NULL;
1444
1445 notalreadyrunning = ami_arexx_init(&rxsig);
1446
1447 /* ...and this ensures the treeview at least gets the WB colour palette to work with */
1448 if(scrn == NULL) {
1449 if((screen = LockPubScreen("Workbench"))) {
1451 UnlockPubScreen(NULL, screen);
1452 }
1453 } else {
1455 }
1456 /**/
1457
1458 hotlist_init(nsoption_charp(hotlist_file),
1459 nsoption_charp(hotlist_file));
1460 search_web_select_provider(nsoption_charp(search_web_provider));
1461
1462 if (notalreadyrunning &&
1463 (nsoption_bool(startup_no_window) == false))
1465
1466 if(cli_force == true) {
1467 notalreadyrunning = TRUE;
1468 }
1469
1470 if(temp_homepage_url && notalreadyrunning) {
1471 error = nsurl_create(temp_homepage_url, &url);
1472 if (error == NSERROR_OK) {
1474 url,
1475 NULL,
1476 NULL,
1477 &bw);
1478 nsurl_unref(url);
1479 }
1480 if (error != NSERROR_OK) {
1482 }
1483 free(temp_homepage_url);
1484 temp_homepage_url = NULL;
1485 }
1486
1487 if(argc == 0) { // WB
1488 struct WBStartup *WBenchMsg = (struct WBStartup *)argv;
1489 struct WBArg *wbarg;
1490 int first=0,i=0;
1491 char fullpath[1024];
1492
1493 for(i=0,wbarg=WBenchMsg->sm_ArgList;i<WBenchMsg->sm_NumArgs;i++,wbarg++)
1494 {
1495 if(i==0) continue;
1496 if((wbarg->wa_Lock)&&(*wbarg->wa_Name))
1497 {
1498 DevNameFromLock(wbarg->wa_Lock,fullpath,1024,DN_FULLPATH);
1499 AddPart(fullpath,wbarg->wa_Name,1024);
1500
1501 if(!temp_homepage_url) {
1502 nsurl *temp_url;
1503 if (netsurf_path_to_nsurl(fullpath, &temp_url) == NSERROR_OK) {
1504 temp_homepage_url = strdup(nsurl_access(temp_url));
1505 nsurl_unref(temp_url);
1506 }
1507 }
1508
1509 if(notalreadyrunning)
1510 {
1511 error = nsurl_create(temp_homepage_url, &url);
1512
1513 if (error == NSERROR_OK) {
1514 if(!first)
1515 {
1517 url,
1518 NULL,
1519 NULL,
1520 &bw);
1521
1522 first=1;
1523 }
1524 else
1525 {
1527 url,
1528 NULL,
1529 bw,
1530 &bw);
1531
1532 }
1533 nsurl_unref(url);
1534
1535 }
1536 if (error != NSERROR_OK) {
1538 }
1539 free(temp_homepage_url);
1540 temp_homepage_url = NULL;
1541 }
1542 }
1543 /* this should be where we read tooltypes, but it's too late for that now */
1544 }
1545 }
1546
1547 nsoption_setnull_charp(homepage_url, (char *)strdup(NETSURF_HOMEPAGE));
1548
1549 if(!notalreadyrunning)
1550 {
1551 STRPTR sendcmd = NULL;
1552 char newtab[11] = "\0";
1553
1554 if(nsoption_bool(tab_new_session) == true) {
1555 strcpy(newtab, "TAB ACTIVE");
1556 }
1557
1558 if(temp_homepage_url) {
1559 sendcmd = ASPrintf("OPEN \"%s\" NEW%s", temp_homepage_url, newtab);
1560 free(temp_homepage_url);
1561 temp_homepage_url = NULL;
1562 } else {
1563 sendcmd = ASPrintf("OPEN \"%s\" NEW%s", nsoption_charp(homepage_url), newtab);
1564 }
1565 ami_arexx_self(sendcmd);
1566 FreeVec(sendcmd);
1567
1568 /* Bring the screen to the front. Intuition may have already done this, but it doesn't hurt. */
1569 ami_arexx_self("TOFRONT");
1570
1571 ami_quit=true;
1572 return;
1573 }
1574#ifdef __amigaos4__
1575 if(IApplication)
1576 {
1577 if(argc == 0)
1578 {
1579 ULONG noicon = TAG_IGNORE;
1580
1581 if (nsoption_bool(hide_docky_icon))
1582 noicon = REGAPP_NoIcon;
1583
1584 ami_appid = RegisterApplication(messages_get("NetSurf"),
1585 REGAPP_URLIdentifier, "netsurf-browser.org",
1586 REGAPP_WBStartup, (struct WBStartup *)argv,
1587 noicon, TRUE,
1588 REGAPP_HasPrefsWindow, TRUE,
1589 REGAPP_CanCreateNewDocs, TRUE,
1590 REGAPP_UniqueApplication, TRUE,
1591 REGAPP_Description, messages_get("NetSurfDesc"),
1592 TAG_DONE);
1593 }
1594 else
1595 {
1596/* TODO: Specify icon when run from Shell */
1597 ami_appid = RegisterApplication(messages_get("NetSurf"),
1598 REGAPP_URLIdentifier, "netsurf-browser.org",
1599 REGAPP_FileName, argv[0],
1600 REGAPP_NoIcon, TRUE,
1601 REGAPP_HasPrefsWindow, TRUE,
1602 REGAPP_CanCreateNewDocs, TRUE,
1603 REGAPP_UniqueApplication, TRUE,
1604 REGAPP_Description, messages_get("NetSurfDesc"),
1605 TAG_DONE);
1606 }
1607
1608 GetApplicationAttrs(ami_appid, APPATTR_Port, (ULONG)&applibport, TAG_DONE);
1609 if(applibport) applibsig = (1L << applibport->mp_SigBit);
1610 }
1611#endif
1612 if(!bw && (nsoption_bool(startup_no_window) == false)) {
1613 error = nsurl_create(nsoption_charp(homepage_url), &url);
1614 if (error == NSERROR_OK) {
1616 url,
1617 NULL,
1618 NULL,
1619 NULL);
1620 nsurl_unref(url);
1621 }
1622 if (error != NSERROR_OK) {
1624 }
1625 }
1626}
1627
1628static void ami_update_buttons(struct gui_window_2 *gwin)
1629{
1630 long back=FALSE, forward=FALSE, tabclose=FALSE, stop=FALSE, reload=FALSE;
1631 long s_back, s_forward, s_tabclose, s_stop, s_reload;
1632
1634 back=TRUE;
1635
1637 forward=TRUE;
1638
1640 stop=TRUE;
1641
1643 reload=TRUE;
1644
1645 if(nsoption_bool(kiosk_mode) == false) {
1646 if(gwin->tabs <= 1) {
1647 tabclose=TRUE;
1648 ami_gui_menu_set_disabled(gwin->win, gwin->imenu, M_CLOSETAB, true);
1649 } else {
1650 ami_gui_menu_set_disabled(gwin->win, gwin->imenu, M_CLOSETAB, false);
1651 }
1652 }
1653
1654 GetAttr(GA_Disabled, gwin->objects[GID_BACK], (uint32 *)&s_back);
1655 GetAttr(GA_Disabled, gwin->objects[GID_FORWARD], (uint32 *)&s_forward);
1656 GetAttr(GA_Disabled, gwin->objects[GID_RELOAD], (uint32 *)&s_reload);
1657 GetAttr(GA_Disabled, gwin->objects[GID_STOP], (uint32 *)&s_stop);
1658
1659 if(BOOL_MISMATCH(s_back, back))
1660 SetGadgetAttrs((struct Gadget *)gwin->objects[GID_BACK],
1661 gwin->win, NULL, GA_Disabled, back, TAG_DONE);
1662
1663 if(BOOL_MISMATCH(s_forward, forward))
1664 SetGadgetAttrs((struct Gadget *)gwin->objects[GID_FORWARD],
1665 gwin->win, NULL, GA_Disabled, forward, TAG_DONE);
1666
1667 if(BOOL_MISMATCH(s_reload, reload))
1668 SetGadgetAttrs((struct Gadget *)gwin->objects[GID_RELOAD],
1669 gwin->win, NULL, GA_Disabled, reload, TAG_DONE);
1670
1671 if(BOOL_MISMATCH(s_stop, stop))
1672 SetGadgetAttrs((struct Gadget *)gwin->objects[GID_STOP],
1673 gwin->win, NULL, GA_Disabled, stop, TAG_DONE);
1674
1675 if(ClickTabBase->lib_Version < 53) {
1676 if(gwin->tabs <= 1) tabclose = TRUE;
1677
1678 GetAttr(GA_Disabled, gwin->objects[GID_CLOSETAB], (uint32 *)&s_tabclose);
1679
1680 if(BOOL_MISMATCH(s_tabclose, tabclose))
1681 SetGadgetAttrs((struct Gadget *)gwin->objects[GID_CLOSETAB],
1682 gwin->win, NULL, GA_Disabled, tabclose, TAG_DONE);
1683 }
1684
1685 /* Update the back/forward buttons history context menu */
1688}
1689
1690void ami_gui_history(struct gui_window_2 *gwin, bool back)
1691{
1692 if(back == true)
1693 {
1695 browser_window_history_back(gwin->gw->bw, false);
1696 }
1697 else
1698 {
1700 browser_window_history_forward(gwin->gw->bw, false);
1701 }
1702
1703 ami_update_buttons(gwin);
1704}
1705
1706int ami_key_to_nskey(ULONG keycode, struct InputEvent *ie)
1707{
1708 int nskey = 0, chars;
1709 char buffer[20];
1710 char *utf8 = NULL;
1711
1712 if(keycode >= IECODE_UP_PREFIX) return 0;
1713
1714 switch(keycode)
1715 {
1716 case RAWKEY_CRSRUP:
1717 if(ie->ie_Qualifier & NSA_QUAL_SHIFT) {
1718 nskey = NS_KEY_PAGE_UP;
1719 } else if(ie->ie_Qualifier & NSA_QUAL_ALT) {
1720 nskey = NS_KEY_TEXT_START;
1721 }
1722 else nskey = NS_KEY_UP;
1723 break;
1724 case RAWKEY_CRSRDOWN:
1725 if(ie->ie_Qualifier & NSA_QUAL_SHIFT) {
1726 nskey = NS_KEY_PAGE_DOWN;
1727 } else if(ie->ie_Qualifier & NSA_QUAL_ALT) {
1728 nskey = NS_KEY_TEXT_END;
1729 }
1730 else nskey = NS_KEY_DOWN;
1731 break;
1732 case RAWKEY_CRSRLEFT:
1733 if(ie->ie_Qualifier & NSA_QUAL_SHIFT) {
1734 nskey = NS_KEY_LINE_START;
1735 }else if(ie->ie_Qualifier & NSA_QUAL_ALT) {
1736 nskey = NS_KEY_WORD_LEFT;
1737 }
1738 else nskey = NS_KEY_LEFT;
1739 break;
1740 case RAWKEY_CRSRRIGHT:
1741 if(ie->ie_Qualifier & NSA_QUAL_SHIFT) {
1742 nskey = NS_KEY_LINE_END;
1743 }else if(ie->ie_Qualifier & NSA_QUAL_ALT) {
1744 nskey = NS_KEY_WORD_RIGHT;
1745 }
1746 else nskey = NS_KEY_RIGHT;
1747 break;
1748 case RAWKEY_ESC:
1749 nskey = NS_KEY_ESCAPE;
1750 break;
1751 case RAWKEY_PAGEUP:
1752 nskey = NS_KEY_PAGE_UP;
1753 break;
1754 case RAWKEY_PAGEDOWN:
1755 nskey = NS_KEY_PAGE_DOWN;
1756 break;
1757 case RAWKEY_HOME:
1758 nskey = NS_KEY_TEXT_START;
1759 break;
1760 case RAWKEY_END:
1761 nskey = NS_KEY_TEXT_END;
1762 break;
1763 case RAWKEY_BACKSPACE:
1764 if(ie->ie_Qualifier & NSA_QUAL_SHIFT) {
1766 } else {
1767 nskey = NS_KEY_DELETE_LEFT;
1768 }
1769 break;
1770 case RAWKEY_DEL:
1771 if(ie->ie_Qualifier & NSA_QUAL_SHIFT) {
1772 nskey = NS_KEY_DELETE_LINE_END;
1773 } else {
1774 nskey = NS_KEY_DELETE_RIGHT;
1775 }
1776 break;
1777 case RAWKEY_TAB:
1778 if(ie->ie_Qualifier & NSA_QUAL_SHIFT) {
1779 nskey = NS_KEY_SHIFT_TAB;
1780 } else {
1781 nskey = NS_KEY_TAB;
1782 }
1783 break;
1784 case RAWKEY_F5:
1785 case RAWKEY_F8:
1786 case RAWKEY_F9:
1787 case RAWKEY_F10:
1788 case RAWKEY_F12:
1789 case RAWKEY_HELP:
1790 // don't translate
1791 nskey = keycode;
1792 break;
1793 default:
1794 if((chars = MapRawKey(ie,buffer,20,NULL)) > 0) {
1795 if(utf8_from_local_encoding(buffer, chars, &utf8) != NSERROR_OK) return 0;
1796 nskey = utf8_to_ucs4(utf8, utf8_char_byte_length(utf8));
1797 free(utf8);
1798
1799 if(ie->ie_Qualifier & IEQUALIFIER_RCOMMAND) {
1800 switch(nskey) {
1801 case 'a':
1802 nskey = NS_KEY_SELECT_ALL;
1803 break;
1804 case 'c':
1805 nskey = NS_KEY_COPY_SELECTION;
1806 break;
1807 case 'v':
1808 nskey = NS_KEY_PASTE;
1809 break;
1810 case 'x':
1811 nskey = NS_KEY_CUT_SELECTION;
1812 break;
1813 case 'y':
1814 nskey = NS_KEY_REDO;
1815 break;
1816 case 'z':
1817 nskey = NS_KEY_UNDO;
1818 break;
1819 }
1820 }
1821 }
1822 break;
1823 }
1824
1825 return nskey;
1826}
1827
1828int ami_gui_get_quals(Object *win_obj)
1829{
1830 uint32 quals = 0;
1831 int key_state = 0;
1832#ifdef __amigaos4__
1833 GetAttr(WINDOW_Qualifier, win_obj, (uint32 *)&quals);
1834#else
1835#warning qualifier needs fixing for OS3
1836#endif
1837
1838 if(quals & NSA_QUAL_SHIFT) {
1839 key_state |= BROWSER_MOUSE_MOD_1;
1840 }
1841
1842 if(quals & IEQUALIFIER_CONTROL) {
1843 key_state |= BROWSER_MOUSE_MOD_2;
1844 }
1845
1846 if(quals & NSA_QUAL_ALT) {
1847 key_state |= BROWSER_MOUSE_MOD_3;
1848 }
1849
1850 return key_state;
1851}
1852
1853static void ami_update_quals(struct gui_window_2 *gwin)
1854{
1856}
1857
1858/* exported interface documented in amiga/gui.h */
1859nserror ami_gui_get_space_box(Object *obj, struct IBox **bbox)
1860{
1861#ifdef __amigaos4__
1862 if(LIB_IS_AT_LEAST((struct Library *)SpaceBase, 53, 6)) {
1863 *bbox = malloc(sizeof(struct IBox));
1864 if(*bbox == NULL) return NSERROR_NOMEM;
1865 GetAttr(SPACE_RenderBox, obj, (ULONG *)*bbox);
1866 } else
1867#endif
1868 {
1869 GetAttr(SPACE_AreaBox, obj, (ULONG *)bbox);
1870 }
1871
1872 return NSERROR_OK;
1873}
1874
1875/* exported interface documented in amiga/gui.h */
1876void ami_gui_free_space_box(struct IBox *bbox)
1877{
1878#ifdef __amigaos4__
1879 if(LIB_IS_AT_LEAST((struct Library *)SpaceBase, 53, 6)) {
1880 free(bbox);
1881 }
1882#endif
1883}
1884
1886 int *restrict x, int *restrict y, int space_x, int space_y)
1887{
1888 int ns_x = space_x;
1889 int ns_y = space_y;
1890
1891 ns_x += gwin->gw->scrollx;
1892 ns_y += gwin->gw->scrolly;
1893
1894 *x = ns_x;
1895 *y = ns_y;
1896
1897 return true;
1898}
1899
1900bool ami_mouse_to_ns_coords(struct gui_window_2 *gwin, int *restrict x, int *restrict y,
1901 int mouse_x, int mouse_y)
1902{
1903 int ns_x, ns_y;
1904 struct IBox *bbox;
1905
1906 if(mouse_x == -1) mouse_x = gwin->win->MouseX;
1907 if(mouse_y == -1) mouse_y = gwin->win->MouseY;
1908
1909 if(ami_gui_get_space_box((Object *)gwin->objects[GID_BROWSER], &bbox) == NSERROR_OK) {
1910 ns_x = (ULONG)(mouse_x - bbox->Left);
1911 ns_y = (ULONG)(mouse_y - bbox->Top);
1912
1913 if((ns_x < 0) || (ns_x > bbox->Width) || (ns_y < 0) || (ns_y > bbox->Height))
1914 return false;
1915
1917 } else {
1918 amiga_warn_user("NoMemory", "");
1919 return false;
1920 }
1921
1922 return ami_spacebox_to_ns_coords(gwin, x, y, ns_x, ns_y);
1923}
1924
1925static void ami_gui_scroll_internal(struct gui_window_2 *gwin, int xs, int ys)
1926{
1927 struct IBox *bbox;
1928 int x, y;
1929 struct rect rect;
1930
1931 if(ami_mouse_to_ns_coords(gwin, &x, &y, -1, -1) == true)
1932 {
1933 if(browser_window_scroll_at_point(gwin->gw->bw, x, y, xs, ys) == false)
1934 {
1935 int width, height;
1936
1938 &gwin->gw->scrollx,
1939 &gwin->gw->scrolly);
1940
1941 if(ami_gui_get_space_box((Object *)gwin->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
1942 amiga_warn_user("NoMemory", "");
1943 return;
1944 }
1945
1946 browser_window_get_extents(gwin->gw->bw, false, &width, &height);
1947
1948 switch(xs)
1949 {
1950 case SCROLL_PAGE_UP:
1951 xs = gwin->gw->scrollx - bbox->Width;
1952 break;
1953
1954 case SCROLL_PAGE_DOWN:
1955 xs = gwin->gw->scrollx + bbox->Width;
1956 break;
1957
1958 case SCROLL_TOP:
1959 xs = 0;
1960 break;
1961
1962 case SCROLL_BOTTOM:
1963 xs = width;
1964 break;
1965
1966 default:
1967 xs += gwin->gw->scrollx;
1968 break;
1969 }
1970
1971 switch(ys)
1972 {
1973 case SCROLL_PAGE_UP:
1974 ys = gwin->gw->scrolly - bbox->Height;
1975 break;
1976
1977 case SCROLL_PAGE_DOWN:
1978 ys = gwin->gw->scrolly + bbox->Height;
1979 break;
1980
1981 case SCROLL_TOP:
1982 ys = 0;
1983 break;
1984
1985 case SCROLL_BOTTOM:
1986 ys = height;
1987 break;
1988
1989 default:
1990 ys += gwin->gw->scrolly;
1991 break;
1992 }
1993
1995 rect.x0 = rect.x1 = xs;
1996 rect.y0 = rect.y1 = ys;
1997 gui_window_set_scroll(gwin->gw, &rect);
1998 }
1999 }
2000}
2001
2002static struct IBox *ami_ns_rect_to_ibox(struct gui_window_2 *gwin, const struct rect *rect)
2003{
2004 struct IBox *bbox, *ibox;
2005
2006 ibox = malloc(sizeof(struct IBox));
2007 if(ibox == NULL) return NULL;
2008
2009 if(ami_gui_get_space_box((Object *)gwin->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
2010 free(ibox);
2011 amiga_warn_user("NoMemory", "");
2012 return NULL;
2013 }
2014
2015 ibox->Left = gwin->win->MouseX + (rect->x0);
2016 ibox->Top = gwin->win->MouseY + (rect->y0);
2017
2018 ibox->Width = (rect->x1 - rect->x0);
2019 ibox->Height = (rect->y1 - rect->y0);
2020
2021 if(ibox->Left < bbox->Left) ibox->Left = bbox->Left;
2022 if(ibox->Top < bbox->Top) ibox->Top = bbox->Top;
2023
2024 if((ibox->Left > (bbox->Left + bbox->Width)) ||
2025 (ibox->Top > (bbox->Top + bbox->Height)) ||
2026 (ibox->Width < 0) || (ibox->Height < 0))
2027 {
2028 free(ibox);
2030 return NULL;
2031 }
2032
2034 return ibox;
2035}
2036
2037static void ami_gui_trap_mouse(struct gui_window_2 *gwin)
2038{
2039#ifdef __amigaos4__
2040 switch(gwin->drag_op)
2041 {
2042 case GDRAGGING_NONE:
2044 case GDRAGGING_OTHER:
2045 break;
2046
2047 default:
2048 if(gwin->ptr_lock)
2049 {
2050 SetWindowAttrs(gwin->win, WA_GrabFocus, 10,
2051 WA_MouseLimits, gwin->ptr_lock, TAG_DONE);
2052 }
2053 break;
2054 }
2055#endif
2056}
2057
2059{
2060 struct nsObject *node;
2061 struct nsObject *nnode;
2062 struct gui_window_2 *gwin;
2063
2064 if(IsMinListEmpty(window_list)) return;
2065
2066 node = (struct nsObject *)GetHead((struct List *)window_list);
2067
2068 do {
2069 nnode=(struct nsObject *)GetSucc((struct Node *)node);
2070 gwin = node->objstruct;
2071
2072 if(node->Type == AMINS_WINDOW)
2073 {
2075 }
2076 } while((node = nnode));
2077}
2078
2079/**
2080 * Find the current dimensions of a amiga browser window content area.
2081 *
2082 * \param gw The gui window to measure content area of.
2083 * \param width receives width of window
2084 * \param height receives height of window
2085 * \return NSERROR_OK on sucess and width and height updated
2086 * else error code.
2087 */
2088static nserror
2090 int *restrict width,
2091 int *restrict height)
2092{
2093 struct IBox *bbox;
2094 nserror res;
2095
2096 res = ami_gui_get_space_box((Object *)gw->shared->objects[GID_BROWSER],
2097 &bbox);
2098 if (res != NSERROR_OK) {
2099 amiga_warn_user("NoMemory", "");
2100 return res;
2101 }
2102
2103 *width = bbox->Width;
2104 *height = bbox->Height;
2105
2107
2108 return NSERROR_OK;
2109}
2110
2111/* Add a horizontal scroller, if not already present
2112 * Returns true if changed, false otherwise */
2113static bool ami_gui_hscroll_add(struct gui_window_2 *gwin)
2114{
2115 struct TagItem attrs[2];
2116
2117 if(gwin->objects[GID_HSCROLL] != NULL) return false;
2118
2119 attrs[0].ti_Tag = CHILD_MinWidth;
2120 attrs[0].ti_Data = 0;
2121 attrs[1].ti_Tag = TAG_DONE;
2122 attrs[1].ti_Data = 0;
2123
2125 GA_ID, GID_HSCROLL,
2126 GA_RelVerify, TRUE,
2127 SCROLLER_Orientation, SORIENT_HORIZ,
2128 ICA_TARGET, ICTARGET_IDCMP,
2129 ScrollerEnd;
2130#ifdef __amigaos4__
2131 IDoMethod(gwin->objects[GID_HSCROLLLAYOUT], LM_ADDCHILD,
2132 gwin->win, gwin->objects[GID_HSCROLL], attrs);
2133#else
2134 SetAttrs(gwin->objects[GID_HSCROLLLAYOUT],
2135 LAYOUT_AddChild, gwin->objects[GID_HSCROLL], TAG_MORE, &attrs);
2136#endif
2137 return true;
2138}
2139
2140/* Remove the horizontal scroller, if present */
2141static bool ami_gui_hscroll_remove(struct gui_window_2 *gwin)
2142{
2143 if(gwin->objects[GID_HSCROLL] == NULL) return false;
2144
2145#ifdef __amigaos4__
2146 IDoMethod(gwin->objects[GID_HSCROLLLAYOUT], LM_REMOVECHILD,
2147 gwin->win, gwin->objects[GID_HSCROLL]);
2148#else
2149 SetAttrs(gwin->objects[GID_HSCROLLLAYOUT], LAYOUT_RemoveChild, gwin->objects[GID_HSCROLL], TAG_DONE);
2150#endif
2151
2152 gwin->objects[GID_HSCROLL] = NULL;
2153
2154 return true;
2155}
2156
2157/* Add a vertical scroller, if not already present
2158 * Returns true if changed, false otherwise */
2159static bool ami_gui_vscroll_add(struct gui_window_2 *gwin)
2160{
2161 struct TagItem attrs[2];
2162
2163 if(gwin->objects[GID_VSCROLL] != NULL) return false;
2164
2165 attrs[0].ti_Tag = CHILD_MinWidth;
2166 attrs[0].ti_Data = 0;
2167 attrs[1].ti_Tag = TAG_DONE;
2168 attrs[1].ti_Data = 0;
2169
2171 GA_ID, GID_VSCROLL,
2172 GA_RelVerify, TRUE,
2173 ICA_TARGET, ICTARGET_IDCMP,
2174 ScrollerEnd;
2175#ifdef __amigaos4__
2176 IDoMethod(gwin->objects[GID_VSCROLLLAYOUT], LM_ADDCHILD,
2177 gwin->win, gwin->objects[GID_VSCROLL], attrs);
2178#else
2179 SetAttrs(gwin->objects[GID_VSCROLLLAYOUT],
2180 LAYOUT_AddChild, gwin->objects[GID_VSCROLL], TAG_MORE, &attrs);
2181#endif
2182 return true;
2183}
2184
2185/* Remove the vertical scroller, if present */
2186static bool ami_gui_vscroll_remove(struct gui_window_2 *gwin)
2187{
2188 if(gwin->objects[GID_VSCROLL] == NULL) return false;
2189
2190#ifdef __amigaos4__
2191 IDoMethod(gwin->objects[GID_VSCROLLLAYOUT], LM_REMOVECHILD,
2192 gwin->win, gwin->objects[GID_VSCROLL]);
2193#else
2194 SetAttrs(gwin->objects[GID_VSCROLLLAYOUT], LAYOUT_RemoveChild, gwin->objects[GID_VSCROLL], TAG_DONE);
2195#endif
2196
2197 gwin->objects[GID_VSCROLL] = NULL;
2198
2199 return true;
2200}
2201
2202/**
2203 * Check the scroll bar requirements for a browser window, and add/remove
2204 * the vertical scroller as appropriate. This should be the main entry
2205 * point used to perform this task.
2206 *
2207 * \param gwin "Shared" GUI window to check the state of
2208 */
2209static void ami_gui_scroller_update(struct gui_window_2 *gwin)
2210{
2211 int h = 1, w = 1, wh = 0, ww = 0;
2212 bool rethinkv = false;
2213 bool rethinkh = false;
2216
2217 browser_window_get_scrollbar_type(gwin->gw->bw, &hscroll, &vscroll);
2218
2219 if(browser_window_is_frameset(gwin->gw->bw) == true) {
2220 rethinkv = ami_gui_vscroll_remove(gwin);
2221 rethinkh = ami_gui_hscroll_remove(gwin);
2222 } else {
2223 if((browser_window_get_extents(gwin->gw->bw, false, &w, &h) == NSERROR_OK)) {
2224 gui_window_get_dimensions(gwin->gw, &ww, &wh);
2225 }
2226
2227 if(vscroll == BW_SCROLLING_NO) {
2228 rethinkv = ami_gui_vscroll_remove(gwin);
2229 } else {
2230 if (h > wh) rethinkv = ami_gui_vscroll_add(gwin);
2231 else rethinkv = ami_gui_vscroll_remove(gwin);
2232 }
2233
2234 if(hscroll == BW_SCROLLING_NO) {
2235 rethinkh = ami_gui_hscroll_remove(gwin);
2236 } else {
2237 if (w > ww) rethinkh = ami_gui_hscroll_add(gwin);
2238 else rethinkh = ami_gui_hscroll_remove(gwin);
2239 }
2240 }
2241
2242 if(rethinkv || rethinkh) {
2243 FlushLayoutDomainCache((struct Gadget *)gwin->objects[GID_MAIN]);
2244 RethinkLayout((struct Gadget *)gwin->objects[GID_MAIN],
2245 gwin->win, NULL, TRUE);
2247 }
2248}
2249
2250/* For future use
2251static void ami_gui_console_log_clear(struct gui_window *g)
2252{
2253 if(g->shared->objects[GID_LOG] != NULL) {
2254 SetGadgetAttrs((struct Gadget *)g->shared->objects[GID_LOG], g->shared->win, NULL,
2255 LISTBROWSER_Labels, NULL,
2256 TAG_DONE);
2257 }
2258
2259 FreeListBrowserList(&g->loglist);
2260
2261 NewList(&g->loglist);
2262
2263 if(g->shared->objects[GID_LOG] != NULL) {
2264 SetGadgetAttrs((struct Gadget *)g->shared->objects[GID_LOG], g->shared->win, NULL,
2265 LISTBROWSER_Labels, &g->loglist,
2266 TAG_DONE);
2267 }
2268}
2269*/
2270
2272{
2273 struct TagItem attrs[2];
2274
2275 if(g->shared->objects[GID_LOG] != NULL) return;
2276
2277 attrs[0].ti_Tag = CHILD_MinHeight;
2278 attrs[0].ti_Data = 50;
2279 attrs[1].ti_Tag = TAG_DONE;
2280 attrs[1].ti_Data = 0;
2281
2283 GA_ID, GID_LOG,
2284 LISTBROWSER_ColumnInfo, g->logcolumns,
2285 LISTBROWSER_ColumnTitles, TRUE,
2286 LISTBROWSER_Labels, &g->loglist,
2288 ListBrowserEnd;
2289
2290#ifdef __amigaos4__
2291 IDoMethod(g->shared->objects[GID_LOGLAYOUT], LM_ADDCHILD,
2292 g->shared->win, g->shared->objects[GID_LOG], NULL);
2293#else
2294 SetAttrs(g->shared->objects[GID_LOGLAYOUT],
2295 LAYOUT_AddChild, g->shared->objects[GID_LOG], TAG_MORE, &attrs);
2296#endif
2297
2298 FlushLayoutDomainCache((struct Gadget *)g->shared->objects[GID_MAIN]);
2299
2300 RethinkLayout((struct Gadget *)g->shared->objects[GID_MAIN],
2301 g->shared->win, NULL, TRUE);
2302
2303 ami_schedule_redraw(g->shared, true);
2304}
2305
2307{
2308 if(g->shared->objects[GID_LOG] == NULL) return;
2309
2310#ifdef __amigaos4__
2311 IDoMethod(g->shared->objects[GID_LOGLAYOUT], LM_REMOVECHILD,
2312 g->shared->win, g->shared->objects[GID_LOG]);
2313#else
2314 SetAttrs(g->shared->objects[GID_LOGLAYOUT],
2315 LAYOUT_RemoveChild, g->shared->objects[GID_LOG], TAG_DONE);
2316#endif
2317
2318 g->shared->objects[GID_LOG] = NULL;
2319
2320 FlushLayoutDomainCache((struct Gadget *)g->shared->objects[GID_MAIN]);
2321
2322 RethinkLayout((struct Gadget *)g->shared->objects[GID_MAIN],
2323 g->shared->win, NULL, TRUE);
2324
2325 ami_schedule_redraw(g->shared, true);
2326}
2327
2329{
2330 if(g->shared->objects[GID_LOG] == NULL) {
2332 return true;
2333 } else {
2335 return false;
2336 }
2337}
2338
2340{
2341 if(g->shared->objects[GID_LOG] == NULL) return;
2342
2343 RefreshSetGadgetAttrs((struct Gadget *)g->shared->objects[GID_LOG], g->shared->win, NULL,
2344 LISTBROWSER_ColumnInfo, g->logcolumns,
2345 LISTBROWSER_Labels, &g->loglist,
2346 TAG_DONE);
2347}
2348
2349static void
2352 const char *msg,
2353 size_t msglen,
2355{
2356 bool foldable = !!(flags & BW_CS_FLAG_FOLDABLE);
2357 const char *src_text;
2358 const char *level_text;
2359 struct Node *node;
2360 ULONG style = 0;
2361 ULONG fgpen = TEXTPEN;
2362 ULONG lbflags = LBFLG_READONLY;
2363 char timestamp[256];
2364 time_t now = time(NULL);
2365 struct tm *timedata = localtime(&now);
2366
2367 strftime(timestamp, 256, "%c", timedata);
2368
2369 if(foldable) lbflags |= LBFLG_HASCHILDREN;
2370
2371 switch (src) {
2372 case BW_CS_INPUT:
2373 src_text = "client-input";
2374 break;
2375 case BW_CS_SCRIPT_ERROR:
2376 src_text = "scripting-error";
2377 break;
2379 src_text = "scripting-console";
2380 break;
2381 default:
2382 assert(0 && "Unknown scripting source");
2383 src_text = "unknown";
2384 break;
2385 }
2386
2387 switch (flags & BW_CS_FLAG_LEVEL_MASK) {
2389 level_text = "DEBUG";
2390 fgpen = DISABLEDTEXTPEN;
2391 lbflags |= LBFLG_CUSTOMPENS;
2392 break;
2394 level_text = "LOG";
2395 fgpen = DISABLEDTEXTPEN;
2396 lbflags |= LBFLG_CUSTOMPENS;
2397 break;
2399 level_text = "INFO";
2400 break;
2402 level_text = "WARN";
2403 break;
2405 level_text = "ERROR";
2406 style = FSF_BOLD;
2407 break;
2408 default:
2409 assert(0 && "Unknown console logging level");
2410 level_text = "unknown";
2411 break;
2412 }
2413
2414 if(g->shared->objects[GID_LOG] != NULL) {
2415 SetGadgetAttrs((struct Gadget *)g->shared->objects[GID_LOG], g->shared->win, NULL,
2416 LISTBROWSER_Labels, NULL,
2417 TAG_DONE);
2418 }
2419
2420 /* Add log entry to list irrespective of whether the log is open. */
2421 if((node = AllocListBrowserNode(4,
2422 LBNA_Flags, lbflags,
2423 LBNA_Column, 0,
2424 LBNCA_SoftStyle, style,
2425 LBNCA_FGPen, fgpen,
2426 LBNCA_CopyText, TRUE,
2427 LBNCA_Text, timestamp,
2428 LBNA_Column, 1,
2429 LBNCA_SoftStyle, style,
2430 LBNCA_FGPen, fgpen,
2431 LBNCA_CopyText, TRUE,
2432 LBNCA_Text, src_text,
2433 LBNA_Column, 2,
2434 LBNCA_SoftStyle, style,
2435 LBNCA_FGPen, fgpen,
2436 LBNCA_CopyText, TRUE,
2437 LBNCA_Text, level_text,
2438 LBNA_Column, 3,
2439 LBNCA_SoftStyle, style,
2440 LBNCA_FGPen, fgpen,
2441 LBNCA_CopyText, TRUE,
2442 LBNCA_Text, msg,
2443 TAG_DONE))) {
2444 AddTail(&g->loglist, node);
2445 }
2446
2447 if(g->shared->objects[GID_LOG] != NULL) {
2448 RefreshSetGadgetAttrs((struct Gadget *)g->shared->objects[GID_LOG], g->shared->win, NULL,
2449 LISTBROWSER_Labels, &g->loglist,
2450 TAG_DONE);
2451 }
2452
2453#ifdef __amigaos4__
2454 DebugPrintF("NETSURF: CONSOLE_LOG SOURCE %s %sFOLDABLE %s %.*s\n",
2455 src_text, foldable ? "" : "NOT-", level_text,
2456 (int)msglen, msg);
2457#endif
2458}
2459
2460
2461/**
2462 * function to add retrieved favicon to gui
2463 */
2464static void gui_window_set_icon(struct gui_window *g, struct hlcache_handle *icon)
2465{
2466 struct BitMap *bm = NULL;
2467 struct IBox *bbox;
2468 struct bitmap *icon_bitmap = NULL;
2469
2470 if(nsoption_bool(kiosk_mode) == true) return;
2471 if(!g) return;
2472
2473 if ((icon != NULL) && ((icon_bitmap = content_get_bitmap(icon)) != NULL))
2474 {
2475 bm = ami_bitmap_get_native(icon_bitmap, 16, 16, ami_plot_screen_is_palettemapped(),
2476 g->shared->win->RPort->BitMap);
2477 }
2478
2479 if(g == g->shared->gw) {
2480 RefreshGList((struct Gadget *)g->shared->objects[GID_ICON],
2481 g->shared->win, NULL, 1);
2482
2483 if(bm)
2484 {
2485 ULONG tag, tag_data, minterm;
2486
2487 if(ami_plot_screen_is_palettemapped() == false) {
2488 tag = BLITA_UseSrcAlpha;
2489 tag_data = !amiga_bitmap_get_opaque(icon_bitmap);
2490 minterm = 0xc0;
2491 } else {
2492 tag = BLITA_MaskPlane;
2493 tag_data = (ULONG)ami_bitmap_get_mask(icon_bitmap, 16, 16, bm);
2494 minterm = MINTERM_SRCMASK;
2495 }
2496
2497 if(ami_gui_get_space_box((Object *)g->shared->objects[GID_ICON], &bbox) != NSERROR_OK) {
2498 amiga_warn_user("NoMemory", "");
2499 return;
2500 }
2501
2502 EraseRect(g->shared->win->RPort, bbox->Left, bbox->Top,
2503 bbox->Left + 16, bbox->Top + 16);
2504
2505#ifdef __amigaos4__
2506 BltBitMapTags(BLITA_SrcX, 0,
2507 BLITA_SrcY, 0,
2508 BLITA_DestX, bbox->Left,
2509 BLITA_DestY, bbox->Top,
2510 BLITA_Width, 16,
2511 BLITA_Height, 16,
2512 BLITA_Source, bm,
2513 BLITA_Dest, g->shared->win->RPort,
2514 BLITA_SrcType, BLITT_BITMAP,
2515 BLITA_DestType, BLITT_RASTPORT,
2516 BLITA_Minterm, minterm,
2517 tag, tag_data,
2518 TAG_DONE);
2519#else
2520 if(tag_data) {
2521 BltMaskBitMapRastPort(bm, 0, 0, g->shared->win->RPort,
2522 bbox->Left, bbox->Top, 16, 16, minterm, tag_data);
2523 } else {
2524 BltBitMapRastPort(bm, 0, 0, g->shared->win->RPort,
2525 bbox->Left, bbox->Top, 16, 16, 0xc0);
2526 }
2527#endif
2529 }
2530 }
2531
2532 g->favicon = icon;
2533}
2534
2535static void ami_gui_refresh_favicon(void *p)
2536{
2537 struct gui_window_2 *gwin = (struct gui_window_2 *)p;
2538 gui_window_set_icon(gwin->gw, gwin->gw->favicon);
2539}
2540
2541/* Gets the size that border gadget 1 (status) needs to be.
2542 * Returns the width of the size gadget as a convenience.
2543 */
2544#ifdef __amigaos4__
2545static ULONG ami_get_border_gadget_size(struct gui_window_2 *gwin,
2546 ULONG *restrict width, ULONG *restrict height)
2547{
2548 static ULONG sz_gad_width = 0;
2549 static ULONG sz_gad_height = 0;
2550 ULONG available_width;
2551
2552 if((sz_gad_width == 0) || (sz_gad_height == 0)) {
2553 struct DrawInfo *dri = GetScreenDrawInfo(scrn);
2554 GetGUIAttrs(NULL, dri,
2555 GUIA_SizeGadgetWidth, &sz_gad_width,
2556 GUIA_SizeGadgetHeight, &sz_gad_height,
2557 TAG_DONE);
2558 FreeScreenDrawInfo(scrn, dri);
2559 }
2560 available_width = gwin->win->Width - scrn->WBorLeft - sz_gad_width;
2561
2562 *width = available_width;
2563 *height = sz_gad_height;
2564
2565 return sz_gad_width;
2566}
2567#endif
2568
2570{
2571#ifdef __amigaos4__
2572 /* Reset gadget widths according to new calculation */
2573 ULONG size1, size2;
2574
2575 ami_get_border_gadget_size(gwin, &size1, &size2);
2576
2577 RefreshSetGadgetAttrs((struct Gadget *)(APTR)gwin->objects[GID_STATUS],
2578 gwin->win, NULL,
2579 GA_Width, size1,
2580 TAG_DONE);
2581
2582 RefreshWindowFrame(gwin->win);
2583#endif
2584}
2585
2586static BOOL ami_handle_msg(void)
2587{
2588 struct ami_generic_window *w = NULL;
2589 struct nsObject *node;
2590 struct nsObject *nnode;
2591 BOOL win_closed = FALSE;
2592
2594 /* no windows in list, so NetSurf should not be running */
2595 ami_try_quit();
2596 return FALSE;
2597 }
2598
2599 node = (struct nsObject *)GetHead((struct List *)window_list);
2600
2601 do {
2602 nnode=(struct nsObject *)GetSucc((struct Node *)node);
2603
2604 w = node->objstruct;
2605 if(w == NULL) continue;
2606
2607 if(w->tbl->event != NULL) {
2608 if((win_closed = w->tbl->event(w))) {
2609 if((node->Type != AMINS_GUIOPTSWINDOW) ||
2610 ((node->Type == AMINS_GUIOPTSWINDOW) && (scrn != NULL))) {
2611 ami_try_quit();
2612 break;
2613 }
2614 } else {
2615 node = nnode;
2616 continue;
2617 }
2618 }
2619 } while((node = nnode));
2620
2621 if(ami_gui_menu_quit_selected() == true) {
2623 }
2624
2625 if(ami_gui_menu_get_check_toggled() == true) {
2627 }
2628
2629 return win_closed;
2630}
2631
2632static BOOL ami_gui_event(void *w)
2633{
2634 struct gui_window_2 *gwin = (struct gui_window_2 *)w;
2635 ULONG result, storage = 0, x, y, xs, ys, width = 800, height = 600;
2636 uint16 code;
2637 struct IBox *bbox;
2638 struct InputEvent *ie;
2639 struct Node *tabnode;
2640 int nskey;
2641 struct timeval curtime;
2642 static int drag_x_move = 0, drag_y_move = 0;
2643 char *utf8 = NULL;
2644 nsurl *url;
2645 BOOL win_closed = FALSE;
2646
2647 while((result = RA_HandleInput(gwin->objects[OID_MAIN], &code)) != WMHI_LASTMSG) {
2648 switch(result & WMHI_CLASSMASK) // class
2649 {
2650 case WMHI_MOUSEMOVE:
2651 ami_gui_trap_mouse(gwin); /* re-assert mouse area */
2652
2653 drag_x_move = 0;
2654 drag_y_move = 0;
2655
2656 if(ami_gui_get_space_box((Object *)gwin->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
2657 amiga_warn_user("NoMemory", "");
2658 break;
2659 }
2660
2661 x = (ULONG)((gwin->win->MouseX - bbox->Left));
2662 y = (ULONG)((gwin->win->MouseY - bbox->Top));
2663
2664 ami_get_hscroll_pos(gwin, (ULONG *)&xs);
2665 ami_get_vscroll_pos(gwin, (ULONG *)&ys);
2666
2667 x += xs;
2668 y += ys;
2669
2670 width=bbox->Width;
2671 height=bbox->Height;
2672
2674 {
2675 if(ami_drag_icon_move() == TRUE) {
2676 if((gwin->win->MouseX < bbox->Left) &&
2677 ((gwin->win->MouseX - bbox->Left) > -AMI_DRAG_THRESHOLD))
2678 drag_x_move = gwin->win->MouseX - bbox->Left;
2679 if((gwin->win->MouseX > (bbox->Left + bbox->Width)) &&
2680 ((gwin->win->MouseX - (bbox->Left + bbox->Width)) < AMI_DRAG_THRESHOLD))
2681 drag_x_move = gwin->win->MouseX - (bbox->Left + bbox->Width);
2682 if((gwin->win->MouseY < bbox->Top) &&
2683 ((gwin->win->MouseY - bbox->Top) > -AMI_DRAG_THRESHOLD))
2684 drag_y_move = gwin->win->MouseY - bbox->Top;
2685 if((gwin->win->MouseY > (bbox->Top + bbox->Height)) &&
2686 ((gwin->win->MouseY - (bbox->Top + bbox->Height)) < AMI_DRAG_THRESHOLD))
2687 drag_y_move = gwin->win->MouseY - (bbox->Top + bbox->Height);
2688 }
2689 }
2690
2692
2693 if((x>=xs) && (y>=ys) && (x<width+xs) && (y<height+ys))
2694 {
2695 ami_update_quals(gwin);
2696
2698 {
2701 }
2702 else if(gwin->mouse_state & BROWSER_MOUSE_PRESS_2)
2703 {
2706 }
2707 else
2708 {
2709 browser_window_mouse_track(gwin->gw->bw,gwin->mouse_state | gwin->key_state,x,y);
2710 }
2711 } else {
2712 if(!gwin->mouse_state) ami_set_pointer(gwin, GUI_POINTER_DEFAULT, true);
2713 }
2714 break;
2715
2716 case WMHI_MOUSEBUTTONS:
2717 if(ami_gui_get_space_box((Object *)gwin->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
2718 amiga_warn_user("NoMemory", "");
2719 return FALSE;
2720 }
2721
2722 x = (ULONG)(gwin->win->MouseX - bbox->Left);
2723 y = (ULONG)(gwin->win->MouseY - bbox->Top);
2724
2725 ami_get_hscroll_pos(gwin, (ULONG *)&xs);
2726 ami_get_vscroll_pos(gwin, (ULONG *)&ys);
2727
2728 x += xs;
2729 y += ys;
2730
2731 width=bbox->Width;
2732 height=bbox->Height;
2733
2735
2736 ami_update_quals(gwin);
2737
2738 if((x>=xs) && (y>=ys) && (x<width+xs) && (y<height+ys))
2739 {
2740 //code = code>>16;
2741 switch(code)
2742 {
2743 case SELECTDOWN:
2746 break;
2747 case MIDDLEDOWN:
2750 break;
2751 }
2752 }
2753
2754 if(x<xs) x=xs;
2755 if(y<ys) y=ys;
2756 if(x>=width+xs) x=width+xs-1;
2757 if(y>=height+ys) y=height+ys-1;
2758
2759 switch(code)
2760 {
2761 case SELECTUP:
2763 {
2764 CurrentTime((ULONG *)&curtime.tv_sec, (ULONG *)&curtime.tv_usec);
2765
2767
2768 if(gwin->lastclick.tv_sec)
2769 {
2770 if(DoubleClick(gwin->lastclick.tv_sec,
2771 gwin->lastclick.tv_usec,
2772 curtime.tv_sec, curtime.tv_usec)) {
2775 } else {
2777 }
2778 }
2779 }
2780
2782 gwin->mouse_state | gwin->key_state,x,y);
2783
2785 {
2786 gwin->lastclick.tv_sec = 0;
2787 gwin->lastclick.tv_usec = 0;
2788 }
2789 else
2790 {
2791 gwin->lastclick.tv_sec = curtime.tv_sec;
2792 gwin->lastclick.tv_usec = curtime.tv_usec;
2793 }
2794 }
2795 else
2796 {
2797 browser_window_mouse_track(gwin->gw->bw, 0, x, y);
2798 }
2799 gwin->prev_mouse_state = gwin->mouse_state;
2800 gwin->mouse_state=0;
2801 break;
2802
2803 case MIDDLEUP:
2805 {
2806 CurrentTime((ULONG *)&curtime.tv_sec, (ULONG *)&curtime.tv_usec);
2807
2809
2810 if(gwin->lastclick.tv_sec)
2811 {
2812 if(DoubleClick(gwin->lastclick.tv_sec,
2813 gwin->lastclick.tv_usec,
2814 curtime.tv_sec, curtime.tv_usec)) {
2817 } else {
2819 }
2820 }
2821 }
2822
2824 gwin->mouse_state | gwin->key_state,x,y);
2825
2827 {
2828 gwin->lastclick.tv_sec = 0;
2829 gwin->lastclick.tv_usec = 0;
2830 }
2831 else
2832 {
2833 gwin->lastclick.tv_sec = curtime.tv_sec;
2834 gwin->lastclick.tv_usec = curtime.tv_usec;
2835 }
2836 }
2837 else
2838 {
2839 browser_window_mouse_track(gwin->gw->bw, 0, x, y);
2840 }
2841 gwin->prev_mouse_state = gwin->mouse_state;
2842 gwin->mouse_state=0;
2843 break;
2844#ifdef __amigaos4__
2845 case SIDEUP:
2846 ami_gui_history(gwin, true);
2847 break;
2848
2849 case EXTRAUP:
2850 ami_gui_history(gwin, false);
2851 break;
2852#endif
2853 }
2854
2855 if(ami_drag_has_data() && !gwin->mouse_state)
2856 ami_drag_save(gwin->win);
2857 break;
2858
2859 case WMHI_GADGETUP:
2860 switch(result & WMHI_GADGETMASK)
2861 {
2862 case GID_TABS:
2863 if(gwin->objects[GID_TABS] == NULL) break;
2864 if(ClickTabBase->lib_Version >= 53) {
2865 GetAttrs(gwin->objects[GID_TABS],
2866 CLICKTAB_NodeClosed, &tabnode, TAG_DONE);
2867 } else {
2868 tabnode = NULL;
2869 }
2870
2871 if(tabnode) {
2872 struct gui_window *closedgw;
2873
2874 GetClickTabNodeAttrs(tabnode,
2875 TNA_UserData, &closedgw,
2876 TAG_DONE);
2877
2878 browser_window_destroy(closedgw->bw);
2879 } else {
2880 ami_switch_tab(gwin, true);
2881 }
2882 break;
2883
2884 case GID_CLOSETAB:
2886 break;
2887
2888 case GID_ADDTAB:
2890 break;
2891
2892 case GID_URL:
2893 {
2894 nserror ret;
2895 nsurl *url;
2896 GetAttr(STRINGA_TextVal,
2897 (Object *)gwin->objects[GID_URL],
2898 (ULONG *)&storage);
2899 utf8 = ami_to_utf8_easy((const char *)storage);
2900
2902 ami_utf8_free(utf8);
2903 if (ret == NSERROR_OK) {
2905 url,
2906 NULL,
2908 NULL,
2909 NULL,
2910 NULL);
2912 }
2913 if (ret != NSERROR_OK) {
2915 }
2916 }
2917 break;
2918
2919 case GID_TOOLBARLAYOUT:
2920 /* Need fixing: never gets here */
2921 break;
2922
2923 case GID_SEARCH_ICON:
2924#ifdef __amigaos4__
2925 {
2926 char *prov = NULL;
2927 GetAttr(CHOOSER_SelectedNode, gwin->objects[GID_SEARCH_ICON],(ULONG *)&storage);
2928 if(storage != NULL) {
2929 GetChooserNodeAttrs((struct Node *)storage, CNA_Text, (ULONG *)&prov, TAG_DONE);
2930 nsoption_set_charp(search_web_provider, (char *)strdup(prov));
2931 }
2932 }
2933#else
2934 /* TODO: Fix for OS<3.2 */
2935#endif
2936 search_web_select_provider(nsoption_charp(search_web_provider));
2937 break;
2938
2939 case GID_SEARCHSTRING:
2940 {
2941 nserror ret;
2942 nsurl *url;
2943
2944 GetAttr(STRINGA_TextVal,
2945 (Object *)gwin->objects[GID_SEARCHSTRING],
2946 (ULONG *)&storage);
2947
2948 utf8 = ami_to_utf8_easy((const char *)storage);
2949
2951 ami_utf8_free(utf8);
2952 if (ret == NSERROR_OK) {
2954 url,
2955 NULL,
2957 NULL,
2958 NULL,
2959 NULL);
2961 }
2962 if (ret != NSERROR_OK) {
2964 }
2965
2966 }
2967 break;
2968
2969 case GID_HOME:
2970 {
2971 if (nsurl_create(nsoption_charp(homepage_url), &url) != NSERROR_OK) {
2972 amiga_warn_user("NoMemory", 0);
2973 } else {
2975 url,
2976 NULL,
2978 NULL,
2979 NULL,
2980 NULL);
2982 }
2983 }
2984 break;
2985
2986 case GID_STOP:
2988 browser_window_stop(gwin->gw->bw);
2989 break;
2990
2991 case GID_RELOAD:
2992 ami_update_quals(gwin);
2993
2995 {
2996 if(gwin->key_state & BROWSER_MOUSE_MOD_1)
2997 {
2998 browser_window_reload(gwin->gw->bw, true);
2999 }
3000 else
3001 {
3002 browser_window_reload(gwin->gw->bw, false);
3003 }
3004 }
3005 break;
3006
3007 case GID_BACK:
3008 ami_gui_history(gwin, true);
3009 break;
3010
3011 case GID_FORWARD:
3012 ami_gui_history(gwin, false);
3013 break;
3014
3015 case GID_PAGEINFO:
3016 {
3017 ULONG w_top, w_left;
3018 ULONG g_top, g_left, g_height;
3019
3020 GetAttr(WA_Top, gwin->objects[OID_MAIN], &w_top);
3021 GetAttr(WA_Left, gwin->objects[OID_MAIN], &w_left);
3022 GetAttr(GA_Top, gwin->objects[GID_PAGEINFO], &g_top);
3023 GetAttr(GA_Left, gwin->objects[GID_PAGEINFO], &g_left);
3024 GetAttr(GA_Height, gwin->objects[GID_PAGEINFO], &g_height);
3025
3026 if(ami_pageinfo_open(gwin->gw->bw,
3027 w_left + g_left,
3028 w_top + g_top + g_height) != NSERROR_OK) {
3029 NSLOG(netsurf, INFO, "Unable to open page info window");
3030 }
3031 }
3032 break;
3033
3034 case GID_FAVE:
3035 GetAttr(STRINGA_TextVal,
3036 (Object *)gwin->objects[GID_URL],
3037 (ULONG *)&storage);
3038 if(nsurl_create((const char *)storage, &url) == NSERROR_OK) {
3039 if(hotlist_has_url(url)) {
3041 } else {
3043 }
3045 }
3047 break;
3048
3049 case GID_HOTLIST:
3050 default:
3051// printf("GADGET: %ld\n",(result & WMHI_GADGETMASK));
3052 break;
3053 }
3054 break;
3055
3056 case WMHI_RAWKEY:
3057 ami_update_quals(gwin);
3058
3059 storage = result & WMHI_GADGETMASK;
3060 if(storage >= IECODE_UP_PREFIX) break;
3061
3062 GetAttr(WINDOW_InputEvent,gwin->objects[OID_MAIN],(ULONG *)&ie);
3063
3064 nskey = ami_key_to_nskey(storage, ie);
3065
3066 if((ie->ie_Qualifier & IEQUALIFIER_RCOMMAND) &&
3067 ((31 < nskey) && (nskey < 127))) {
3068 /* NB: Some keypresses are converted to generic keypresses above
3069 * rather than being "menu-emulated" here. */
3070 switch(nskey)
3071 {
3072 /* The following aren't available from the menu at the moment */
3073
3074 case 'r': // reload
3076 browser_window_reload(gwin->gw->bw, false);
3077 break;
3078
3079 case 'u': // open url
3080 if((nsoption_bool(kiosk_mode) == false))
3081 ActivateLayoutGadget((struct Gadget *)gwin->objects[GID_MAIN],
3082 gwin->win, NULL, (uint32)gwin->objects[GID_URL]);
3083 break;
3084 }
3085 }
3086 else
3087 {
3088 if(!browser_window_key_press(gwin->gw->bw, nskey))
3089 {
3090 switch(nskey)
3091 {
3092 case NS_KEY_UP:
3094 break;
3095
3096 case NS_KEY_DOWN:
3098 break;
3099
3100 case NS_KEY_LEFT:
3102 break;
3103
3104 case NS_KEY_RIGHT:
3106 break;
3107
3108 case NS_KEY_PAGE_UP:
3110 break;
3111
3112 case NS_KEY_PAGE_DOWN:
3113 case ' ':
3115 break;
3116
3117 case NS_KEY_LINE_START: // page left
3119 break;
3120
3121 case NS_KEY_LINE_END: // page right
3123 break;
3124
3125 case NS_KEY_TEXT_START: // home
3127 break;
3128
3129 case NS_KEY_TEXT_END: // end
3131 break;
3132
3133 case NS_KEY_WORD_RIGHT: // alt+right
3134 ami_change_tab(gwin, 1);
3135 break;
3136
3137 case NS_KEY_WORD_LEFT: // alt+left
3138 ami_change_tab(gwin, -1);
3139 break;
3140
3141 case NS_KEY_DELETE_LEFT: // backspace
3142 ami_gui_history(gwin, true);
3143 break;
3144
3145 /* RawKeys. NB: These are passthrus in ami_key_to_nskey() */
3146 case RAWKEY_F5: // reload
3148 browser_window_reload(gwin->gw->bw,false);
3149 break;
3150
3151 case RAWKEY_F8: // scale 100%
3152 ami_gui_set_scale(gwin->gw, 1.0);
3153 break;
3154
3155 case RAWKEY_F9: // decrease scale
3156 ami_gui_adjust_scale(gwin->gw, -0.1);
3157 break;
3158
3159 case RAWKEY_F10: // increase scale
3160 ami_gui_adjust_scale(gwin->gw, +0.1);
3161 break;
3162
3163 case RAWKEY_F12: // console log
3165 break;
3166
3167 case RAWKEY_HELP: // help
3169 break;
3170 }
3171 } else if(nskey == NS_KEY_COPY_SELECTION) {
3172 /* if we've copied a selection we need to clear it - style guide rules */
3174 }
3175 }
3176 break;
3177
3178 case WMHI_NEWSIZE:
3183 break;
3184
3185 case WMHI_CLOSEWINDOW:
3187 win_closed = TRUE;
3188 break;
3189#ifdef __amigaos4__
3190 case WMHI_ICONIFY:
3191 {
3192 struct bitmap *bm = NULL;
3194 &bm);
3195 gwin->dobj = amiga_icon_from_bitmap(bm);
3197 gwin->dobj);
3198 HideWindow(gwin->win);
3199 if(strlen(gwin->wintitle) > 23) {
3200 strncpy(gwin->icontitle, gwin->wintitle, 20);
3201 gwin->icontitle[20] = '.';
3202 gwin->icontitle[21] = '.';
3203 gwin->icontitle[22] = '.';
3204 gwin->icontitle[23] = '\0';
3205 } else {
3206 strlcpy(gwin->icontitle, gwin->wintitle, 23);
3207 }
3208 gwin->appicon = AddAppIcon((ULONG)gwin->objects[OID_MAIN],
3209 (ULONG)gwin, gwin->icontitle, appport,
3210 0, gwin->dobj, NULL);
3211
3212 cur_gw = NULL;
3213 }
3214 break;
3215#endif
3216 case WMHI_INACTIVE:
3217 gwin->gw->c_h_temp = gwin->gw->c_h;
3219 break;
3220
3221 case WMHI_ACTIVE:
3222 if(gwin->gw->bw) cur_gw = gwin->gw;
3223 if(gwin->gw->c_h_temp)
3224 gwin->gw->c_h = gwin->gw->c_h_temp;
3225 break;
3226
3227 case WMHI_INTUITICK:
3228 break;
3229
3230 default:
3231 //printf("class: %ld\n",(result & WMHI_CLASSMASK));
3232 break;
3233 }
3234
3235 if(win_destroyed)
3236 {
3237 /* we can't be sure what state our window_list is in, so let's
3238 jump out of the function and start again */
3239
3240 win_destroyed = false;
3241 return TRUE;
3242 }
3243
3244 if(drag_x_move || drag_y_move)
3245 {
3246 struct rect rect;
3247
3249 &gwin->gw->scrollx, &gwin->gw->scrolly);
3250
3251 rect.x0 = rect.x1 = gwin->gw->scrollx + drag_x_move;
3252 rect.y0 = rect.y1 = gwin->gw->scrolly + drag_y_move;
3253
3254 gui_window_set_scroll(gwin->gw, &rect);
3255 }
3256
3257// ReplyMsg((struct Message *)message);
3258 }
3259
3260 if(gwin->closed == true) {
3261 win_closed = TRUE;
3263 }
3264
3265 return win_closed;
3266}
3267
3268static void ami_gui_appicon_remove(struct gui_window_2 *gwin)
3269{
3270 if(gwin->appicon)
3271 {
3272 RemoveAppIcon(gwin->appicon);
3273 amiga_icon_free(gwin->dobj);
3274 gwin->appicon = NULL;
3275 }
3276}
3277
3279{
3280 int bm_idx;
3284
3285 /* if this isn't the visible tab, don't do anything */
3286 if((gwin == NULL) || (gwin->gw != gw)) return NSERROR_OK;
3287
3289
3290 switch(pistate) {
3292 bm_idx = GID_PAGEINFO_INTERNAL_BM;
3293 break;
3294
3295 case PAGE_STATE_LOCAL:
3296 bm_idx = GID_PAGEINFO_LOCAL_BM;
3297 break;
3298
3300 bm_idx = GID_PAGEINFO_INSECURE_BM;
3301 break;
3302
3304 bm_idx = GID_PAGEINFO_WARNING_BM;
3305 break;
3306
3308 bm_idx = GID_PAGEINFO_WARNING_BM;
3309 break;
3310
3311 case PAGE_STATE_SECURE:
3312 bm_idx = GID_PAGEINFO_SECURE_BM;
3313 break;
3314
3315 default:
3316 bm_idx = GID_PAGEINFO_INTERNAL_BM;
3317 break;
3318 }
3319
3320 RefreshSetGadgetAttrs((struct Gadget *)gwin->objects[GID_PAGEINFO], gwin->win, NULL,
3321 BUTTON_RenderImage, gwin->objects[bm_idx],
3322 GA_HintInfo, gwin->helphints[bm_idx],
3323 TAG_DONE);
3324
3325 return NSERROR_OK;
3326}
3327
3328static void ami_handle_appmsg(void)
3329{
3330 struct AppMessage *appmsg;
3331 struct gui_window_2 *gwin;
3332 int x, y;
3333 struct WBArg *appwinargs;
3334 STRPTR filename;
3335 int i = 0;
3336
3337 while((appmsg = (struct AppMessage *)GetMsg(appport)))
3338 {
3339 gwin = (struct gui_window_2 *)appmsg->am_UserData;
3340
3341 if(appmsg->am_Type == AMTYPE_APPICON)
3342 {
3344 ShowWindow(gwin->win, WINDOW_FRONTMOST);
3345 ActivateWindow(gwin->win);
3346 }
3347 else if(appmsg->am_Type == AMTYPE_APPWINDOW)
3348 {
3349 for(i = 0; i < appmsg->am_NumArgs; ++i)
3350 {
3351 if((appwinargs = &appmsg->am_ArgList[i]))
3352 {
3353 if((filename = malloc(1024)))
3354 {
3355 if(appwinargs->wa_Lock)
3356 {
3357 NameFromLock(appwinargs->wa_Lock, filename, 1024);
3358 }
3359
3360 AddPart(filename, appwinargs->wa_Name, 1024);
3361
3362 if(ami_mouse_to_ns_coords(gwin, &x, &y,
3363 appmsg->am_MouseX, appmsg->am_MouseY) == false)
3364 {
3365 nsurl *url;
3366
3367 if (netsurf_path_to_nsurl(filename, &url) != NSERROR_OK) {
3368 amiga_warn_user("NoMemory", 0);
3369 }
3370 else
3371 {
3372 if(i == 0)
3373 {
3375 url,
3376 NULL,
3378 NULL,
3379 NULL,
3380 NULL);
3381
3382 ActivateWindow(gwin->win);
3383 }
3384 else
3385 {
3388 url,
3389 NULL,
3390 gwin->gw->bw,
3391 NULL);
3392 }
3393 nsurl_unref(url);
3394 }
3395 }
3396 else
3397 {
3398 if(browser_window_drop_file_at_point(gwin->gw->bw, x, y, filename) == false)
3399 {
3400 nsurl *url;
3401
3402 if (netsurf_path_to_nsurl(filename, &url) != NSERROR_OK) {
3403 amiga_warn_user("NoMemory", 0);
3404 }
3405 else
3406 {
3407
3408 if(i == 0)
3409 {
3411 url,
3412 NULL,
3414 NULL,
3415 NULL,
3416 NULL);
3417
3418 ActivateWindow(gwin->win);
3419 }
3420 else
3421 {
3424 url,
3425 NULL,
3426 gwin->gw->bw,
3427 NULL);
3428
3429 }
3430 nsurl_unref(url);
3431 }
3432 }
3433 }
3434 free(filename);
3435 }
3436 }
3437 }
3438 }
3439 ReplyMsg((struct Message *)appmsg);
3440 }
3441}
3442
3443static void ami_handle_applib(void)
3444{
3445#ifdef __amigaos4__
3446 struct ApplicationMsg *applibmsg;
3447 struct browser_window *bw;
3448 nsurl *url;
3449 nserror error;
3450
3451 if(!applibport) return;
3452
3453 while((applibmsg=(struct ApplicationMsg *)GetMsg(applibport)))
3454 {
3455 switch (applibmsg->type)
3456 {
3457 case APPLIBMT_NewBlankDoc:
3458 {
3459
3460 error = nsurl_create(nsoption_charp(homepage_url), &url);
3461 if (error == NSERROR_OK) {
3463 url,
3464 NULL,
3465 NULL,
3466 &bw);
3467 nsurl_unref(url);
3468 }
3469 if (error != NSERROR_OK) {
3471 }
3472 }
3473 break;
3474
3475 case APPLIBMT_OpenDoc:
3476 {
3477 struct ApplicationOpenPrintDocMsg *applibopdmsg =
3478 (struct ApplicationOpenPrintDocMsg *)applibmsg;
3479
3480 error = netsurf_path_to_nsurl(applibopdmsg->fileName, &url);
3481 if (error == NSERROR_OK) {
3483 url,
3484 NULL,
3485 NULL,
3486 &bw);
3487 nsurl_unref(url);
3488 }
3489 if (error != NSERROR_OK) {
3491 }
3492 }
3493 break;
3494
3495 case APPLIBMT_ToFront:
3496 if(cur_gw)
3497 {
3498 ScreenToFront(scrn);
3499 WindowToFront(cur_gw->shared->win);
3500 ActivateWindow(cur_gw->shared->win);
3501 }
3502 break;
3503
3504 case APPLIBMT_OpenPrefs:
3505 ScreenToFront(scrn);
3507 break;
3508
3509 case APPLIBMT_Quit:
3510 case APPLIBMT_ForceQuit:
3512 break;
3513
3514 case APPLIBMT_CustomMsg:
3515 {
3516 struct ApplicationCustomMsg *applibcustmsg =
3517 (struct ApplicationCustomMsg *)applibmsg;
3518 NSLOG(netsurf, INFO,
3519 "Ringhio BackMsg received: %s",
3520 applibcustmsg->customMsg);
3521
3522 ami_download_parse_backmsg(applibcustmsg->customMsg);
3523 }
3524 break;
3525 }
3526 ReplyMsg((struct Message *)applibmsg);
3527 }
3528#endif
3529}
3530
3531void ami_get_msg(void)
3532{
3533 ULONG winsignal = 1L << sport->mp_SigBit;
3534 ULONG appsig = 1L << appport->mp_SigBit;
3535 ULONG schedulesig = 1L << schedulermsgport->mp_SigBit;
3536 ULONG ctrlcsig = SIGBREAKF_CTRL_C;
3537 uint32 signal = 0;
3538 fd_set read_fd_set, write_fd_set, except_fd_set;
3539 int max_fd = -1;
3540 struct MsgPort *printmsgport = ami_print_get_msgport();
3541 ULONG printsig = 0;
3542 ULONG helpsignal = ami_help_signal();
3543 if(printmsgport) printsig = 1L << printmsgport->mp_SigBit;
3544 uint32 signalmask = winsignal | appsig | schedulesig | rxsig |
3545 printsig | applibsig | helpsignal;
3546
3547 if ((fetch_fdset(&read_fd_set, &write_fd_set, &except_fd_set, &max_fd) == NSERROR_OK) &&
3548 (max_fd != -1)) {
3549 /* max_fd is the highest fd in use, but waitselect() needs to know how many
3550 * are in use, so we add 1. */
3551
3552 if (waitselect(max_fd + 1, &read_fd_set, &write_fd_set, &except_fd_set,
3553 NULL, (unsigned int *)&signalmask) != -1) {
3554 signal = signalmask;
3555 } else {
3556 NSLOG(netsurf, INFO, "waitselect() returned error");
3557 /* \todo Fix Ctrl-C handling.
3558 * WaitSelect() from bsdsocket.library returns -1 if the task was
3559 * signalled with a Ctrl-C. waitselect() from newlib.library does not.
3560 * Adding the Ctrl-C signal to our user signal mask causes a Ctrl-C to
3561 * occur sporadically. Otherwise we never get a -1 except on error.
3562 * NetSurf still terminates at the Wait() when network activity is over.
3563 */
3564 }
3565 } else {
3566 /* If fetcher_fdset fails or no network activity, do it the old fashioned way. */
3567 signalmask |= ctrlcsig;
3568 signal = Wait(signalmask);
3569 }
3570
3571 if(signal & winsignal)
3572 while(ami_handle_msg());
3573
3574 if(signal & appsig)
3576
3577 if(signal & rxsig)
3579
3580 if(signal & applibsig)
3582
3583 if(signal & printsig) {
3584 while(GetMsg(printmsgport)); //ReplyMsg
3586 }
3587
3588 if(signal & schedulesig) {
3590 }
3591
3592 if(signal & helpsignal)
3594
3595 if(signal & ctrlcsig)
3597}
3598
3599static void ami_change_tab(struct gui_window_2 *gwin, int direction)
3600{
3601 struct Node *tab_node = gwin->gw->tab_node;
3602 struct Node *ptab = NULL;
3603
3604 if(gwin->tabs <= 1) return;
3605
3606 if(direction > 0) {
3607 ptab = GetSucc(tab_node);
3608 } else {
3609 ptab = GetPred(tab_node);
3610 }
3611
3612 if(!ptab) return;
3613
3614 RefreshSetGadgetAttrs((struct Gadget *)gwin->objects[GID_TABS], gwin->win, NULL,
3615 CLICKTAB_CurrentNode, ptab,
3616 TAG_DONE);
3617
3618 ami_switch_tab(gwin, true);
3619}
3620
3621
3622static void gui_window_set_title(struct gui_window *g, const char *restrict title)
3623{
3624 struct Node *node;
3625 char *restrict utf8title;
3626
3627 if(!g) return;
3628 if(!title) return;
3629
3630 utf8title = ami_utf8_easy((char *)title);
3631
3632 if(g->tab_node) {
3633 node = g->tab_node;
3634
3635 if((g->tabtitle == NULL) || (strcmp(utf8title, g->tabtitle)))
3636 {
3637 SetGadgetAttrs((struct Gadget *)g->shared->objects[GID_TABS],
3638 g->shared->win, NULL,
3639 CLICKTAB_Labels, ~0,
3640 TAG_DONE);
3641
3642 if(g->tabtitle) free(g->tabtitle);
3643 g->tabtitle = strdup(utf8title);
3644
3645 SetClickTabNodeAttrs(node, TNA_Text, g->tabtitle,
3647 TAG_DONE);
3648
3649 RefreshSetGadgetAttrs((struct Gadget *)g->shared->objects[GID_TABS],
3650 g->shared->win, NULL,
3651 CLICKTAB_Labels, &g->shared->tab_list,
3652 TAG_DONE);
3653
3654 if(ClickTabBase->lib_Version < 53)
3655 RethinkLayout((struct Gadget *)g->shared->objects[GID_TABLAYOUT],
3656 g->shared->win, NULL, TRUE);
3657 }
3658 }
3659
3660 if(g == g->shared->gw) {
3661 if((g->shared->wintitle == NULL) || (strcmp(utf8title, g->shared->wintitle)))
3662 {
3663 if(g->shared->wintitle) free(g->shared->wintitle);
3664 g->shared->wintitle = strdup(utf8title);
3665 SetWindowTitles(g->shared->win, g->shared->wintitle, ami_gui_get_screen_title());
3666 }
3667 }
3668
3669 ami_utf8_free(utf8title);
3670}
3671
3673{
3674 struct IBox *bbox;
3675
3676 if(!g || !g->bw) return;
3677 if(browser_window_has_content(g->bw) == false) return;
3678
3679 if(g == g->shared->gw) {
3680 int width, height;
3681 if(ami_gui_get_space_box((Object *)g->shared->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
3682 amiga_warn_user("NoMemory", "");
3683 return;
3684 }
3685
3686 if(g->shared->objects[GID_VSCROLL]) {
3688 RefreshSetGadgetAttrs((struct Gadget *)(APTR)g->shared->objects[GID_VSCROLL],g->shared->win,NULL,
3689 SCROLLER_Total, (ULONG)(height),
3690 SCROLLER_Visible, bbox->Height,
3691 TAG_DONE);
3692 }
3693
3694 if(g->shared->objects[GID_HSCROLL])
3695 {
3697 RefreshSetGadgetAttrs((struct Gadget *)(APTR)g->shared->objects[GID_HSCROLL],
3698 g->shared->win, NULL,
3699 SCROLLER_Total, (ULONG)(width),
3700 SCROLLER_Visible, bbox->Width,
3701 TAG_DONE);
3702 }
3703
3705 }
3706
3708 g->shared->new_content = true;
3709}
3710
3711
3712/**
3713 * Invalidates an area of an amiga browser window
3714 *
3715 * \param g gui_window
3716 * \param rect area to redraw or NULL for the entire window area
3717 * \return NSERROR_OK on success or appropriate error code
3718 */
3720 const struct rect *restrict rect)
3721{
3722 struct nsObject *nsobj;
3723 struct rect *restrict deferred_rect;
3724
3725 if(!g) return NSERROR_BAD_PARAMETER;
3726
3727 if (rect == NULL) {
3728 if (g != g->shared->gw) {
3729 return NSERROR_OK;
3730 }
3731 } else {
3733 g->deferred_rects_pool)) {
3735 sizeof(struct rect));
3736 CopyMem(rect, deferred_rect, sizeof(struct rect));
3737 nsobj = AddObject(g->deferred_rects, AMINS_RECT);
3738 nsobj->objstruct = deferred_rect;
3739 } else {
3740 NSLOG(netsurf, INFO,
3741 "Ignoring duplicate or subset of queued box redraw");
3742 }
3743 }
3744 ami_schedule_redraw(g->shared, false);
3745
3746 return NSERROR_OK;
3747}
3748
3749
3750static void ami_switch_tab(struct gui_window_2 *gwin, bool redraw)
3751{
3752 struct Node *tabnode;
3753 struct IBox *bbox;
3754
3755 /* Clear the last new tab list */
3756 gwin->last_new_tab = NULL;
3757
3758 if(gwin->tabs == 0) return;
3759
3761 &gwin->gw->scrollx, &gwin->gw->scrolly);
3762
3763 GetAttr(CLICKTAB_CurrentNode, (Object *)gwin->objects[GID_TABS],
3764 (ULONG *)&tabnode);
3765 GetClickTabNodeAttrs(tabnode,
3766 TNA_UserData, &gwin->gw,
3767 TAG_DONE);
3768 cur_gw = gwin->gw;
3769
3771
3772 if(ami_gui_get_space_box((Object *)gwin->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
3773 amiga_warn_user("NoMemory", "");
3774 return;
3775 }
3776
3777 if((gwin->gw->bw == NULL) || (browser_window_has_content(gwin->gw->bw)) == false) {
3778 RefreshSetGadgetAttrs((struct Gadget *)gwin->objects[GID_URL],
3779 gwin->win, NULL, STRINGA_TextVal, "", TAG_DONE);
3780
3781 ami_plot_clear_bbox(gwin->win->RPort, bbox);
3783 return;
3784 }
3785
3787 ami_update_buttons(gwin);
3789
3790 if(redraw)
3791 {
3792 struct rect rect;
3793
3794 ami_plot_clear_bbox(gwin->win->RPort, bbox);
3798 amiga_window_invalidate_area(gwin->gw, NULL);
3799
3800 rect.x0 = rect.x1 = gwin->gw->scrollx;
3801 rect.y0 = rect.y1 = gwin->gw->scrolly;
3802
3803 gui_window_set_scroll(gwin->gw, &rect);
3804 gwin->redraw_scroll = false;
3805
3810
3811 gui_window_set_icon(gwin->gw, gwin->gw->favicon);
3812 gui_page_info_change(gwin->gw);
3813 }
3814
3816}
3817
3819{
3820 struct nsObject *node;
3821 struct nsObject *nnode;
3822 struct ami_generic_window *w;
3823
3824 /* Disable the multiple tabs open warning */
3825 nsoption_set_bool(tab_close_warn, false);
3826
3828 node = (struct nsObject *)GetHead((struct List *)window_list);
3829
3830 do {
3831 nnode=(struct nsObject *)GetSucc((struct Node *)node);
3832 w = node->objstruct;
3833
3834 if(w->tbl->close != NULL) {
3835 if(node->Type == AMINS_WINDOW) {
3836 struct gui_window_2 *gwin = (struct gui_window_2 *)w;
3837 ShowWindow(gwin->win, WINDOW_BACKMOST); // do we need this??
3838 }
3839 w->tbl->close(w);
3840 }
3841 } while((node = nnode));
3842
3843 win_destroyed = true;
3844 }
3845
3847 /* last window closed, so exit */
3848 ami_quit = true;
3849 }
3850}
3851
3853{
3854 int res = -1;
3855#ifdef __amigaos4__
3856 char *utf8text = ami_utf8_easy(messages_get("TCPIPShutdown"));
3857 char *utf8gadgets = ami_utf8_easy(messages_get("AbortShutdown"));
3858
3859 DisplayBeep(NULL);
3860
3861 res = TimedDosRequesterTags(TDR_ImageType, TDRIMAGE_INFO,
3862 TDR_TitleString, messages_get("NetSurf"),
3863 TDR_FormatString, utf8text,
3864 TDR_GadgetString, utf8gadgets,
3865 TDR_Timeout, 5,
3866 TDR_Inactive, TRUE,
3867 TAG_DONE);
3868
3869 free(utf8text);
3870 free(utf8gadgets);
3871#endif
3872 if(res == -1) { /* Requester timed out */
3874 }
3875}
3876
3877static void ami_gui_close_screen(struct Screen *scrn, BOOL locked_screen, BOOL donotwait)
3878{
3879 if(scrn == NULL) return;
3880
3881 if(locked_screen) {
3882 UnlockPubScreen(NULL,scrn);
3883 locked_screen = FALSE;
3884 }
3885
3886 /* If this is our own screen, wait for visitor windows to close */
3887 if(screen_signal == -1) return;
3888
3889 if(CloseScreen(scrn) == TRUE) {
3890 if(screen_signal != -1) {
3891 FreeSignal(screen_signal);
3892 screen_signal = -1;
3893 scrn = NULL;
3894 }
3895 return;
3896 }
3897 if(donotwait == TRUE) return;
3898
3899 ULONG scrnsig = 1 << screen_signal;
3900 NSLOG(netsurf, INFO,
3901 "Waiting for visitor windows to close... (signal)");
3902 Wait(scrnsig);
3903
3904 while (CloseScreen(scrn) == FALSE) {
3905 NSLOG(netsurf, INFO,
3906 "Waiting for visitor windows to close... (polling)");
3907 Delay(50);
3908 }
3909
3910 FreeSignal(screen_signal);
3911 screen_signal = -1;
3912 scrn = NULL;
3913}
3914
3916{
3917 if(!IsMinListEmpty(window_list)) return;
3918
3919 if(nsoption_bool(close_no_quit) == false)
3920 {
3921 ami_quit = true;
3922 return;
3923 }
3924 else
3925 {
3927 }
3928}
3929
3930static void gui_quit(void)
3931{
3933
3934 urldb_save(nsoption_charp(url_file));
3935 urldb_save_cookies(nsoption_charp(cookie_file));
3936 hotlist_fini();
3937#ifdef __amigaos4__
3938 if(IApplication && ami_appid)
3939 UnregisterApplication(ami_appid, NULL);
3940#endif
3942
3944
3945 ami_font_fini();
3946 ami_help_free();
3947
3948 NSLOG(netsurf, INFO, "Freeing menu items");
3951
3952 NSLOG(netsurf, INFO, "Freeing mouse pointers");
3954
3957#ifdef __amigaos4__
3958 FreeStringClass(urlStringClass);
3959#endif
3960
3962
3965
3966 NSLOG(netsurf, INFO, "Closing screen");
3968 if(nsscreentitle) FreeVec(nsscreentitle);
3969}
3970
3971char *ami_gui_get_cache_favicon_name(nsurl *url, bool only_if_avail)
3972{
3973 STRPTR filename = NULL;
3974
3975 if ((filename = ASPrintf("%s/%x", current_user_faviconcache, nsurl_hash(url)))) {
3976 NSLOG(netsurf, INFO, "favicon cache location: %s", filename);
3977
3978 if (only_if_avail == true) {
3979 BPTR lock = 0;
3980 if((lock = Lock(filename, ACCESS_READ))) {
3981 UnLock(lock);
3982 return filename;
3983 }
3984 } else {
3985 return filename;
3986 }
3987 }
3988 return NULL;
3989}
3990
3991static void ami_gui_cache_favicon(nsurl *url, struct bitmap *favicon)
3992{
3993 STRPTR filename = NULL;
3994
3995 if ((filename = ami_gui_get_cache_favicon_name(url, false))) {
3996 if(favicon) amiga_bitmap_save(favicon, filename, AMI_BITMAP_SCALE_ICON);
3997 FreeVec(filename);
3998 }
3999}
4000
4002{
4003 char *url;
4004 nsurl *nsurl;
4005
4006 GetAttr(STRINGA_TextVal,
4007 (Object *)gwin->objects[GID_URL],
4008 (ULONG *)&url);
4009
4010 if(nsurl_create(url, &nsurl) == NSERROR_OK) {
4011 if(hotlist_has_url(nsurl)) {
4012 RefreshSetGadgetAttrs((struct Gadget *)gwin->objects[GID_FAVE], gwin->win, NULL,
4013 BUTTON_RenderImage, gwin->objects[GID_FAVE_RMV], TAG_DONE);
4014
4015 if (gwin->gw->favicon)
4017 } else {
4018 RefreshSetGadgetAttrs((struct Gadget *)gwin->objects[GID_FAVE], gwin->win, NULL,
4019 BUTTON_RenderImage, gwin->objects[GID_FAVE_ADD], TAG_DONE);
4020 }
4021
4023 }
4024}
4025
4026static bool ami_gui_hotlist_add(void *userdata, int level, int item,
4027 const char *title, nsurl *url, bool is_folder)
4028{
4029 struct ami_gui_tb_userdata *tb_userdata = (struct ami_gui_tb_userdata *)userdata;
4030 struct Node *speed_button_node;
4031 char menu_icon[1024];
4032 char *utf8title = NULL;
4033
4034 if(level != 1) return false;
4035 if(item > AMI_GUI_TOOLBAR_MAX) return false;
4036 if(is_folder == true) return false;
4037
4038 if(utf8_to_local_encoding(title,
4039 (strlen(title) < NSA_MAX_HOTLIST_BUTTON_LEN) ? strlen(title) : NSA_MAX_HOTLIST_BUTTON_LEN,
4040 &utf8title) != NSERROR_OK)
4041 return false;
4042
4043 char *iconname = ami_gui_get_cache_favicon_name(url, true);
4044 if (iconname == NULL) iconname = ASPrintf("icons/content.png");
4045 ami_locate_resource(menu_icon, iconname);
4046
4047 tb_userdata->gw->hotlist_toolbar_lab[item] = BitMapObj,
4048 IA_Scalable, TRUE,
4049 BITMAP_Screen, scrn,
4050 BITMAP_SourceFile, menu_icon,
4051 BITMAP_Masking, TRUE,
4052 BitMapEnd;
4053
4054 /* \todo make this scale the bitmap to these dimensions */
4055 SetAttrs(tb_userdata->gw->hotlist_toolbar_lab[item],
4056 BITMAP_Width, 16,
4057 BITMAP_Height, 16,
4058 TAG_DONE);
4059
4060 Object *lab_item = LabelObj,
4061 // LABEL_DrawInfo, dri,
4062 LABEL_DisposeImage, TRUE,
4063 LABEL_Image, tb_userdata->gw->hotlist_toolbar_lab[item],
4064 LABEL_Text, " ",
4065 LABEL_Text, utf8title,
4066 LabelEnd;
4067
4068 free(utf8title);
4069
4070 speed_button_node = AllocSpeedButtonNode(item,
4071 SBNA_Image, lab_item,
4073 SBNA_UserData, (void *)url,
4074 TAG_DONE);
4075
4076 AddTail(tb_userdata->sblist, speed_button_node);
4077
4078 tb_userdata->items++;
4079 return true;
4080}
4081
4082static int ami_gui_hotlist_scan(struct List *speed_button_list, struct gui_window_2 *gwin)
4083{
4084 struct ami_gui_tb_userdata userdata;
4085 userdata.gw = gwin;
4086 userdata.sblist = speed_button_list;
4087 userdata.items = 0;
4088
4089 ami_hotlist_scan((void *)&userdata, 0, messages_get("HotlistToolbar"), ami_gui_hotlist_add);
4090 return userdata.items;
4091}
4092
4094{
4095 struct TagItem attrs[2];
4096
4097 attrs[0].ti_Tag = CHILD_MinWidth;
4098 attrs[0].ti_Data = 0;
4099 attrs[1].ti_Tag = TAG_DONE;
4100 attrs[1].ti_Data = 0;
4101
4102 NewList(&gwin->hotlist_toolbar_list);
4103
4104 if(ami_gui_hotlist_scan(&gwin->hotlist_toolbar_list, gwin) > 0) {
4105 gwin->objects[GID_HOTLIST] =
4107 GA_ID, GID_HOTLIST,
4108 GA_RelVerify, TRUE,
4109 ICA_TARGET, ICTARGET_IDCMP,
4110 SPEEDBAR_BevelStyle, BVS_NONE,
4111 SPEEDBAR_Buttons, &gwin->hotlist_toolbar_list,
4112 SpeedBarEnd;
4113
4114 gwin->objects[GID_HOTLISTSEPBAR] =
4115 BevelObj,
4116 BEVEL_Style, BVS_SBAR_VERT,
4117 BevelEnd;
4118#ifdef __amigaos4__
4119 IDoMethod(gwin->objects[GID_HOTLISTLAYOUT], LM_ADDCHILD,
4120 gwin->win, gwin->objects[GID_HOTLIST], attrs);
4121
4122 IDoMethod(gwin->objects[GID_HOTLISTLAYOUT], LM_ADDIMAGE,
4123 gwin->win, gwin->objects[GID_HOTLISTSEPBAR], NULL);
4124
4125#else
4126 SetAttrs(gwin->objects[GID_HOTLISTLAYOUT],
4127 LAYOUT_AddChild, gwin->objects[GID_HOTLIST], TAG_MORE, &attrs);
4128 SetAttrs(gwin->objects[GID_HOTLISTLAYOUT],
4129 LAYOUT_AddChild, gwin->objects[GID_HOTLISTSEPBAR], TAG_DONE);
4130#endif
4131
4132 FlushLayoutDomainCache((struct Gadget *)gwin->objects[GID_MAIN]);
4133
4134 RethinkLayout((struct Gadget *)gwin->objects[GID_MAIN],
4135 gwin->win, NULL, TRUE);
4136
4137 ami_schedule_redraw(gwin, true);
4138 }
4139}
4140
4141static void ami_gui_hotlist_toolbar_free(struct gui_window_2 *gwin, struct List *speed_button_list)
4142{
4143 int i;
4144 struct Node *node;
4145 struct Node *nnode;
4146
4147 if(nsoption_bool(kiosk_mode) == true) return;
4148
4149 if(IsListEmpty(speed_button_list)) return;
4150 node = GetHead(speed_button_list);
4151
4152 do {
4153 nnode = GetSucc(node);
4154 Remove(node);
4155 FreeSpeedButtonNode(node);
4156 } while((node = nnode));
4157
4158 for(i = 0; i < AMI_GUI_TOOLBAR_MAX; i++) {
4159 if(gwin->hotlist_toolbar_lab[i]) {
4160 DisposeObject(gwin->hotlist_toolbar_lab[i]);
4161 gwin->hotlist_toolbar_lab[i] = NULL;
4162 }
4163 }
4164}
4165
4167{
4168#ifdef __amigaos4__
4169 IDoMethod(gwin->objects[GID_HOTLISTLAYOUT], LM_REMOVECHILD,
4170 gwin->win, gwin->objects[GID_HOTLIST]);
4171
4172 IDoMethod(gwin->objects[GID_HOTLISTLAYOUT], LM_REMOVECHILD,
4173 gwin->win, gwin->objects[GID_HOTLISTSEPBAR]);
4174#else
4175 SetAttrs(gwin->objects[GID_HOTLISTLAYOUT],
4176 LAYOUT_RemoveChild, gwin->objects[GID_HOTLIST], TAG_DONE);
4177 SetAttrs(gwin->objects[GID_HOTLISTLAYOUT],
4178 LAYOUT_RemoveChild, gwin->objects[GID_HOTLISTSEPBAR], TAG_DONE);
4179#endif
4180 FlushLayoutDomainCache((struct Gadget *)gwin->objects[GID_MAIN]);
4181
4182 RethinkLayout((struct Gadget *)gwin->objects[GID_MAIN],
4183 gwin->win, NULL, TRUE);
4184
4185 ami_schedule_redraw(gwin, true);
4186}
4187
4189{
4190 if(IsListEmpty(&gwin->hotlist_toolbar_list)) {
4192 return;
4193 }
4194
4195 /* Below should be SetAttr according to Autodocs */
4196 SetGadgetAttrs((struct Gadget *)gwin->objects[GID_HOTLIST],
4197 gwin->win, NULL,
4198 SPEEDBAR_Buttons, ~0,
4199 TAG_DONE);
4200
4202
4203 if(ami_gui_hotlist_scan(&gwin->hotlist_toolbar_list, gwin) > 0) {
4204 SetGadgetAttrs((struct Gadget *)gwin->objects[GID_HOTLIST],
4205 gwin->win, NULL,
4206 SPEEDBAR_Buttons, &gwin->hotlist_toolbar_list,
4207 TAG_DONE);
4208 } else {
4210 }
4211}
4212
4213/**
4214 * Update hotlist toolbar and recreate the menu for all windows
4215 */
4217{
4218 struct nsObject *node;
4219 struct nsObject *nnode;
4220 struct gui_window_2 *gwin;
4221
4222 if(IsMinListEmpty(window_list)) return;
4223
4225
4226 node = (struct nsObject *)GetHead((struct List *)window_list);
4227
4228 do {
4229 nnode=(struct nsObject *)GetSucc((struct Node *)node);
4230 gwin = node->objstruct;
4231
4232 if(node->Type == AMINS_WINDOW) {
4234 }
4235 } while((node = nnode));
4236}
4237
4238static void ami_toggletabbar(struct gui_window_2 *gwin, bool show)
4239{
4240 if(ClickTabBase->lib_Version < 53) return;
4241
4242 if(show) {
4243 struct TagItem attrs[3];
4244
4245 attrs[0].ti_Tag = CHILD_WeightedWidth;
4246 attrs[0].ti_Data = 0;
4247 attrs[1].ti_Tag = CHILD_WeightedHeight;
4248 attrs[1].ti_Data = 0;
4249 attrs[2].ti_Tag = TAG_DONE;
4250 attrs[2].ti_Data = 0;
4251
4252 gwin->objects[GID_TABS] = ClickTabObj,
4253 GA_ID, GID_TABS,
4254 GA_RelVerify, TRUE,
4255 GA_Underscore, 13, // disable kb shortcuts
4257 CLICKTAB_Labels, &gwin->tab_list,
4261 ClickTabEnd;
4262
4263 gwin->objects[GID_ADDTAB] = ButtonObj,
4264 GA_ID, GID_ADDTAB,
4265 GA_RelVerify, TRUE,
4267 GA_Text, "+",
4268 BUTTON_RenderImage, gwin->objects[GID_ADDTAB_BM],
4269 ButtonEnd;
4270#ifdef __amigaos4__
4271 IDoMethod(gwin->objects[GID_TABLAYOUT], LM_ADDCHILD,
4272 gwin->win, gwin->objects[GID_TABS], NULL);
4273
4274 IDoMethod(gwin->objects[GID_TABLAYOUT], LM_ADDCHILD,
4275 gwin->win, gwin->objects[GID_ADDTAB], attrs);
4276#else
4277 SetAttrs(gwin->objects[GID_TABLAYOUT],
4278 LAYOUT_AddChild, gwin->objects[GID_TABS], TAG_DONE);
4279 SetAttrs(gwin->objects[GID_TABLAYOUT],
4280 LAYOUT_AddChild, gwin->objects[GID_ADDTAB], TAG_MORE, &attrs);
4281#endif
4282 } else {
4283#ifdef __amigaos4__
4284 IDoMethod(gwin->objects[GID_TABLAYOUT], LM_REMOVECHILD,
4285 gwin->win, gwin->objects[GID_TABS]);
4286
4287 IDoMethod(gwin->objects[GID_TABLAYOUT], LM_REMOVECHILD,
4288 gwin->win, gwin->objects[GID_ADDTAB]);
4289#else
4290 SetAttrs(gwin->objects[GID_TABLAYOUT],
4291 LAYOUT_RemoveChild, gwin->objects[GID_TABS], TAG_DONE);
4292 SetAttrs(gwin->objects[GID_TABLAYOUT],
4293 LAYOUT_RemoveChild, gwin->objects[GID_ADDTAB], TAG_DONE);
4294#endif
4295
4296 gwin->objects[GID_TABS] = NULL;
4297 gwin->objects[GID_ADDTAB] = NULL;
4298 }
4299
4300 FlushLayoutDomainCache((struct Gadget *)gwin->objects[GID_MAIN]);
4301
4302 RethinkLayout((struct Gadget *)gwin->objects[GID_MAIN],
4303 gwin->win, NULL, TRUE);
4304
4305 if (gwin->gw && gwin->gw->bw) {
4309 amiga_window_invalidate_area(gwin->gw, NULL);
4310 }
4311}
4312
4314{
4315 struct nsObject *node;
4316 struct nsObject *nnode;
4317 struct gui_window_2 *gwin;
4318
4319 if(IsMinListEmpty(window_list)) return;
4320
4321 node = (struct nsObject *)GetHead((struct List *)window_list);
4322
4323 do {
4324 nnode=(struct nsObject *)GetSucc((struct Node *)node);
4325 gwin = node->objstruct;
4326
4327 if(node->Type == AMINS_WINDOW)
4328 {
4329 if(gwin->tabs == 1) {
4330 if(nsoption_bool(tab_always_show) == true) {
4331 ami_toggletabbar(gwin, true);
4332 } else {
4333 ami_toggletabbar(gwin, false);
4334 }
4335 }
4336 }
4337 } while((node = nnode));
4338}
4339
4340
4341/**
4342 * Count windows, and optionally tabs.
4343 *
4344 * \param window window to count tabs of
4345 * \param tabs if window > 0, will be updated to contain the number of tabs
4346 * in that window, unchanged otherwise
4347 * \return number of windows currently open
4348 */
4349int ami_gui_count_windows(int window, int *tabs)
4350{
4351 int windows = 0;
4352 struct nsObject *node, *nnode;
4353 struct gui_window_2 *gwin;
4354
4356 node = (struct nsObject *)GetHead((struct List *)window_list);
4357 do {
4358 nnode=(struct nsObject *)GetSucc((struct Node *)node);
4359
4360 gwin = node->objstruct;
4361
4362 if(node->Type == AMINS_WINDOW) {
4363 windows++;
4364 if(window == windows) *tabs = gwin->tabs;
4365 }
4366 } while((node = nnode));
4367 }
4368 return windows;
4369}
4370
4371/**
4372 * Set the scale of a gui window
4373 *
4374 * \param gw gui_window to set scale for
4375 * \param scale scale to set
4376 */
4377void ami_gui_set_scale(struct gui_window *gw, float scale)
4378{
4379 browser_window_set_scale(gw->bw, scale, true);
4380 ami_schedule_redraw(gw->shared, true);
4381}
4382
4383void ami_gui_adjust_scale(struct gui_window *gw, float adjustment)
4384{
4385 browser_window_set_scale(gw->bw, adjustment, false);
4386 ami_schedule_redraw(gw->shared, true);
4387}
4388
4390{
4391 if(nsoption_bool(new_tab_is_active) == true) return;
4392
4393 /* Switch to the just-opened tab (if new_tab_is_active, we already did!) */
4394 RefreshSetGadgetAttrs((struct Gadget *)gwin->objects[GID_TABS],
4395 gwin->win, NULL,
4396 CLICKTAB_CurrentNode, gwin->last_new_tab,
4397 TAG_DONE);
4398
4399 ami_switch_tab(gwin, false);
4400}
4401
4403{
4404 nsurl *url;
4405 nserror error;
4406 struct browser_window *bw = NULL;
4407
4408 error = nsurl_create(nsoption_charp(homepage_url), &url);
4409 if (error == NSERROR_OK) {
4412 url,
4413 NULL,
4414 gwin->gw->bw,
4415 &bw);
4416 nsurl_unref(url);
4417 }
4418 if (error != NSERROR_OK) {
4420 return error;
4421 }
4422
4424
4425 return NSERROR_OK;
4426}
4427
4428static void ami_do_redraw_tiled(struct gui_window_2 *gwin, bool busy,
4429 int left, int top, int width, int height,
4430 int sx, int sy, struct IBox *bbox, struct redraw_context *ctx)
4431{
4432 struct gui_globals *glob = (struct gui_globals *)ctx->priv;
4433 int x, y;
4434 struct rect clip;
4435 int tile_size_x;
4436 int tile_size_y;
4437
4438 ami_plot_ra_get_size(glob, &tile_size_x, &tile_size_y);
4440
4441 if(top < 0) {
4442 height += top;
4443 top = 0;
4444 }
4445
4446 if(left < 0) {
4447 width += left;
4448 left = 0;
4449 }
4450
4451 if(top < sy) {
4452 height += (top - sy);
4453 top = sy;
4454 }
4455 if(left < sx) {
4456 width += (left - sx);
4457 left = sx;
4458 }
4459
4460 if(((top - sy) + height) > bbox->Height)
4461 height = bbox->Height - (top - sy);
4462
4463 if(((left - sx) + width) > bbox->Width)
4464 width = bbox->Width - (left - sx);
4465
4466 if(width <= 0) return;
4467 if(height <= 0) return;
4468
4469 if(busy) ami_set_pointer(gwin, GUI_POINTER_WAIT, false);
4470
4471 for(y = top; y < (top + height); y += tile_size_y) {
4472 clip.y0 = 0;
4473 clip.y1 = tile_size_y;
4474 if(clip.y1 > height) clip.y1 = height;
4475 if(((y - sy) + clip.y1) > bbox->Height)
4476 clip.y1 = bbox->Height - (y - sy);
4477
4478 for(x = left; x < (left + width); x += tile_size_x) {
4479 clip.x0 = 0;
4480 clip.x1 = tile_size_x;
4481 if(clip.x1 > width) clip.x1 = width;
4482 if(((x - sx) + clip.x1) > bbox->Width)
4483 clip.x1 = bbox->Width - (x - sx);
4484
4485 if(browser_window_redraw(gwin->gw->bw,
4486 clip.x0 - (int)x,
4487 clip.y0 - (int)y,
4488 &clip, ctx))
4489 {
4490 ami_clearclipreg(glob);
4491#ifdef __amigaos4__
4492 BltBitMapTags(BLITA_SrcType, BLITT_BITMAP,
4493 BLITA_Source, ami_plot_ra_get_bitmap(glob),
4494 BLITA_SrcX, 0,
4495 BLITA_SrcY, 0,
4496 BLITA_DestType, BLITT_RASTPORT,
4497 BLITA_Dest, gwin->win->RPort,
4498 BLITA_DestX, bbox->Left + (int)(x - sx),
4499 BLITA_DestY, bbox->Top + (int)(y - sy),
4500 BLITA_Width, (int)(clip.x1),
4501 BLITA_Height, (int)(clip.y1),
4502 TAG_DONE);
4503#else
4504 BltBitMapRastPort(ami_plot_ra_get_bitmap(glob), 0, 0, gwin->win->RPort,
4505 bbox->Left + (int)(x - sx),
4506 bbox->Top + (int)(y - sy),
4507 (int)(clip.x1), (int)(clip.y1), 0xC0);
4508#endif
4509 }
4510 }
4511 }
4512
4513 if(busy) ami_reset_pointer(gwin);
4514}
4515
4516
4517/**
4518 * Redraw an area of the browser window - Amiga-specific function
4519 *
4520 * \param g a struct gui_window
4521 * \param bw a struct browser_window
4522 * \param busy busy flag passed to tiled redraw.
4523 * \param x0 top-left co-ordinate (in document co-ordinates)
4524 * \param y0 top-left co-ordinate (in document co-ordinates)
4525 * \param x1 bottom-right co-ordinate (in document co-ordinates)
4526 * \param y1 bottom-right co-ordinate (in document co-ordinates)
4527 */
4528
4529static void ami_do_redraw_limits(struct gui_window *g, struct browser_window *bw, bool busy,
4530 int x0, int y0, int x1, int y1)
4531{
4532 struct IBox *bbox;
4533 ULONG sx, sy;
4534
4535 struct redraw_context ctx = {
4536 .interactive = true,
4537 .background_images = true,
4538 .plot = &amiplot,
4539 .priv = browserglob
4540 };
4541
4542 if(!g) return;
4543 if(browser_window_redraw_ready(bw) == false) return;
4544
4545 sx = g->scrollx;
4546 sy = g->scrolly;
4547
4548 if(g != g->shared->gw) return;
4549
4550 if(ami_gui_get_space_box((Object *)g->shared->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
4551 amiga_warn_user("NoMemory", "");
4552 return;
4553 }
4554
4555 ami_do_redraw_tiled(g->shared, busy, x0, y0,
4556 x1 - x0, y1 - y0, sx, sy, bbox, &ctx);
4557
4559
4560 return;
4561}
4562
4563
4564static void ami_refresh_window(struct gui_window_2 *gwin)
4565{
4566 /* simplerefresh only */
4567
4568 struct IBox *bbox;
4569 int sx, sy;
4570 struct RegionRectangle *regrect;
4571 struct rect r;
4572
4573 sx = gwin->gw->scrollx;
4574 sy = gwin->gw->scrolly;
4575
4576 ami_set_pointer(gwin, GUI_POINTER_WAIT, false);
4577
4578 if(ami_gui_get_space_box((Object *)gwin->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
4579 amiga_warn_user("NoMemory", "");
4580 return;
4581 }
4582
4583 BeginRefresh(gwin->win);
4584
4585 r.x0 = (gwin->win->RPort->Layer->DamageList->bounds.MinX - bbox->Left) + sx - 1;
4586 r.x1 = (gwin->win->RPort->Layer->DamageList->bounds.MaxX - bbox->Left) + sx + 2;
4587 r.y0 = (gwin->win->RPort->Layer->DamageList->bounds.MinY - bbox->Top) + sy - 1;
4588 r.y1 = (gwin->win->RPort->Layer->DamageList->bounds.MaxY - bbox->Top) + sy + 2;
4589
4590 regrect = gwin->win->RPort->Layer->DamageList->RegionRectangle;
4591
4593
4594 while(regrect)
4595 {
4596 r.x0 = (regrect->bounds.MinX - bbox->Left) + sx - 1;
4597 r.x1 = (regrect->bounds.MaxX - bbox->Left) + sx + 2;
4598 r.y0 = (regrect->bounds.MinY - bbox->Top) + sy - 1;
4599 r.y1 = (regrect->bounds.MaxY - bbox->Top) + sy + 2;
4600
4601 regrect = regrect->Next;
4602
4604 }
4605
4606 EndRefresh(gwin->win, TRUE);
4607
4609 ami_reset_pointer(gwin);
4610}
4611
4612HOOKF(void, ami_scroller_hook, Object *, object, struct IntuiMessage *)
4613{
4614 ULONG gid;
4615 struct gui_window_2 *gwin = hook->h_Data;
4616 struct IntuiWheelData *wheel;
4617 struct Node *node = NULL;
4618 nsurl *url;
4619
4620 switch(msg->Class)
4621 {
4622 case IDCMP_IDCMPUPDATE:
4623 gid = GetTagData( GA_ID, 0, msg->IAddress );
4624
4625 switch( gid )
4626 {
4627 case GID_HSCROLL:
4628 case GID_VSCROLL:
4629 if(nsoption_bool(faster_scroll) == true) gwin->redraw_scroll = true;
4630 else gwin->redraw_scroll = false;
4631
4632 ami_schedule_redraw(gwin, true);
4633 break;
4634
4635 case GID_HOTLIST:
4636 if((node = (struct Node *)GetTagData(SPEEDBAR_SelectedNode, 0, msg->IAddress))) {
4637 GetSpeedButtonNodeAttrs(node, SBNA_UserData, (ULONG *)&url, TAG_DONE);
4638
4639 if(gwin->key_state & BROWSER_MOUSE_MOD_2) {
4641 url,
4642 NULL,
4643 gwin->gw->bw,
4644 NULL);
4645 } else {
4647 url,
4648 NULL,
4650 NULL,
4651 NULL,
4652 NULL);
4653
4654 }
4655 }
4656 break;
4657 }
4658 break;
4659#ifdef __amigaos4__
4661 if(msg->Code == IMSGCODE_INTUIWHEELDATA)
4662 {
4663 wheel = (struct IntuiWheelData *)msg->IAddress;
4664
4665 ami_gui_scroll_internal(gwin, wheel->WheelX * 50, wheel->WheelY * 50);
4666 }
4667 break;
4668#endif
4669 case IDCMP_SIZEVERIFY:
4670 break;
4671
4672 case IDCMP_REFRESHWINDOW:
4673 ami_refresh_window(gwin);
4674 break;
4675
4676 default:
4677 NSLOG(netsurf, INFO,
4678 "IDCMP hook unhandled event: %ld", msg->Class);
4679 break;
4680 }
4681// ReplyMsg((struct Message *)msg);
4682}
4683
4684/* exported function documented in gui.h */
4685nserror ami_gui_win_list_add(void *win, int type, const struct ami_win_event_table *table)
4686{
4687 struct nsObject *node = AddObject(window_list, type);
4688 if(node == NULL) return NSERROR_NOMEM;
4689 node->objstruct = win;
4690
4691 struct ami_generic_window *w = (struct ami_generic_window *)win;
4692 w->tbl = table;
4693 w->node = node;
4694
4695 return NSERROR_OK;
4696}
4697
4698/* exported function documented in gui.h */
4700{
4701 struct ami_generic_window *w = (struct ami_generic_window *)win;
4702
4703 if(w->node->Type == AMINS_TVWINDOW) {
4705 } else {
4706 DelObject(w->node);
4707 }
4708}
4709
4710static const struct ami_win_event_table ami_gui_table = {
4713};
4714
4715static struct gui_window *
4717 struct gui_window *existing,
4719{
4720 struct gui_window *g = NULL;
4721 ULONG offset = 0;
4722 ULONG curx = nsoption_int(window_x), cury = nsoption_int(window_y);
4723 ULONG curw = nsoption_int(window_width), curh = nsoption_int(window_height);
4724 char nav_west[100],nav_west_s[100],nav_west_g[100];
4725 char nav_east[100],nav_east_s[100],nav_east_g[100];
4726 char stop[100],stop_s[100],stop_g[100];
4727 char reload[100],reload_s[100],reload_g[100];
4728 char home[100],home_s[100],home_g[100];
4729 char closetab[100],closetab_s[100],closetab_g[100];
4730 char addtab[100],addtab_s[100],addtab_g[100];
4731 char fave[100], unfave[100];
4732 char pi_insecure[100], pi_internal[100], pi_local[100], pi_secure[100], pi_warning[100];
4733 char tabthrobber[100];
4734 ULONG refresh_mode = WA_SmartRefresh;
4735 ULONG defer_layout = TRUE;
4736 ULONG idcmp_sizeverify = IDCMP_SIZEVERIFY;
4737
4738 NSLOG(netsurf, INFO, "Creating window");
4739
4740 if (!scrn) ami_openscreenfirst();
4741
4742 if (nsoption_bool(kiosk_mode)) flags &= ~GW_CREATE_TAB;
4743 if (nsoption_bool(resize_with_contents)) idcmp_sizeverify = 0;
4744
4745 /* Offset the new window by titlebar + 1 as per AmigaOS style guide.
4746 * If we don't have a clone window we offset by all windows open. */
4747 offset = scrn->WBorTop + scrn->Font->ta_YSize + 1;
4748
4749 if(existing) {
4750 curx = existing->shared->win->LeftEdge;
4751 cury = existing->shared->win->TopEdge + offset;
4752 curw = existing->shared->win->Width;
4753 curh = existing->shared->win->Height;
4754 } else {
4755 if(nsoption_bool(kiosk_mode) == false) {
4756 cury += offset * ami_gui_count_windows(0, NULL);
4757 }
4758 }
4759
4760 if(curh > (scrn->Height - cury)) curh = scrn->Height - cury;
4761
4762 g = calloc(1, sizeof(struct gui_window));
4763
4764 if(!g)
4765 {
4766 amiga_warn_user("NoMemory","");
4767 return NULL;
4768 }
4769
4770 NewList(&g->dllist);
4773 g->bw = bw;
4774
4775 NewList(&g->loglist);
4776#ifdef __amigaos4__
4777 g->logcolumns = AllocLBColumnInfo(4,
4778 LBCIA_Column, 0,
4779 // LBCIA_CopyTitle, TRUE,
4780 LBCIA_Title, "time", /**\TODO: add these to Messages */
4781 LBCIA_Weight, 10,
4782 LBCIA_DraggableSeparator, TRUE,
4783 LBCIA_Separator, TRUE,
4784 LBCIA_Column, 1,
4785 // LBCIA_CopyTitle, TRUE,
4786 LBCIA_Title, "source", /**\TODO: add these to Messages */
4787 LBCIA_Weight, 10,
4788 LBCIA_DraggableSeparator, TRUE,
4789 LBCIA_Separator, TRUE,
4790 LBCIA_Column, 2,
4791 // LBCIA_CopyTitle, TRUE,
4792 LBCIA_Title, "level", /**\TODO: add these to Messages */
4793 LBCIA_Weight, 5,
4794 LBCIA_DraggableSeparator, TRUE,
4795 LBCIA_Separator, TRUE,
4796 LBCIA_Column, 3,
4797 // LBCIA_CopyTitle, TRUE,
4798 LBCIA_Title, "message", /**\TODO: add these to Messages */
4799 LBCIA_Weight, 75,
4800 LBCIA_DraggableSeparator, TRUE,
4801 LBCIA_Separator, TRUE,
4802 TAG_DONE);
4803#else
4804 /**\TODO write OS3-compatible version */
4805#endif
4806
4807 if((flags & GW_CREATE_TAB) && existing)
4808 {
4809 g->shared = existing->shared;
4810 g->tab = g->shared->next_tab;
4811 g->shared->tabs++; /* do this early so functions know to update the tabs */
4812
4813 if((g->shared->tabs == 2) && (nsoption_bool(tab_always_show) == false)) {
4814 ami_toggletabbar(g->shared, true);
4815 }
4816
4817 SetGadgetAttrs((struct Gadget *)g->shared->objects[GID_TABS],
4818 g->shared->win, NULL,
4819 CLICKTAB_Labels, ~0,
4820 TAG_DONE);
4821
4822 g->tab_node = AllocClickTabNode(TNA_Text, messages_get("NetSurf"),
4823 TNA_Number, g->tab,
4824 TNA_UserData, g,
4825 TNA_CloseGadget, TRUE,
4826 TAG_DONE);
4827
4828 if(nsoption_bool(new_tab_last)) {
4829 AddTail(&g->shared->tab_list, g->tab_node);
4830 } else {
4831 struct Node *insert_after = existing->tab_node;
4832
4833 if(g->shared->last_new_tab)
4834 insert_after = g->shared->last_new_tab;
4835 Insert(&g->shared->tab_list, g->tab_node, insert_after);
4836 }
4837
4838 g->shared->last_new_tab = g->tab_node;
4839
4840 RefreshSetGadgetAttrs((struct Gadget *)g->shared->objects[GID_TABS],
4841 g->shared->win, NULL,
4842 CLICKTAB_Labels, &g->shared->tab_list,
4843 TAG_DONE);
4844
4845 if(nsoption_bool(new_tab_is_active)) {
4846 RefreshSetGadgetAttrs((struct Gadget *)g->shared->objects[GID_TABS],
4847 g->shared->win, NULL,
4848 CLICKTAB_Current, g->tab,
4849 TAG_DONE);
4850 }
4851
4852 if(ClickTabBase->lib_Version < 53) {
4853 RethinkLayout((struct Gadget *)g->shared->objects[GID_TABLAYOUT],
4854 g->shared->win, NULL, TRUE);
4855 }
4856
4857 g->shared->next_tab++;
4858
4859 if(nsoption_bool(new_tab_is_active)) ami_switch_tab(g->shared,false);
4860
4863
4864 return g;
4865 }
4866
4867 g->shared = calloc(1, sizeof(struct gui_window_2));
4868
4869 if(!g->shared)
4870 {
4871 amiga_warn_user("NoMemory","");
4872 return NULL;
4873 }
4874
4876
4877 g->shared->scrollerhook.h_Entry = (void *)ami_scroller_hook;
4878 g->shared->scrollerhook.h_Data = g->shared;
4879
4880 g->shared->favicon_hook.h_Entry = (void *)ami_set_favicon_render_hook;
4881 g->shared->favicon_hook.h_Data = g->shared;
4882
4883 g->shared->throbber_hook.h_Entry = (void *)ami_set_throbber_render_hook;
4884 g->shared->throbber_hook.h_Data = g->shared;
4885
4886 g->shared->browser_hook.h_Entry = (void *)ami_gui_browser_render_hook;
4887 g->shared->browser_hook.h_Data = g->shared;
4888
4889 newprefs_hook.h_Entry = (void *)ami_gui_newprefs_hook;
4890 newprefs_hook.h_Data = 0;
4891
4895 g->shared->clicktab_ctxmenu = NULL;
4896
4897 if(nsoption_bool(window_simple_refresh) == true) {
4898 refresh_mode = WA_SimpleRefresh;
4899 defer_layout = FALSE; /* testing reveals this does work with SimpleRefresh,
4900 but the docs say it doesn't so err on the side of caution. */
4901 } else {
4902 refresh_mode = WA_SmartRefresh;
4903 defer_layout = TRUE;
4904 }
4905
4906 if(!nsoption_bool(kiosk_mode))
4907 {
4908 ULONG addtabclosegadget = TAG_IGNORE;
4909 ULONG iconifygadget = FALSE;
4910
4911#ifdef __amigaos4__
4912 if (nsoption_charp(pubscreen_name) &&
4913 (locked_screen == TRUE) &&
4914 (strcmp(nsoption_charp(pubscreen_name), "Workbench") == 0))
4915 iconifygadget = TRUE;
4916#endif
4917
4918 NSLOG(netsurf, INFO, "Creating menu");
4919 struct Menu *menu = ami_gui_menu_create(g->shared);
4920
4921 NewList(&g->shared->tab_list);
4922 g->tab_node = AllocClickTabNode(TNA_Text,messages_get("NetSurf"),
4923 TNA_Number, 0,
4924 TNA_UserData, g,
4925 TNA_CloseGadget, TRUE,
4926 TAG_DONE);
4927 AddTail(&g->shared->tab_list,g->tab_node);
4928
4930 g->shared->search_bm = NULL;
4931
4932 g->shared->tabs=1;
4933 g->shared->next_tab=1;
4934
4935 g->shared->svbuffer = calloc(1, 2000);
4936
4938 translate_escape_chars(messages_get("HelpToolbarBack"));
4940 translate_escape_chars(messages_get("HelpToolbarForward"));
4942 translate_escape_chars(messages_get("HelpToolbarStop"));
4944 translate_escape_chars(messages_get("HelpToolbarReload"));
4946 translate_escape_chars(messages_get("HelpToolbarHome"));
4947 g->shared->helphints[GID_URL] =
4948 translate_escape_chars(messages_get("HelpToolbarURL"));
4950 translate_escape_chars(messages_get("HelpToolbarWebSearch"));
4952 translate_escape_chars(messages_get("HelpToolbarAddTab"));
4953
4959
4960 ami_get_theme_filename(nav_west, "theme_nav_west", false);
4961 ami_get_theme_filename(nav_west_s, "theme_nav_west_s", false);
4962 ami_get_theme_filename(nav_west_g, "theme_nav_west_g", false);
4963 ami_get_theme_filename(nav_east, "theme_nav_east", false);
4964 ami_get_theme_filename(nav_east_s, "theme_nav_east_s", false);
4965 ami_get_theme_filename(nav_east_g, "theme_nav_east_g", false);
4966 ami_get_theme_filename(stop, "theme_stop", false);
4967 ami_get_theme_filename(stop_s, "theme_stop_s", false);
4968 ami_get_theme_filename(stop_g, "theme_stop_g", false);
4969 ami_get_theme_filename(reload, "theme_reload", false);
4970 ami_get_theme_filename(reload_s, "theme_reload_s", false);
4971 ami_get_theme_filename(reload_g, "theme_reload_g", false);
4972 ami_get_theme_filename(home, "theme_home", false);
4973 ami_get_theme_filename(home_s, "theme_home_s", false);
4974 ami_get_theme_filename(home_g, "theme_home_g", false);
4975 ami_get_theme_filename(closetab, "theme_closetab", false);
4976 ami_get_theme_filename(closetab_s, "theme_closetab_s", false);
4977 ami_get_theme_filename(closetab_g, "theme_closetab_g", false);
4978 ami_get_theme_filename(addtab, "theme_addtab", false);
4979 ami_get_theme_filename(addtab_s, "theme_addtab_s", false);
4980 ami_get_theme_filename(addtab_g, "theme_addtab_g", false);
4981 ami_get_theme_filename(tabthrobber, "theme_tab_loading", false);
4982 ami_get_theme_filename(fave, "theme_fave", false);
4983 ami_get_theme_filename(unfave, "theme_unfave", false);
4984 ami_get_theme_filename(pi_insecure, "theme_pageinfo_insecure", false);
4985 ami_get_theme_filename(pi_internal, "theme_pageinfo_internal", false);
4986 ami_get_theme_filename(pi_local, "theme_pageinfo_local", false);
4987 ami_get_theme_filename(pi_secure, "theme_pageinfo_secure", false);
4988 ami_get_theme_filename(pi_warning, "theme_pageinfo_warning", false);
4989
4991 BITMAP_SourceFile, fave,
4992 BITMAP_Screen, scrn,
4993 BITMAP_Masking, TRUE,
4994 BitMapEnd;
4995
4997 BITMAP_SourceFile, unfave,
4998 BITMAP_Screen, scrn,
4999 BITMAP_Masking, TRUE,
5000 BitMapEnd;
5001
5003 BITMAP_SourceFile, addtab,
5004 BITMAP_SelectSourceFile, addtab_s,
5005 BITMAP_DisabledSourceFile, addtab_g,
5006 BITMAP_Screen, scrn,
5007 BITMAP_Masking, TRUE,
5008 BitMapEnd;
5009
5011 BITMAP_SourceFile, closetab,
5012 BITMAP_SelectSourceFile, closetab_s,
5013 BITMAP_DisabledSourceFile, closetab_g,
5014 BITMAP_Screen, scrn,
5015 BITMAP_Masking, TRUE,
5016 BitMapEnd;
5017
5019 BITMAP_SourceFile, pi_insecure,
5020 BITMAP_Screen, scrn,
5021 BITMAP_Masking, TRUE,
5022 BitMapEnd;
5023
5025 BITMAP_SourceFile, pi_internal,
5026 BITMAP_Screen, scrn,
5027 BITMAP_Masking, TRUE,
5028 BitMapEnd;
5029
5031 BITMAP_SourceFile, pi_local,
5032 BITMAP_Screen, scrn,
5033 BITMAP_Masking, TRUE,
5034 BitMapEnd;
5035
5037 BITMAP_SourceFile, pi_secure,
5038 BITMAP_Screen, scrn,
5039 BITMAP_Masking, TRUE,
5040 BitMapEnd;
5041
5043 BITMAP_SourceFile, pi_warning,
5044 BITMAP_Screen, scrn,
5045 BITMAP_Masking, TRUE,
5046 BitMapEnd;
5047
5048
5049 if(ClickTabBase->lib_Version < 53)
5050 {
5051 addtabclosegadget = LAYOUT_AddChild;
5053 GA_ID, GID_CLOSETAB,
5054 GA_RelVerify, TRUE,
5055 BUTTON_RenderImage, g->shared->objects[GID_CLOSETAB_BM],
5056 ButtonEnd;
5057
5059 GA_ID,GID_TABS,
5060 GA_RelVerify,TRUE,
5061 GA_Underscore,13, // disable kb shortcuts
5062 CLICKTAB_Labels,&g->shared->tab_list,
5064 ClickTabEnd;
5065
5067 GA_ID, GID_ADDTAB,
5068 GA_RelVerify, TRUE,
5069 GA_Text, "+",
5070 BUTTON_RenderImage, g->shared->objects[GID_ADDTAB_BM],
5071 ButtonEnd;
5072 }
5073 else
5074 {
5076 BITMAP_SourceFile, tabthrobber,
5077 BITMAP_Screen,scrn,
5078 BITMAP_Masking,TRUE,
5079 BitMapEnd;
5080 }
5081
5082 NSLOG(netsurf, INFO, "Creating window object");
5083
5085 WA_ScreenTitle, ami_gui_get_screen_title(),
5086 WA_Activate, TRUE,
5087 WA_DepthGadget, TRUE,
5088 WA_DragBar, TRUE,
5089 WA_CloseGadget, TRUE,
5090 WA_SizeGadget, TRUE,
5091 WA_Top,cury,
5092 WA_Left,curx,
5093 WA_Width,curw,
5094 WA_Height,curh,
5095 WA_PubScreen,scrn,
5096 WA_ReportMouse,TRUE,
5097 refresh_mode, TRUE,
5098 WA_SizeBBottom, TRUE,
5100 WA_IDCMP, IDCMP_MENUPICK | IDCMP_MOUSEMOVE |
5101 IDCMP_MOUSEBUTTONS | IDCMP_NEWSIZE |
5102 IDCMP_RAWKEY | idcmp_sizeverify |
5103 IDCMP_GADGETUP | IDCMP_IDCMPUPDATE |
5104 IDCMP_REFRESHWINDOW |
5105 IDCMP_ACTIVEWINDOW | IDCMP_EXTENDEDMOUSE,
5106 WINDOW_IconifyGadget, iconifygadget,
5107 WINDOW_MenuStrip, menu,
5108 WINDOW_MenuUserData, WGUD_HOOK,
5110 WINDOW_IDCMPHook, &g->shared->scrollerhook,
5111 WINDOW_IDCMPHookBits, IDCMP_IDCMPUPDATE | IDCMP_REFRESHWINDOW |
5112 IDCMP_EXTENDEDMOUSE | IDCMP_SIZEVERIFY,
5113 WINDOW_SharedPort, sport,
5115 WINDOW_GadgetHelp, TRUE,
5116 WINDOW_UserData, g->shared,
5117 WINDOW_ParentGroup, g->shared->objects[GID_MAIN] = LayoutVObj,
5118 LAYOUT_DeferLayout, defer_layout,
5119 LAYOUT_SpaceOuter, TRUE,
5120 LAYOUT_AddChild, g->shared->objects[GID_TOOLBARLAYOUT] = LayoutHObj,
5121 LAYOUT_VertAlignment, LALIGN_CENTER,
5122 LAYOUT_AddChild, g->shared->objects[GID_BACK] = ButtonObj,
5123 GA_ID, GID_BACK,
5124 GA_RelVerify, TRUE,
5125 GA_Disabled, TRUE,
5128 BUTTON_RenderImage,BitMapObj,
5129 BITMAP_SourceFile,nav_west,
5130 BITMAP_SelectSourceFile,nav_west_s,
5131 BITMAP_DisabledSourceFile,nav_west_g,
5132 BITMAP_Screen,scrn,
5133 BITMAP_Masking,TRUE,
5134 BitMapEnd,
5135 ButtonEnd,
5136 CHILD_WeightedWidth,0,
5137 CHILD_WeightedHeight,0,
5138 LAYOUT_AddChild, g->shared->objects[GID_FORWARD] = ButtonObj,
5139 GA_ID, GID_FORWARD,
5140 GA_RelVerify, TRUE,
5141 GA_Disabled, TRUE,
5144 BUTTON_RenderImage,BitMapObj,
5145 BITMAP_SourceFile,nav_east,
5146 BITMAP_SelectSourceFile,nav_east_s,
5147 BITMAP_DisabledSourceFile,nav_east_g,
5148 BITMAP_Screen,scrn,
5149 BITMAP_Masking,TRUE,
5150 BitMapEnd,
5151 ButtonEnd,
5152 CHILD_WeightedWidth,0,
5153 CHILD_WeightedHeight,0,
5154 LAYOUT_AddChild, g->shared->objects[GID_STOP] = ButtonObj,
5155 GA_ID,GID_STOP,
5156 GA_RelVerify,TRUE,
5158 BUTTON_RenderImage,BitMapObj,
5159 BITMAP_SourceFile,stop,
5160 BITMAP_SelectSourceFile,stop_s,
5162 BITMAP_Screen,scrn,
5163 BITMAP_Masking,TRUE,
5164 BitMapEnd,
5165 ButtonEnd,
5166 CHILD_WeightedWidth,0,
5167 CHILD_WeightedHeight,0,
5168 LAYOUT_AddChild, g->shared->objects[GID_RELOAD] = ButtonObj,
5169 GA_ID,GID_RELOAD,
5170 GA_RelVerify,TRUE,
5172 BUTTON_RenderImage,BitMapObj,
5173 BITMAP_SourceFile,reload,
5174 BITMAP_SelectSourceFile,reload_s,
5176 BITMAP_Screen,scrn,
5177 BITMAP_Masking,TRUE,
5178 BitMapEnd,
5179 ButtonEnd,
5180 CHILD_WeightedWidth,0,
5181 CHILD_WeightedHeight,0,
5182 LAYOUT_AddChild, g->shared->objects[GID_HOME] = ButtonObj,
5183 GA_ID,GID_HOME,
5184 GA_RelVerify,TRUE,
5186 BUTTON_RenderImage,BitMapObj,
5187 BITMAP_SourceFile,home,
5188 BITMAP_SelectSourceFile,home_s,
5190 BITMAP_Screen,scrn,
5191 BITMAP_Masking,TRUE,
5192 BitMapEnd,
5193 ButtonEnd,
5194 CHILD_WeightedWidth,0,
5195 CHILD_WeightedHeight,0,
5196 LAYOUT_AddChild, LayoutHObj, // FavIcon, URL bar and hotlist star
5197 LAYOUT_VertAlignment, LALIGN_CENTER,
5198 LAYOUT_AddChild, g->shared->objects[GID_ICON] = SpaceObj,
5199 GA_ID, GID_ICON,
5200 SPACE_MinWidth, 16,
5201 SPACE_MinHeight, 16,
5202 SPACE_Transparent, TRUE,
5203 // SPACE_RenderHook, &g->shared->favicon_hook,
5204 SpaceEnd,
5205 CHILD_WeightedWidth, 0,
5206 CHILD_WeightedHeight, 0,
5207 LAYOUT_AddChild, g->shared->objects[GID_PAGEINFO] = ButtonObj,
5208 GA_ID, GID_PAGEINFO,
5209 GA_RelVerify, TRUE,
5210 GA_ReadOnly, FALSE,
5211 BUTTON_RenderImage, g->shared->objects[GID_PAGEINFO_INTERNAL_BM],
5212 ButtonEnd,
5213 CHILD_WeightedWidth, 0,
5214 CHILD_WeightedHeight, 0,
5215 LAYOUT_AddChild, g->shared->objects[GID_URL] =
5216#ifdef __amigaos4__
5217 NewObject(urlStringClass, NULL,
5218#else
5219 StringObj,
5220#endif
5221 STRINGA_MaxChars, 2000,
5222 GA_ID, GID_URL,
5223 GA_RelVerify, TRUE,
5225 GA_TabCycle, TRUE,
5226 STRINGA_Buffer, g->shared->svbuffer,
5227#ifdef __amigaos4__
5229#endif
5230 TAG_DONE),
5231 LAYOUT_AddChild, g->shared->objects[GID_FAVE] = ButtonObj,
5232 GA_ID, GID_FAVE,
5233 GA_RelVerify, TRUE,
5234 // GA_HintInfo, g->shared->helphints[GID_FAVE],
5235 BUTTON_RenderImage, g->shared->objects[GID_FAVE_ADD],
5236 ButtonEnd,
5237 CHILD_WeightedWidth, 0,
5238 CHILD_WeightedHeight, 0,
5239 LayoutEnd,
5240 // GA_ID, GID_TOOLBARLAYOUT,
5241 // GA_RelVerify, TRUE,
5242 // LAYOUT_RelVerify, TRUE,
5243 LAYOUT_WeightBar, TRUE,
5244 LAYOUT_AddChild, LayoutHObj,
5245 LAYOUT_VertAlignment, LALIGN_CENTER,
5246 LAYOUT_AddChild, g->shared->objects[GID_SEARCH_ICON] = ChooserObj,
5247 GA_ID, GID_SEARCH_ICON,
5248 GA_RelVerify, TRUE,
5249 CHOOSER_DropDown, TRUE,
5250 CHOOSER_Labels, g->shared->web_search_list,
5251 CHOOSER_MaxLabels, 40, /* Same as options GUI */
5252 ChooserEnd,
5253 CHILD_WeightedWidth,0,
5254 CHILD_WeightedHeight,0,
5255 LAYOUT_AddChild, g->shared->objects[GID_SEARCHSTRING] = StringObj,
5256 GA_ID,GID_SEARCHSTRING,
5257 STRINGA_TextVal, NULL,
5258 GA_RelVerify,TRUE,
5260 StringEnd,
5261 LayoutEnd,
5262 CHILD_WeightedWidth, nsoption_int(web_search_width),
5263 LAYOUT_AddChild, g->shared->objects[GID_THROBBER] = SpaceObj,
5264 GA_ID,GID_THROBBER,
5265 SPACE_MinWidth, ami_theme_throbber_get_width(),
5266 SPACE_MinHeight, ami_theme_throbber_get_height(),
5267 SPACE_Transparent,TRUE,
5268 // SPACE_RenderHook, &g->shared->throbber_hook,
5269 SpaceEnd,
5270 CHILD_WeightedWidth,0,
5271 CHILD_WeightedHeight,0,
5272 LayoutEnd,
5273 CHILD_WeightedHeight,0,
5274 LAYOUT_AddImage, BevelObj,
5275 BEVEL_Style, BVS_SBAR_VERT,
5276 BevelEnd,
5277 CHILD_WeightedHeight, 0,
5278 LAYOUT_AddChild, g->shared->objects[GID_HOTLISTLAYOUT] = LayoutVObj,
5279 LAYOUT_SpaceInner, FALSE,
5280 LayoutEnd,
5281 CHILD_WeightedHeight,0,
5282 LAYOUT_AddChild, g->shared->objects[GID_TABLAYOUT] = LayoutHObj,
5283 LAYOUT_SpaceInner,FALSE,
5284 addtabclosegadget, g->shared->objects[GID_CLOSETAB],
5285 CHILD_WeightedWidth,0,
5286 CHILD_WeightedHeight,0,
5287
5288 addtabclosegadget, g->shared->objects[GID_TABS],
5289 CHILD_CacheDomain,FALSE,
5290
5291 addtabclosegadget, g->shared->objects[GID_ADDTAB],
5292 CHILD_WeightedWidth,0,
5293 CHILD_WeightedHeight,0,
5294 LayoutEnd,
5295 CHILD_WeightedHeight,0,
5296 LAYOUT_AddChild, LayoutVObj,
5297 LAYOUT_AddChild, g->shared->objects[GID_VSCROLLLAYOUT] = LayoutHObj,
5298 LAYOUT_AddChild, LayoutVObj,
5299 LAYOUT_AddChild, g->shared->objects[GID_HSCROLLLAYOUT] = LayoutVObj,
5300 LAYOUT_AddChild, g->shared->objects[GID_BROWSER] = SpaceObj,
5301 GA_ID,GID_BROWSER,
5302 SPACE_Transparent,TRUE,
5303 SPACE_RenderHook, &g->shared->browser_hook,
5304 SpaceEnd,
5305 EndGroup,
5306 EndGroup,
5307 EndGroup,
5308// LAYOUT_WeightBar, TRUE,
5309 LAYOUT_AddChild, g->shared->objects[GID_LOGLAYOUT] = LayoutVObj,
5310 EndGroup,
5311 CHILD_WeightedHeight, 0,
5312#ifndef __amigaos4__
5313 LAYOUT_AddChild, g->shared->objects[GID_STATUS] = StringObj,
5314 GA_ID, GID_STATUS,
5315 GA_ReadOnly, TRUE,
5316 STRINGA_TextVal, NULL,
5317 GA_RelVerify, TRUE,
5318 StringEnd,
5319#endif
5320 EndGroup,
5321 EndGroup,
5322 EndWindow;
5323 }
5324 else
5325 {
5326 /* borderless kiosk mode window */
5327 g->tab = 0;
5328 g->shared->tabs = 0;
5329 g->tab_node = NULL;
5330
5332 WA_ScreenTitle, ami_gui_get_screen_title(),
5333 WA_Activate, TRUE,
5334 WA_DepthGadget, FALSE,
5335 WA_DragBar, FALSE,
5336 WA_CloseGadget, FALSE,
5337 WA_Borderless,TRUE,
5338 WA_RMBTrap,TRUE,
5339 WA_Top,0,
5340 WA_Left,0,
5341 WA_Width, scrn->Width,
5342 WA_Height, scrn->Height,
5343 WA_SizeGadget, FALSE,
5344 WA_PubScreen, scrn,
5345 WA_ReportMouse, TRUE,
5346 refresh_mode, TRUE,
5347 WA_IDCMP, IDCMP_MENUPICK | IDCMP_MOUSEMOVE |
5348 IDCMP_MOUSEBUTTONS | IDCMP_NEWSIZE |
5349 IDCMP_RAWKEY | IDCMP_REFRESHWINDOW |
5350 IDCMP_GADGETUP | IDCMP_IDCMPUPDATE |
5352 WINDOW_IDCMPHook,&g->shared->scrollerhook,
5353 WINDOW_IDCMPHookBits, IDCMP_IDCMPUPDATE |
5354 IDCMP_EXTENDEDMOUSE | IDCMP_REFRESHWINDOW,
5355 WINDOW_SharedPort,sport,
5356 WINDOW_UserData,g->shared,
5358 WINDOW_ParentGroup, g->shared->objects[GID_MAIN] = LayoutHObj,
5359 LAYOUT_DeferLayout, defer_layout,
5360 LAYOUT_SpaceOuter, TRUE,
5361 LAYOUT_AddChild, g->shared->objects[GID_VSCROLLLAYOUT] = LayoutHObj,
5362 LAYOUT_AddChild, g->shared->objects[GID_HSCROLLLAYOUT] = LayoutVObj,
5363 LAYOUT_AddChild, g->shared->objects[GID_BROWSER] = SpaceObj,
5364 GA_ID,GID_BROWSER,
5365 SPACE_Transparent,TRUE,
5366 SpaceEnd,
5367 EndGroup,
5368 EndGroup,
5369 EndGroup,
5370 EndWindow;
5371 }
5372
5373 NSLOG(netsurf, INFO, "Opening window");
5374
5375 g->shared->win = (struct Window *)RA_OpenWindow(g->shared->objects[OID_MAIN]);
5376
5377 NSLOG(netsurf, INFO, "Window opened, adding border gadgets");
5378
5379 if(!g->shared->win)
5380 {
5381 amiga_warn_user("NoMemory","");
5382 free(g->shared);
5383 free(g);
5384 return NULL;
5385 }
5386
5387 if(nsoption_bool(kiosk_mode) == false)
5388 {
5389#ifdef __amigaos4__
5390 ULONG width, height;
5391 struct DrawInfo *dri = GetScreenDrawInfo(scrn);
5392
5393 ami_get_border_gadget_size(g->shared,
5394 (ULONG *)&width, (ULONG *)&height);
5395
5397 NULL,
5398 "frbuttonclass",
5399 GA_ID, GID_STATUS,
5400 GA_Left, scrn->WBorLeft + 2,
5401 GA_RelBottom, scrn->WBorBottom - (height/2),
5402 GA_BottomBorder, TRUE,
5403 GA_Width, width,
5404 GA_Height, 1 + height - scrn->WBorBottom,
5405 GA_DrawInfo, dri,
5406 GA_ReadOnly, TRUE,
5407 GA_Disabled, TRUE,
5408 GA_Image, (struct Image *)NewObject(
5409 NULL,
5410 "gaugeiclass",
5411 GAUGEIA_Level, 0,
5412 IA_Top, (int)(- ceil((scrn->WBorBottom + height) / 2)),
5413 IA_Left, -4,
5414 IA_Height, 2 + height - scrn->WBorBottom,
5415 IA_Label, NULL,
5416 IA_InBorder, TRUE,
5417 IA_Screen, scrn,
5418 TAG_DONE),
5419 TAG_DONE);
5420
5421 AddGList(g->shared->win, (struct Gadget *)g->shared->objects[GID_STATUS],
5422 (UWORD)~0, -1, NULL);
5423
5424 /* Apparently you can't set GA_Width on creation time for frbuttonclass */
5425
5426 SetGadgetAttrs((struct Gadget *)g->shared->objects[GID_STATUS],
5427 g->shared->win, NULL,
5428 GA_Width, width,
5429 TAG_DONE);
5430
5431 RefreshGadgets((APTR)g->shared->objects[GID_STATUS],
5432 g->shared->win, NULL);
5433
5434 FreeScreenDrawInfo(scrn, dri);
5435#endif //__amigaos4__
5436 ami_gui_hotlist_toolbar_add(g->shared); /* is this the right place for this? */
5437 if(nsoption_bool(tab_always_show)) ami_toggletabbar(g->shared, true);
5438 }
5439
5440 g->shared->gw = g;
5441 cur_gw = g;
5442
5443 g->shared->appwin = AddAppWindowA((ULONG)g->shared->objects[OID_MAIN],
5444 (ULONG)g->shared, g->shared->win, appport, NULL);
5445
5447
5448 if(locked_screen) {
5449 UnlockPubScreen(NULL,scrn);
5450 locked_screen = FALSE;
5451 }
5452
5453 ScreenToFront(scrn);
5454
5455 return g;
5456}
5457
5458static void ami_gui_close_tabs(struct gui_window_2 *gwin, bool other_tabs)
5459{
5460 struct Node *tab;
5461 struct Node *ntab;
5462 struct gui_window *gw;
5463
5464 if((gwin->tabs > 1) && (nsoption_bool(tab_close_warn) == true)) {
5465 int32 res = amiga_warn_user_multi(messages_get("MultiTabClose"), "Yes", "No", gwin->win);
5466
5467 if(res == 0) return;
5468 }
5469
5470 if(gwin->tabs) {
5471 tab = GetHead(&gwin->tab_list);
5472
5473 do {
5474 ntab=GetSucc(tab);
5475 GetClickTabNodeAttrs(tab,
5476 TNA_UserData,&gw,
5477 TAG_DONE);
5478
5479 if((other_tabs == false) || (gwin->gw != gw)) {
5481 }
5482 } while((tab=ntab));
5483 } else {
5484 if(other_tabs == false) browser_window_destroy(gwin->gw->bw);
5485 }
5486}
5487
5489{
5490 struct gui_window_2 *gwin = (struct gui_window_2 *)w;
5491 ami_gui_close_tabs(gwin, false);
5492}
5493
5495{
5496 ami_gui_close_tabs(gwin, true);
5497}
5498
5499static void gui_window_destroy(struct gui_window *g)
5500{
5501 struct Node *ptab = NULL;
5502 int gid;
5503
5504 if(!g) return;
5505
5506 if (ami_search_get_gwin(g->shared->searchwin) == g)
5507 {
5509 win_destroyed = true;
5510 }
5511
5512 if(g->hw)
5513 {
5515 win_destroyed = true;
5516 }
5517
5522
5523 cur_gw = NULL;
5524
5525 if(g->shared->tabs > 1) {
5526 SetGadgetAttrs((struct Gadget *)g->shared->objects[GID_TABS],g->shared->win,NULL,
5527 CLICKTAB_Labels,~0,
5528 TAG_DONE);
5529
5530 GetAttr(CLICKTAB_CurrentNode, g->shared->objects[GID_TABS], (ULONG *)&ptab);
5531
5532 if(ptab == g->tab_node) {
5533 ptab = GetSucc(g->tab_node);
5534 if(!ptab) ptab = GetPred(g->tab_node);
5535 }
5536
5537 Remove(g->tab_node);
5538 FreeClickTabNode(g->tab_node);
5539 RefreshSetGadgetAttrs((struct Gadget *)g->shared->objects[GID_TABS], g->shared->win, NULL,
5540 CLICKTAB_Labels, &g->shared->tab_list,
5541 CLICKTAB_CurrentNode, ptab,
5542 TAG_DONE);
5543
5544 if(ClickTabBase->lib_Version < 53)
5545 RethinkLayout((struct Gadget *)g->shared->objects[GID_TABLAYOUT],
5546 g->shared->win, NULL, TRUE);
5547
5548 g->shared->tabs--;
5549 ami_switch_tab(g->shared,true);
5551
5552 if((g->shared->tabs == 1) && (nsoption_bool(tab_always_show) == false))
5553 ami_toggletabbar(g->shared, false);
5554
5555 FreeListBrowserList(&g->loglist);
5556#ifdef __amigaos4__
5557 FreeLBColumnInfo(g->logcolumns);
5558#endif
5559
5560 if(g->tabtitle) free(g->tabtitle);
5561 free(g);
5562 return;
5563 }
5564
5566 free(g->shared->shared_pens);
5569
5570 DisposeObject(g->shared->objects[OID_MAIN]);
5572 if(g->shared->appwin) RemoveAppWindow(g->shared->appwin);
5574
5575 /* These aren't freed by the above.
5576 * TODO: nav_west etc need freeing too? */
5577 DisposeObject(g->shared->objects[GID_ADDTAB_BM]);
5578 DisposeObject(g->shared->objects[GID_CLOSETAB_BM]);
5579 DisposeObject(g->shared->objects[GID_TABS_FLAG]);
5580 DisposeObject(g->shared->objects[GID_FAVE_ADD]);
5581 DisposeObject(g->shared->objects[GID_FAVE_RMV]);
5582 DisposeObject(g->shared->objects[GID_PAGEINFO_INSECURE_BM]);
5583 DisposeObject(g->shared->objects[GID_PAGEINFO_INTERNAL_BM]);
5584 DisposeObject(g->shared->objects[GID_PAGEINFO_LOCAL_BM]);
5585 DisposeObject(g->shared->objects[GID_PAGEINFO_SECURE_BM]);
5586 DisposeObject(g->shared->objects[GID_PAGEINFO_WARNING_BM]);
5587
5589 if(g->shared->search_bm) DisposeObject(g->shared->search_bm);
5590
5591 /* This appears to be disposed along with the ClickTab object
5592 if(g->shared->clicktab_ctxmenu) DisposeObject((Object *)g->shared->clicktab_ctxmenu); */
5593 DisposeObject((Object *)g->shared->history_ctxmenu[AMI_CTXMENU_HISTORY_BACK]);
5594 DisposeObject((Object *)g->shared->history_ctxmenu[AMI_CTXMENU_HISTORY_FORWARD]);
5597
5598 FreeListBrowserList(&g->loglist);
5599#ifdef __amigaos4__
5600 FreeLBColumnInfo(g->logcolumns);
5601#endif
5602
5603 free(g->shared->wintitle);
5605 free(g->shared->svbuffer);
5606
5607 for(gid = 0; gid < GID_LAST; gid++)
5608 ami_utf8_free(g->shared->helphints[gid]);
5609
5611 if(g->tab_node) {
5612 Remove(g->tab_node);
5613 FreeClickTabNode(g->tab_node);
5614 }
5615 if(g->tabtitle) free(g->tabtitle);
5616 free(g); // g->shared should be freed by DelObject()
5617
5619 {
5620 /* last window closed, so exit */
5621 ami_try_quit();
5622 }
5623
5624 win_destroyed = true;
5625}
5626
5627
5628static void ami_redraw_callback(void *p)
5629{
5630 struct gui_window_2 *gwin = (struct gui_window_2 *)p;
5631
5632 if(gwin->redraw_required) {
5633 ami_do_redraw(gwin);
5634 }
5635
5637
5638 if(gwin->gw->c_h)
5639 {
5640 gui_window_place_caret(gwin->gw, gwin->gw->c_x,
5641 gwin->gw->c_y, gwin->gw->c_h, NULL);
5642 }
5643}
5644
5645/**
5646 * Schedule a redraw of the browser window - Amiga-specific function
5647 *
5648 * \param gwin a struct gui_window_2
5649 * \param full_redraw set to true to schedule a full redraw,
5650 should only be set to false when called from amiga_window_invalidate_area()
5651 */
5652void ami_schedule_redraw(struct gui_window_2 *gwin, bool full_redraw)
5653{
5654 int ms = 1;
5655
5656 if(full_redraw) gwin->redraw_required = true;
5658}
5659
5661{
5663}
5664
5665static void ami_gui_window_update_box_deferred(struct gui_window *g, bool draw)
5666{
5667 struct nsObject *node;
5668 struct nsObject *nnode;
5669 struct rect *rect;
5670
5671 if(!g) return;
5672 if(IsMinListEmpty(g->deferred_rects)) return;
5673
5674 if(draw == true) {
5676 } else {
5677 NSLOG(netsurf, INFO, "Ignoring deferred box redraw queue");
5678 }
5679
5680 node = (struct nsObject *)GetHead((struct List *)g->deferred_rects);
5681
5682 do {
5683 if(draw == true) {
5684 rect = (struct rect *)node->objstruct;
5685 ami_do_redraw_limits(g, g->bw, false,
5686 rect->x0, rect->y0, rect->x1, rect->y1);
5687 }
5688 nnode=(struct nsObject *)GetSucc((struct Node *)node);
5690 DelObjectNoFree(node);
5691 } while((node = nnode));
5692
5693 if(draw == true) ami_reset_pointer(g->shared);
5694}
5695
5696bool ami_gui_window_update_box_deferred_check(struct MinList *deferred_rects,
5697 const struct rect *restrict new_rect, APTR mempool)
5698{
5699 struct nsObject *node;
5700 struct nsObject *nnode;
5701 struct rect *restrict rect;
5702
5703 if(IsMinListEmpty(deferred_rects)) return true;
5704
5705 node = (struct nsObject *)GetHead((struct List *)deferred_rects);
5706
5707 do {
5708 nnode=(struct nsObject *)GetSucc((struct Node *)node);
5709 rect = (struct rect *)node->objstruct;
5710
5711 if((rect->x0 <= new_rect->x0) &&
5712 (rect->y0 <= new_rect->y0) &&
5713 (rect->x1 >= new_rect->x1) &&
5714 (rect->y1 >= new_rect->y1)) {
5715 return false;
5716 }
5717
5718 if ((new_rect->x0 <= rect->x0) &&
5719 (new_rect->y0 <= rect->y0) &&
5720 (new_rect->x1 >= rect->x1) &&
5721 (new_rect->y1 >= rect->y1)) {
5722 NSLOG(netsurf, INFO,
5723 "Removing queued redraw that is a subset of new box redraw");
5724 ami_memory_itempool_free(mempool, node->objstruct, sizeof(struct rect));
5725 DelObjectNoFree(node);
5726 /* Don't return - we might find more */
5727 }
5728 } while((node = nnode));
5729
5730 return true;
5731}
5732
5733
5734static void ami_do_redraw(struct gui_window_2 *gwin)
5735{
5736 ULONG hcurrent,vcurrent,xoffset,yoffset,width=800,height=600;
5737 struct IBox *bbox;
5738 ULONG oldh = gwin->oldh, oldv=gwin->oldv;
5739
5740 if(browser_window_redraw_ready(gwin->gw->bw) == false) return;
5741
5742 ami_get_hscroll_pos(gwin, (ULONG *)&hcurrent);
5743 ami_get_vscroll_pos(gwin, (ULONG *)&vcurrent);
5744
5745 gwin->gw->scrollx = hcurrent;
5746 gwin->gw->scrolly = vcurrent;
5747
5748 if(ami_gui_get_space_box((Object *)gwin->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
5749 amiga_warn_user("NoMemory", "");
5750 return;
5751 }
5752
5753 width=bbox->Width;
5754 height=bbox->Height;
5755 xoffset=bbox->Left;
5756 yoffset=bbox->Top;
5757
5758 if(gwin->redraw_scroll)
5759 {
5760 if((abs(vcurrent-oldv) > height) || (abs(hcurrent-oldh) > width))
5761 gwin->redraw_scroll = false;
5762
5763 if(gwin->new_content) gwin->redraw_scroll = false;
5764 }
5765
5766 if(gwin->redraw_scroll)
5767 {
5768 struct rect rect;
5769
5770 gwin->gw->c_h_temp = gwin->gw->c_h;
5772
5773 ScrollWindowRaster(gwin->win, hcurrent - oldh, vcurrent - oldv,
5774 xoffset, yoffset, xoffset + width - 1, yoffset + height - 1);
5775
5776 gwin->gw->c_h = gwin->gw->c_h_temp;
5777
5778 if(vcurrent>oldv) /* Going down */
5779 {
5780 ami_spacebox_to_ns_coords(gwin, &rect.x0, &rect.y0, 0, height - (vcurrent - oldv) - 1);
5781 ami_spacebox_to_ns_coords(gwin, &rect.x1, &rect.y1, width + 1, height + 1);
5783 }
5784 else if(vcurrent<oldv) /* Going up */
5785 {
5786 ami_spacebox_to_ns_coords(gwin, &rect.x0, &rect.y0, 0, 0);
5787 ami_spacebox_to_ns_coords(gwin, &rect.x1, &rect.y1, width + 1, oldv - vcurrent + 1);
5789 }
5790
5791 if(hcurrent>oldh) /* Going right */
5792 {
5793 ami_spacebox_to_ns_coords(gwin, &rect.x0, &rect.y0, width - (hcurrent - oldh), 0);
5794 ami_spacebox_to_ns_coords(gwin, &rect.x1, &rect.y1, width + 1, height + 1);
5796 }
5797 else if(hcurrent<oldh) /* Going left */
5798 {
5799 ami_spacebox_to_ns_coords(gwin, &rect.x0, &rect.y0, 0, 0);
5800 ami_spacebox_to_ns_coords(gwin, &rect.x1, &rect.y1, oldh - hcurrent + 1, height + 1);
5802 }
5803 }
5804 else
5805 {
5806 struct redraw_context ctx = {
5807 .interactive = true,
5808 .background_images = true,
5809 .plot = &amiplot,
5810 .priv = browserglob
5811 };
5812
5813 ami_do_redraw_tiled(gwin, true, hcurrent, vcurrent, width, height, hcurrent, vcurrent, bbox, &ctx);
5814
5815 /* Tell NetSurf not to bother with the next queued box redraw, as we've redrawn everything. */
5817 }
5818
5819 ami_update_buttons(gwin);
5820
5821 gwin->oldh = hcurrent;
5822 gwin->oldv = vcurrent;
5823
5824 gwin->redraw_scroll = false;
5825 gwin->redraw_required = false;
5826 gwin->new_content = false;
5827
5829}
5830
5831
5832static void ami_get_hscroll_pos(struct gui_window_2 *gwin, ULONG *xs)
5833{
5834 if(gwin->objects[GID_HSCROLL])
5835 {
5836 GetAttr(SCROLLER_Top, (Object *)gwin->objects[GID_HSCROLL], xs);
5837 } else {
5838 *xs = 0;
5839 }
5840}
5841
5842static void ami_get_vscroll_pos(struct gui_window_2 *gwin, ULONG *ys)
5843{
5844 if(gwin->objects[GID_VSCROLL]) {
5845 GetAttr(SCROLLER_Top, gwin->objects[GID_VSCROLL], ys);
5846 } else {
5847 *ys = 0;
5848 }
5849}
5850
5851static bool gui_window_get_scroll(struct gui_window *g, int *restrict sx, int *restrict sy)
5852{
5853 ami_get_hscroll_pos(g->shared, (ULONG *)sx);
5854 ami_get_vscroll_pos(g->shared, (ULONG *)sy);
5855
5856 return true;
5857}
5858
5859/**
5860 * Set the scroll position of a amiga browser window.
5861 *
5862 * Scrolls the viewport to ensure the specified rectangle of the
5863 * content is shown. The amiga implementation scrolls the contents so
5864 * the specified point in the content is at the top of the viewport.
5865 *
5866 * \param g gui_window to scroll
5867 * \param rect The rectangle to ensure is shown.
5868 * \return NSERROR_OK on success or apropriate error code.
5869 */
5870static nserror
5872{
5873 struct IBox *bbox;
5874 int width, height;
5875 nserror res;
5876 int sx = 0, sy = 0;
5877
5878 if(!g) {
5879 return NSERROR_BAD_PARAMETER;
5880 }
5881 if(!g->bw || browser_window_has_content(g->bw) == false) {
5882 return NSERROR_BAD_PARAMETER;
5883 }
5884
5885 res = ami_gui_get_space_box((Object *)g->shared->objects[GID_BROWSER], &bbox);
5886 if(res != NSERROR_OK) {
5887 amiga_warn_user("NoMemory", "");
5888 return res;
5889 }
5890
5891 if (rect->x0 > 0) {
5892 sx = rect->x0;
5893 }
5894 if (rect->y0 > 0) {
5895 sy = rect->y0;
5896 }
5897
5899
5900 if(sx >= width - bbox->Width)
5901 sx = width - bbox->Width;
5902 if(sy >= height - bbox->Height)
5903 sy = height - bbox->Height;
5904
5905 if(width <= bbox->Width) sx = 0;
5906 if(height <= bbox->Height) sy = 0;
5907
5909
5910 if(g == g->shared->gw) {
5911 if(g->shared->objects[GID_VSCROLL]) {
5912 RefreshSetGadgetAttrs((struct Gadget *)(APTR)g->shared->objects[GID_VSCROLL],
5913 g->shared->win, NULL,
5914 SCROLLER_Top, (ULONG)(sy),
5915 TAG_DONE);
5916 }
5917
5918 if(g->shared->objects[GID_HSCROLL])
5919 {
5920 RefreshSetGadgetAttrs((struct Gadget *)(APTR)g->shared->objects[GID_HSCROLL],
5921 g->shared->win, NULL,
5922 SCROLLER_Top, (ULONG)(sx),
5923 TAG_DONE);
5924 }
5925
5926 ami_schedule_redraw(g->shared, true);
5927
5928 if(nsoption_bool(faster_scroll) == true) g->shared->redraw_scroll = true;
5929 else g->shared->redraw_scroll = false;
5930
5931 g->scrollx = sx;
5932 g->scrolly = sy;
5933 }
5934 return NSERROR_OK;
5935}
5936
5937static void gui_window_set_status(struct gui_window *g, const char *text)
5938{
5939 char *utf8text;
5940 ULONG size;
5941 UWORD chars;
5942 struct TextExtent textex;
5943
5944 if(!g) return;
5945 if(!text) return;
5946 if(!g->shared->objects[GID_STATUS]) return;
5947
5948 if(g == g->shared->gw) {
5949 utf8text = ami_utf8_easy((char *)text);
5950 if(utf8text == NULL) return;
5951
5952 GetAttr(GA_Width, g->shared->objects[GID_STATUS], (ULONG *)&size);
5953 chars = TextFit(&scrn->RastPort, utf8text, (UWORD)strlen(utf8text),
5954 &textex, NULL, 1, size - 4, scrn->RastPort.TxHeight);
5955
5956 utf8text[chars] = 0;
5957
5958 SetGadgetAttrs((struct Gadget *)g->shared->objects[GID_STATUS],
5959 g->shared->win, NULL,
5960 NSA_STATUS_TEXT, utf8text,
5961 TAG_DONE);
5962
5963 RefreshGList((struct Gadget *)g->shared->objects[GID_STATUS],
5964 g->shared->win, NULL, 1);
5965
5967 g->shared->status = utf8text;
5968 }
5969}
5970
5972{
5973 size_t idn_url_l;
5974 char *idn_url_s = NULL;
5975 char *url_lc = NULL;
5976
5977 if(!g) return NSERROR_OK;
5978
5979 if(g == g->shared->gw) {
5980 if(nsoption_bool(display_decoded_idn) == true) {
5981 if (nsurl_get_utf8(url, &idn_url_s, &idn_url_l) == NSERROR_OK) {
5982 url_lc = ami_utf8_easy(idn_url_s);
5983 }
5984 }
5985
5986 RefreshSetGadgetAttrs((struct Gadget *)g->shared->objects[GID_URL],
5987 g->shared->win, NULL,
5988 STRINGA_TextVal, url_lc ? url_lc : nsurl_access(url),
5989 TAG_DONE);
5990
5991 if(url_lc) {
5992 ami_utf8_free(url_lc);
5993 if(idn_url_s) free(idn_url_s);
5994 }
5995 }
5996
5998
5999 return NSERROR_OK;
6000}
6001
6002HOOKF(uint32, ami_set_favicon_render_hook, APTR, space, struct gpRender *)
6003{
6004 ami_schedule(0, ami_gui_refresh_favicon, hook->h_Data);
6005 return 0;
6006}
6007
6008/**
6009 * Gui callback when search provider details are updated.
6010 *
6011 * \param provider_name The providers name.
6012 * \param ico_bitmap The icon bitmap representing the provider.
6013 * \return NSERROR_OK on success else error code.
6014 */
6015static nserror gui_search_web_provider_update(const char *provider_name,
6016 struct bitmap *ico_bitmap)
6017{
6018 struct BitMap *bm = NULL;
6019 struct nsObject *node;
6020 struct nsObject *nnode;
6021 struct gui_window_2 *gwin;
6022
6024 if(nsoption_bool(kiosk_mode) == true) return NSERROR_BAD_PARAMETER;
6025
6026 if (ico_bitmap != NULL) {
6027 bm = ami_bitmap_get_native(ico_bitmap, 16, 16, ami_plot_screen_is_palettemapped(), NULL);
6028 }
6029
6030 if(bm == NULL) return NSERROR_BAD_PARAMETER;
6031
6032 node = (struct nsObject *)GetHead((struct List *)window_list);
6033
6034 do {
6035 nnode=(struct nsObject *)GetSucc((struct Node *)node);
6036 gwin = node->objstruct;
6037
6038 if(node->Type == AMINS_WINDOW)
6039 {
6040 if(gwin->search_bm != NULL)
6041 DisposeObject(gwin->search_bm);
6042
6043 ULONG bm_masking_tag = TAG_IGNORE;
6044
6045 if(LIB_IS_AT_LEAST((struct Library *)ChooserBase, 53, 21)) {
6046 /* Broken in earlier versions */
6047 bm_masking_tag = BITMAP_Masking;
6048 }
6049
6050 gwin->search_bm = BitMapObj,
6051 BITMAP_Screen, scrn,
6052 BITMAP_Width, 16,
6053 BITMAP_Height, 16,
6054 BITMAP_BitMap, bm,
6055 BITMAP_HasAlpha, TRUE,
6056 bm_masking_tag, TRUE,
6057 BitMapEnd;
6058
6059 RefreshSetGadgetAttrs((struct Gadget *)gwin->objects[GID_SEARCH_ICON],
6060 gwin->win, NULL,
6061 GA_HintInfo, provider_name,
6062 GA_Image, gwin->search_bm,
6063 TAG_DONE);
6064 }
6065 } while((node = nnode));
6066
6067 return NSERROR_OK;
6068}
6069
6070HOOKF(uint32, ami_set_throbber_render_hook, APTR, space, struct gpRender *)
6071{
6072 struct gui_window_2 *gwin = hook->h_Data;
6074 return 0;
6075}
6076
6077HOOKF(uint32, ami_gui_browser_render_hook, APTR, space, struct gpRender *)
6078{
6079 struct gui_window_2 *gwin = hook->h_Data;
6080
6081 NSLOG(netsurf, DEBUG, "Render hook called with %ld (REDRAW=1)", msg->gpr_Redraw);
6082
6083 if(msg->gpr_Redraw != GREDRAW_REDRAW) return 0;
6084
6085 ami_schedule_redraw(gwin, true);
6086
6087 return 0;
6088}
6089
6090static void gui_window_place_caret(struct gui_window *g, int x, int y, int height,
6091 const struct rect *clip)
6092{
6093 struct IBox *bbox;
6094 int xs,ys;
6095
6096 if(!g) return;
6097
6099
6100 xs = g->scrollx;
6101 ys = g->scrolly;
6102
6103 SetAPen(g->shared->win->RPort,3);
6104
6105 if(ami_gui_get_space_box((Object *)g->shared->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
6106 amiga_warn_user("NoMemory", "");
6107 return;
6108 }
6109
6110 if((y-ys+height) > (bbox->Height)) height = bbox->Height-y+ys;
6111
6112 if(((x-xs) <= 0) || ((x-xs+2) >= (bbox->Width)) || ((y-ys) <= 0) || ((y-ys) >= (bbox->Height))) {
6114 return;
6115 }
6116
6117 g->c_w = 2;
6118
6119 SetDrMd(g->shared->win->RPort,COMPLEMENT);
6120 RectFill(g->shared->win->RPort, x + bbox->Left - xs, y + bbox->Top - ys,
6121 x + bbox->Left + g->c_w - xs, y+bbox->Top + height - ys);
6122 SetDrMd(g->shared->win->RPort,JAM1);
6123
6125
6126 g->c_x = x;
6127 g->c_y = y;
6128 g->c_h = height;
6129
6130 if((nsoption_bool(kiosk_mode) == false))
6132}
6133
6135{
6136 if(!g) return;
6137 if(g->c_h == 0) return;
6138
6139 if((nsoption_bool(kiosk_mode) == false))
6141
6142 ami_do_redraw_limits(g, g->bw, false, g->c_x, g->c_y,
6143 g->c_x + g->c_w + 1, g->c_y + g->c_h + 1);
6144
6145 g->c_h = 0;
6146}
6147
6149{
6150 struct hlcache_handle *c;
6151
6152 if(g && g->shared && g->bw && browser_window_has_content(g->bw))
6154 else return;
6155
6157 g->shared->new_content = true;
6158 g->scrollx = 0;
6159 g->scrolly = 0;
6160 g->shared->oldh = 0;
6161 g->shared->oldv = 0;
6162 g->favicon = NULL;
6167}
6168
6170 const struct rect *rect)
6171{
6172#ifdef __amigaos4__
6173 g->shared->drag_op = type;
6175
6176 if(type == GDRAGGING_NONE)
6177 {
6178 SetWindowAttrs(g->shared->win, WA_GrabFocus, 0,
6179 WA_MouseLimits, NULL, TAG_DONE);
6180
6181 if(g->shared->ptr_lock)
6182 {
6183 free(g->shared->ptr_lock);
6184 g->shared->ptr_lock = NULL;
6185 }
6186 }
6187#endif
6188 return true;
6189}
6190
6191/* return the text box at posn x,y in window coordinates
6192 x,y are updated to be document co-ordinates */
6193
6194bool ami_text_box_at_point(struct gui_window_2 *gwin, ULONG *restrict x, ULONG *restrict y)
6195{
6196 struct IBox *bbox;
6197 ULONG xs, ys;
6198 struct browser_window_features data;
6199
6200 if(ami_gui_get_space_box((Object *)gwin->objects[GID_BROWSER], &bbox) != NSERROR_OK) {
6201 amiga_warn_user("NoMemory", "");
6202 return false;
6203 }
6204
6205 ami_get_hscroll_pos(gwin, (ULONG *)&xs);
6206 *x = *x - (bbox->Left) +xs;
6207
6208 ami_get_vscroll_pos(gwin, (ULONG *)&ys);
6209 *y = *y - (bbox->Top) + ys;
6210
6212
6213 browser_window_get_features(gwin->gw->bw, *x, *y, &data);
6214
6215 if (data.form_features == CTX_FORM_TEXT)
6216 return true;
6217
6218 return false;
6219}
6220
6221BOOL ami_gadget_hit(Object *obj, int x, int y)
6222{
6223 int top, left, width, height;
6224
6225 GetAttrs(obj,
6226 GA_Left, &left,
6227 GA_Top, &top,
6228 GA_Width, &width,
6229 GA_Height, &height,
6230 TAG_DONE);
6231
6232 if((x >= left) && (x <= (left + width)) && (y >= top) && (y <= (top + height)))
6233 return TRUE;
6234 else return FALSE;
6235}
6236
6237static Object *ami_gui_splash_open(void)
6238{
6239 Object *restrict win_obj, *restrict bm_obj;
6240 struct Window *win;
6241 struct Screen *wbscreen = LockPubScreen("Workbench");
6242 uint32 top = 0, left = 0;
6243 struct TextAttr tattr;
6244 struct TextFont *tfont;
6245
6246 win_obj = WindowObj,
6247#ifdef __amigaos4__
6248 WA_ToolBox, TRUE,
6249#endif
6250 WA_Borderless, TRUE,
6251 WA_BusyPointer, TRUE,
6252 WINDOW_Position, WPOS_CENTERSCREEN,
6253 WINDOW_LockWidth, TRUE,
6254 WINDOW_LockHeight, TRUE,
6255 WINDOW_ParentGroup, LayoutVObj,
6256 LAYOUT_AddImage, bm_obj = BitMapObj,
6257 BITMAP_SourceFile, "PROGDIR:Resources/splash.png",
6258 BITMAP_Screen, wbscreen,
6259 BITMAP_Precision, PRECISION_IMAGE,
6260 BitMapEnd,
6261 LayoutEnd,
6262 EndWindow;
6263
6264 if(win_obj == NULL) {
6265 NSLOG(netsurf, INFO, "Splash window object not created");
6266 return NULL;
6267 }
6268
6269 NSLOG(netsurf, INFO, "Attempting to open splash window...");
6270 win = RA_OpenWindow(win_obj);
6271
6272 if(win == NULL) {
6273 NSLOG(netsurf, INFO, "Splash window did not open");
6274 return NULL;
6275 }
6276
6277 if(bm_obj == NULL) {
6278 NSLOG(netsurf, INFO, "BitMap object not created");
6279 return NULL;
6280 }
6281
6282 GetAttrs(bm_obj, IA_Top, &top,
6283 IA_Left, &left,
6284 TAG_DONE);
6285
6286 SetDrMd(win->RPort, JAM1);
6287#ifdef __amigaos4__
6288 SetRPAttrs(win->RPort, RPTAG_APenColor, 0xFF3F6DFE, TAG_DONE);
6289 tattr.ta_Name = "DejaVu Serif Italic.font";
6290#else
6291 SetAPen(win->RPort, 3); /* Pen 3 is usually blue */
6292 tattr.ta_Name = "ruby.font";
6293#endif
6294 tattr.ta_YSize = 24;
6295 tattr.ta_Style = 0;
6296 tattr.ta_Flags = 0;
6297
6298 if((tfont = ami_font_open_disk_font(&tattr)))
6299 {
6300 SetFont(win->RPort, tfont);
6301 }
6302 else
6303 {
6304 tattr.ta_Name = "DejaVu Serif Oblique.font";
6305 if((tfont = ami_font_open_disk_font(&tattr)))
6306 SetFont(win->RPort, tfont);
6307 }
6308
6309 Move(win->RPort, left + 5, top + 25);
6310 Text(win->RPort, "Initialising...", strlen("Initialising..."));
6311
6312 if(tfont) ami_font_close_disk_font(tfont);
6313
6314#ifdef __amigaos4__
6315 tattr.ta_Name = "DejaVu Sans.font";
6316#else
6317 tattr.ta_Name = "helvetica.font";
6318#endif
6319 tattr.ta_YSize = 16;
6320 tattr.ta_Style = 0;
6321 tattr.ta_Flags = 0;
6322
6323 if((tfont = ami_font_open_disk_font(&tattr)))
6324 SetFont(win->RPort, tfont);
6325
6326 Move(win->RPort, left + 185, top + 220);
6327 Text(win->RPort, netsurf_version, strlen(netsurf_version));
6328
6329 if(tfont) ami_font_close_disk_font(tfont);
6330
6331 UnlockPubScreen(NULL, wbscreen);
6332
6333 return win_obj;
6334}
6335
6336static void ami_gui_splash_close(Object *win_obj)
6337{
6338 if(win_obj == NULL) return;
6339
6340 NSLOG(netsurf, INFO, "Closing splash window");
6341 DisposeObject(win_obj);
6342}
6343
6344static void gui_file_gadget_open(struct gui_window *g, struct hlcache_handle *hl,
6345 struct form_control *gadget)
6346{
6347 NSLOG(netsurf, INFO, "File open dialog request for %p/%p", g, gadget);
6348
6349 if(AslRequestTags(filereq,
6350 ASLFR_Window, g->shared->win,
6351 ASLFR_SleepWindow, TRUE,
6352 ASLFR_TitleText, messages_get("NetSurf"),
6353 ASLFR_Screen, scrn,
6354 ASLFR_DoSaveMode, FALSE,
6355 TAG_DONE)) {
6356 char fname[1024];
6357 strlcpy(fname, filereq->fr_Drawer, 1024);
6358 AddPart(fname, filereq->fr_File, 1024);
6359 browser_window_set_gadget_filename(g->bw, gadget, fname);
6360 }
6361}
6362
6363/* exported function documented in amiga/gui.h */
6365{
6366 return ami_appid;
6367}
6368
6369/* Get current user directory for user-specific NetSurf data
6370 * Returns NULL on error
6371 */
6372static char *ami_gui_get_user_dir(STRPTR current_user)
6373{
6374 BPTR lock = 0;
6375 char temp[1024];
6376 int32 user = 0;
6377
6378 if(current_user == NULL) {
6379 user = GetVar("user", temp, 1024, GVF_GLOBAL_ONLY);
6380 current_user = ASPrintf("%s", (user == -1) ? "Default" : temp);
6381 }
6382 NSLOG(netsurf, INFO, "User: %s", current_user);
6383
6384 if(users_dir == NULL) {
6385 users_dir = ASPrintf("%s", USERS_DIR);
6386 if(users_dir == NULL) {
6387 ami_misc_fatal_error("Failed to allocate memory");
6388 FreeVec(current_user);
6389 return NULL;
6390 }
6391 }
6392
6393 if(LIB_IS_AT_LEAST((struct Library *)DOSBase, 51, 96)) {
6394#ifdef __amigaos4__
6395 struct InfoData *infodata = AllocDosObject(DOS_INFODATA, 0);
6396 if(infodata == NULL) {
6397 ami_misc_fatal_error("Failed to allocate memory");
6398 FreeVec(current_user);
6399 return NULL;
6400 }
6401 GetDiskInfoTags(GDI_StringNameInput, users_dir,
6402 GDI_InfoData, infodata,
6403 TAG_DONE);
6404 if(infodata->id_DiskState == ID_DISKSTATE_WRITE_PROTECTED) {
6405 FreeDosObject(DOS_INFODATA, infodata);
6406 ami_misc_fatal_error("User directory MUST be on a writeable volume");
6407 FreeVec(current_user);
6408 return NULL;
6409 }
6410 FreeDosObject(DOS_INFODATA, infodata);
6411#else
6412#warning FIXME for OS3 and older OS4
6413#endif
6414 } else {
6415//TODO: check volume write status using old API
6416 }
6417
6418 int len = strlen(current_user);
6419 len += strlen(users_dir);
6420 len += 2; /* for poss path sep and NULL term */
6421
6422 current_user_dir = malloc(len);
6423 if(current_user_dir == NULL) {
6424 ami_misc_fatal_error("Failed to allocate memory");
6425 FreeVec(current_user);
6426 return NULL;
6427 }
6428
6429 strlcpy(current_user_dir, users_dir, len);
6430 AddPart(current_user_dir, current_user, len);
6431 FreeVec(users_dir);
6432 FreeVec(current_user);
6433
6434 NSLOG(netsurf, INFO, "User dir: %s", current_user_dir);
6435
6436 if((lock = CreateDirTree(current_user_dir)))
6437 UnLock(lock);
6438
6440
6442 if((lock = CreateDirTree(current_user_faviconcache))) UnLock(lock);
6443
6444 return current_user_dir;
6445}
6446
6447
6448/**
6449 * process miscellaneous window events
6450 *
6451 * \param gw The window receiving the event.
6452 * \param event The event code.
6453 * \return NSERROR_OK when processed ok
6454 */
6455static nserror
6457{
6458 switch (event) {
6461 break;
6462
6465 break;
6466
6469 break;
6470
6473 break;
6474
6477 break;
6478
6481 break;
6482
6485 break;
6486
6487 default:
6488 break;
6489 }
6490 return NSERROR_OK;
6491}
6492
6493
6496 .destroy = gui_window_destroy,
6497 .invalidate = amiga_window_invalidate_area,
6498 .get_scroll = gui_window_get_scroll,
6499 .set_scroll = gui_window_set_scroll,
6500 .get_dimensions = gui_window_get_dimensions,
6501 .event = gui_window_event,
6502
6503 .set_icon = gui_window_set_icon,
6504 .set_title = gui_window_set_title,
6505 .set_url = gui_window_set_url,
6506 .set_status = gui_window_set_status,
6507 .place_caret = gui_window_place_caret,
6508 .drag_start = gui_window_drag_start,
6509 .create_form_select_menu = gui_create_form_select_menu,
6510 .file_gadget_open = gui_file_gadget_open,
6511 .drag_save_object = gui_drag_save_object,
6512 .drag_save_selection = gui_drag_save_selection,
6513
6514 .console_log = gui_window_console_log,
6515
6516 /* from theme */
6517 .set_pointer = gui_window_set_pointer,
6518
6519 /* from download */
6520 .save_link = gui_window_save_link,
6521};
6522
6523
6526
6527 .get_resource_url = gui_get_resource_url,
6528};
6529
6532};
6533
6536
6537 .quit = gui_quit,
6538 .launch_url = gui_launch_url,
6539 .present_cookies = ami_cookies_present,
6540};
6541
6542/** Normal entry point from OS */
6543int main(int argc, char** argv)
6544{
6545 setbuf(stderr, NULL);
6546 char messages[100];
6547 char script[1024];
6548 char temp[1024];
6549 STRPTR current_user_cache = NULL;
6550 STRPTR current_user = NULL;
6551 BPTR lock = 0;
6552 nserror ret;
6553 int nargc = 0;
6554 char *nargv = NULL;
6555
6556 struct netsurf_table amiga_table = {
6558 .window = &amiga_window_table,
6559 .corewindow = amiga_core_window_table,
6560 .clipboard = amiga_clipboard_table,
6561 .download = amiga_download_table,
6562 .fetch = &amiga_fetch_table,
6563 .file = amiga_file_table,
6564 .utf8 = amiga_utf8_table,
6565 .search = amiga_search_table,
6566 .search_web = &amiga_search_web_table,
6567 .llcache = filesystem_llcache_table,
6568 .bitmap = amiga_bitmap_table,
6569 .layout = ami_layout_table,
6570 };
6571
6572#ifdef __amigaos4__
6573 signal(SIGINT, SIG_IGN);
6574#endif
6575 ret = netsurf_register(&amiga_table);
6576 if (ret != NSERROR_OK) {
6577 ami_misc_fatal_error("NetSurf operation table failed registration");
6578 return RETURN_FAIL;
6579 }
6580
6581 /* initialise logging. Not fatal if it fails but not much we
6582 * can do about it either.
6583 */
6584 nslog_init(NULL, &argc, argv);
6585
6586 /* Need to do this before opening any splash windows etc... */
6587 if ((ami_libs_open() == false)) {
6588 return RETURN_FAIL;
6589 }
6590
6591 /* Open splash window */
6592 Object *splash_window = ami_gui_splash_open();
6593
6594#ifndef __amigaos4__
6595 /* OS3 low memory handler */
6596 struct Interupt *memhandler = ami_memory_init();
6597#endif
6598
6599 if (ami_gui_resources_open() == false) { /* alloc msgports, objects and other miscelleny */
6600 ami_misc_fatal_error("Unable to allocate resources");
6601 ami_gui_splash_close(splash_window);
6603 return RETURN_FAIL;
6604 }
6605
6606 current_user = ami_gui_read_all_tooltypes(argc, argv);
6607 struct RDArgs *args = ami_gui_commandline(&argc, argv, &nargc, &nargv);
6608
6609 current_user_dir = ami_gui_get_user_dir(current_user);
6610 if(current_user_dir == NULL) {
6612 ami_gui_splash_close(splash_window);
6614 return RETURN_FAIL;
6615 }
6616
6617 ami_mime_init("PROGDIR:Resources/mimetypes");
6618 sprintf(temp, "%s/mimetypes.user", current_user_dir);
6619 ami_mime_init(temp);
6620
6621#ifdef __amigaos4__
6623
6624 /* DataTypes loader needs datatypes.library v45,
6625 * but for some reason that's not in OS3.9.
6626 * Skip it to ensure it isn't causing other problems. */
6627 ret = amiga_datatypes_init();
6628#endif
6629
6630 /* user options setup */
6632 if (ret != NSERROR_OK) {
6633 ami_misc_fatal_error("Options failed to initialise");
6635 ami_gui_splash_close(splash_window);
6637 return RETURN_FAIL;
6638 }
6640 if(args != NULL) {
6641 nsoption_commandline(&nargc, &nargv, NULL);
6642 FreeArgs(args);
6643 }
6644
6645 if (ami_locate_resource(messages, "Messages") == false) {
6646 ami_misc_fatal_error("Cannot open Messages file");
6650 ami_gui_splash_close(splash_window);
6652 return RETURN_FAIL;
6653 }
6654
6655 ret = messages_add_from_file(messages);
6656
6657 current_user_cache = ASPrintf("%s/Cache", current_user_dir);
6658 if((lock = CreateDirTree(current_user_cache))) UnLock(lock);
6659
6660 ret = netsurf_init(current_user_cache);
6661
6662 if(current_user_cache != NULL) FreeVec(current_user_cache);
6663
6664 if (ret != NSERROR_OK) {
6665 ami_misc_fatal_error("NetSurf failed to initialise");
6669 ami_gui_splash_close(splash_window);
6671 return RETURN_FAIL;
6672 }
6673
6674 ret = amiga_icon_init();
6675
6676 search_web_init(nsoption_charp(search_engines_file));
6679 ami_amiupdate(); /* set env-vars for AmiUpdate */
6680 ami_font_init();
6685
6686 win_destroyed = false;
6687 ami_font_setdevicedpi(0); /* for early font requests, eg treeview init */
6688
6690
6691 urldb_load(nsoption_charp(url_file));
6692 urldb_load_cookies(nsoption_charp(cookie_file));
6693
6694 gui_init2(argc, argv);
6695
6696 ami_ctxmenu_init(); /* Requires screen pointer */
6697
6698 ami_gui_splash_close(splash_window);
6699
6700 strlcpy(script, nsoption_charp(arexx_dir), 1024);
6701 AddPart(script, nsoption_charp(arexx_startup), 1024);
6702 ami_arexx_execute(script);
6703
6704 NSLOG(netsurf, INFO, "Entering main loop");
6705
6706 while (!ami_quit) {
6707 ami_get_msg();
6708 }
6709
6710 strlcpy(script, nsoption_charp(arexx_dir), 1024);
6711 AddPart(script, nsoption_charp(arexx_shutdown), 1024);
6712 ami_arexx_execute(script);
6713
6714 ami_mime_free();
6715
6716 netsurf_exit();
6717
6720 free(current_user_dir);
6722
6723 /* finalise logging */
6725
6726#ifndef __amigaos4__
6727 /* OS3 low memory handler */
6728 ami_memory_fini(memhandler);
6729#endif
6730
6733
6734 return RETURN_OK;
6735}
6736
void ami_clipboard_free(void)
Definition: clipboard.c:82
void ami_clipboard_init(void)
Definition: clipboard.c:70
struct gui_clipboard_table * amiga_clipboard_table
Definition: clipboard.c:381
void gui_start_selection(struct gui_window *g)
Definition: clipboard.c:87
nserror ami_cookies_present(const char *search_term)
Open the cookie viewer.
Definition: cookies.c:348
struct core_window_table * amiga_core_window_table
Definition: corewindow.c:925
Interface to Intuition-based context menu operations.
struct Menu * ami_ctxmenu_clicktab_create(struct gui_window_2 *gwin, Object **clicktab_obj)
Definition: ctxmenu.h:90
struct Menu * ami_ctxmenu_history_create(int direction, struct gui_window_2 *gwin)
Definition: ctxmenu.h:89
struct Hook * ami_ctxmenu_get_hook(APTR data)
Definition: ctxmenu.h:87
void ami_ctxmenu_init(void)
Definition: ctxmenu.h:85
void ami_ctxmenu_release_hook(struct Hook *hook)
Definition: ctxmenu.h:88
@ AMI_CTXMENU_HISTORY_BACK
Definition: ctxmenu.h:30
@ AMI_CTXMENU_HISTORY_FORWARD
Definition: ctxmenu.h:31
void ami_ctxmenu_free(void)
Definition: ctxmenu.h:86
void ami_mime_free(void)
Definition: filetype.c:264
const char * fetch_filetype(const char *unix_path)
Determine the MIME type of a local file.
Definition: filetype.c:58
nserror ami_mime_init(const char *mimefile)
Definition: filetype.c:177
static void ami_gui_close_tabs(struct gui_window_2 *gwin, bool other_tabs)
Definition: gui.c:5458
static bool cli_force
Definition: gui.c:353
static void ami_gui_splash_close(Object *win_obj)
Definition: gui.c:6336
static nserror gui_window_get_dimensions(struct gui_window *gw, int *restrict width, int *restrict height)
Find the current dimensions of a amiga browser window content area.
Definition: gui.c:2089
static void ami_refresh_window(struct gui_window_2 *gwin)
Definition: gui.c:4564
static ULONG rxsig
Definition: gui.c:349
void ami_try_quit(void)
Definition: gui.c:3915
static void ami_gui_console_log_remove(struct gui_window *g)
Definition: gui.c:2306
bool ami_gui_window_update_box_deferred_check(struct MinList *deferred_rects, const struct rect *restrict new_rect, APTR mempool)
Check rect is not already queued for redraw.
Definition: gui.c:5696
struct ami_history_local_window * ami_gui_get_history_window(struct gui_window *gw)
Get local history window from gui_window.
Definition: gui.c:488
static void ami_update_buttons(struct gui_window_2 *gwin)
Definition: gui.c:1628
static void ami_gui_hotlist_toolbar_add(struct gui_window_2 *gwin)
Definition: gui.c:4093
static STRPTR nsscreentitle
Definition: gui.c:343
struct Window * ami_gui_get_window(struct gui_window *gw)
Get window from gui_window.
Definition: gui.c:578
static void gui_window_set_status(struct gui_window *g, const char *text)
Definition: gui.c:5937
static nsurl * gui_get_resource_url(const char *path)
Definition: gui.c:1218
static nserror gui_window_event(struct gui_window *gw, enum gui_window_event event)
process miscellaneous window events
Definition: gui.c:6456
static void gui_window_destroy(struct gui_window *g)
Definition: gui.c:5499
static uint32 ami_appid
Definition: gui.c:347
static void ami_gui_refresh_favicon(void *p)
Definition: gui.c:2535
static void gui_window_remove_caret(struct gui_window *g)
Definition: gui.c:6134
static void ami_gui_cache_favicon(nsurl *url, struct bitmap *favicon)
Definition: gui.c:3991
#define NSA_STATUS_TEXT
Definition: gui.c:188
#define EXTRAUP
Definition: gui.c:179
int ami_key_to_nskey(ULONG keycode, struct InputEvent *ie)
Definition: gui.c:1706
static void ami_gui_scroller_update(struct gui_window_2 *gwin)
Check the scroll bar requirements for a browser window, and add/remove the vertical scroller as appro...
Definition: gui.c:2209
void ami_gui_set_find_window(struct gui_window *gw, struct find_window *fw)
Set search window in gui_window.
Definition: gui.c:500
static const __attribute__((used))
Definition: gui.c:360
static void gui_window_update_extent(struct gui_window *g)
Definition: gui.c:3672
static nserror ami_set_options(struct nsoption_s *defaults)
Set option defaults for amiga frontend.
Definition: gui.c:1062
static void ami_set_border_gadget_size(struct gui_window_2 *gwin)
Definition: gui.c:2569
int ami_gui2_get_ctxmenu_history_tmp(struct gui_window_2 *gwin)
Get ctxmenu history tmp from gui_window_2.
Definition: gui.c:612
static void ami_gui_appicon_remove(struct gui_window_2 *gwin)
Definition: gui.c:3268
struct Screen * ami_gui_get_screen(void)
Get a pointer to the screen NetSurf is running on.
Definition: gui.c:405
struct gui_utf8_table * amiga_utf8_table
Definition: utf8.c:136
struct Node * ami_gui_get_tab_node(struct gui_window *gw)
Get tab node from gui_window.
Definition: gui.c:464
void ami_gui_hotlist_update_all(void)
Update hotlist toolbar and recreate the menu for all windows.
Definition: gui.c:4216
void ami_gui_close_inactive_tabs(struct gui_window_2 *gwin)
Close all tabs in a window except the active one.
Definition: gui.c:5494
static bool ami_quit
Definition: gui.c:332
static void ami_gui_console_log_switch(struct gui_window *g)
Definition: gui.c:2339
static void ami_gui_console_log_add(struct gui_window *g)
Definition: gui.c:2271
void ami_gui2_set_new_content(struct gui_window_2 *gwin, bool new_content)
Set new_content in gui_window_2 Indicates the window needs redrawing.
Definition: gui.c:636
static void ami_amiupdate(void)
Definition: gui.c:1189
static struct Screen * scrn
Definition: gui.c:328
static bool ami_gui_map_filename(char **remapped, const char *restrict path, const char *restrict file, const char *restrict map)
Definition: gui.c:745
static struct gui_misc_table amiga_misc_table
Definition: gui.c:6534
static int screen_signal
Definition: gui.c:341
@ GID_TABLAYOUT
Definition: gui.c:205
@ GID_HOTLISTSEPBAR
Definition: gui.c:236
@ GID_SEARCHSTRING
Definition: gui.c:232
@ OID_HSCROLL
Definition: gui.c:203
@ GID_HSCROLLLAYOUT
Definition: gui.c:238
@ GID_MAIN
Definition: gui.c:204
@ GID_ICON
Definition: gui.c:209
@ GID_PAGEINFO_INSECURE_BM
Definition: gui.c:218
@ GID_FAVE_ADD
Definition: gui.c:224
@ OID_VSCROLL
Definition: gui.c:202
@ GID_ADDTAB_BM
Definition: gui.c:229
@ GID_FAVE_RMV
Definition: gui.c:225
@ GID_PAGEINFO_INTERNAL_BM
Definition: gui.c:219
@ GID_PAGEINFO_SECURE_BM
Definition: gui.c:221
@ GID_FORWARD
Definition: gui.c:214
@ GID_STOP
Definition: gui.c:210
@ GID_PAGEINFO_LOCAL_BM
Definition: gui.c:220
@ GID_CLOSETAB_BM
Definition: gui.c:227
@ OID_MAIN
Definition: gui.c:201
@ GID_LOG
Definition: gui.c:242
@ GID_STATUS
Definition: gui.c:207
@ GID_HSCROLL
Definition: gui.c:237
@ GID_HOME
Definition: gui.c:212
@ GID_LAST
Definition: gui.c:243
@ GID_FAVE
Definition: gui.c:223
@ GID_PAGEINFO
Definition: gui.c:217
@ GID_TABS
Definition: gui.c:230
@ GID_RELOAD
Definition: gui.c:211
@ GID_SEARCH_ICON
Definition: gui.c:216
@ GID_ADDTAB
Definition: gui.c:228
@ GID_TABS_FLAG
Definition: gui.c:231
@ GID_LOGLAYOUT
Definition: gui.c:241
@ GID_TOOLBARLAYOUT
Definition: gui.c:233
@ GID_CLOSETAB
Definition: gui.c:226
@ GID_HOTLISTLAYOUT
Definition: gui.c:235
@ GID_VSCROLLLAYOUT
Definition: gui.c:240
@ GID_THROBBER
Definition: gui.c:215
@ GID_PAGEINFO_WARNING_BM
Definition: gui.c:222
@ GID_URL
Definition: gui.c:208
@ GID_HOTLIST
Definition: gui.c:234
@ GID_BACK
Definition: gui.c:213
@ GID_VSCROLL
Definition: gui.c:239
@ GID_BROWSER
Definition: gui.c:206
void ami_gui2_set_ctxmenu_history_tmp(struct gui_window_2 *gwin, int temp)
Set ctxmenu history tmp in gui_window_2.
Definition: gui.c:606
static void ami_gui_hotlist_toolbar_remove(struct gui_window_2 *gwin)
Definition: gui.c:4166
static struct gui_window * gui_window_create(struct browser_window *bw, struct gui_window *existing, gui_window_create_flags flags)
Definition: gui.c:4716
static void ami_gui_hotlist_toolbar_update(struct gui_window_2 *gwin)
Definition: gui.c:4188
int main(int argc, char **argv)
Normal entry point from OS.
Definition: gui.c:6543
nserror ami_gui_win_list_add(void *win, int type, const struct ami_win_event_table *table)
Add a window to the NetSurf window list (to enable event processing)
Definition: gui.c:4685
static nserror gui_search_web_provider_update(const char *provider_name, struct bitmap *ico_bitmap)
Gui callback when search provider details are updated.
Definition: gui.c:6015
static void ami_update_quals(struct gui_window_2 *gwin)
Definition: gui.c:1853
static void ami_handle_appmsg(void)
Definition: gui.c:3328
uint32 ami_gui_get_app_id(void)
Get the application.library ID NetSurf is registered as.
Definition: gui.c:6364
static void ami_toggletabbar(struct gui_window_2 *gwin, bool show)
Definition: gui.c:4238
static STRPTR temp_homepage_url
Definition: gui.c:352
static struct IBox * ami_ns_rect_to_ibox(struct gui_window_2 *gwin, const struct rect *rect)
Definition: gui.c:2002
void ami_gui_switch_to_new_tab(struct gui_window_2 *gwin)
Switch to the most-recently-opened tab.
Definition: gui.c:4389
void ami_gui_history(struct gui_window_2 *gwin, bool back)
Definition: gui.c:1690
static void ami_set_screen_defaults(struct Screen *screen)
Definition: gui.c:987
bool ami_text_box_at_point(struct gui_window_2 *gwin, ULONG *restrict x, ULONG *restrict y)
Definition: gui.c:6194
void * ami_window_at_pointer(int type)
undocumented, or internal, or documented elsewhere
Definition: gui.c:684
void ami_gui_close_window(void *w)
Close a window and all tabs attached to it.
Definition: gui.c:5488
static nserror amiga_window_invalidate_area(struct gui_window *g, const struct rect *restrict rect)
Invalidates an area of an amiga browser window.
Definition: gui.c:3719
struct Menu * ami_gui_get_menu(struct gui_window *gw)
Get imenu from gui_window.
Definition: gui.c:584
static void gui_file_gadget_open(struct gui_window *g, struct hlcache_handle *hl, struct form_control *gadget)
Definition: gui.c:6344
void ami_gui_set_throbbing(struct gui_window *gw, bool throbbing)
Set throbbing status in gui_window.
Definition: gui.c:516
void ami_set_pointer(struct gui_window_2 *gwin, gui_pointer_shape shape, bool update)
Definition: gui.c:690
static void ami_do_redraw(struct gui_window_2 *gwin)
Definition: gui.c:5734
static void ami_get_vscroll_pos(struct gui_window_2 *gwin, ULONG *ys)
Definition: gui.c:5842
#define SCROLL_BOTTOM
Definition: gui.c:173
static nserror gui_window_set_url(struct gui_window *g, nsurl *url)
Definition: gui.c:5971
static UWORD ami_system_colour_scrollbar_fgpen(struct DrawInfo *drinfo)
Definition: gui.c:918
void ami_gui_adjust_scale(struct gui_window *gw, float adjustment)
Adjust scale by specified amount.
Definition: gui.c:4383
static struct MinList * window_list
Definition: gui.c:327
bool ami_locate_resource(char *fullpath, const char *file)
Definition: gui.c:816
#define SIDEUP
Definition: gui.c:177
static bool ami_gui_vscroll_add(struct gui_window_2 *gwin)
Definition: gui.c:2159
static ULONG applibsig
Definition: gui.c:348
bool ami_gui_get_throbbing(struct gui_window *gw)
Get throbbing status from gui_window.
Definition: gui.c:510
struct gui_window * ami_gui_get_active_gw(void)
Get a pointer to the gui_window which NetSurf considers to be the current/active one.
Definition: gui.c:400
static void ami_do_redraw_tiled(struct gui_window_2 *gwin, bool busy, int left, int top, int width, int height, int sx, int sy, struct IBox *bbox, struct redraw_context *ctx)
Definition: gui.c:4428
struct browser_window * ami_gui2_get_browser_window(struct gui_window_2 *gwin)
Get browser window from gui_window_2.
Definition: gui.c:427
static void gui_init2(int argc, char **argv)
Definition: gui.c:1437
static bool ami_gui_console_log_toggle(struct gui_window *g)
Definition: gui.c:2328
static BOOL locked_screen
Definition: gui.c:340
static Object * ami_gui_splash_open(void)
Definition: gui.c:6237
void ami_reset_pointer(struct gui_window_2 *gwin)
Definition: gui.c:698
static bool ami_gui_resources_open(void)
Definition: gui.c:890
void ami_gui2_set_ctxmenu_history(struct gui_window_2 *gwin, ULONG direction, Object *ctx_hist)
Set ctxmenu history in gui_window_2.
Definition: gui.c:624
static bool ami_gui_vscroll_remove(struct gui_window_2 *gwin)
Definition: gui.c:2186
static struct MsgPort * applibport
Definition: gui.c:346
static void gui_quit(void)
Definition: gui.c:3930
#define USERS_DIR
Definition: gui.c:355
static struct gui_fetch_table amiga_fetch_table
Definition: gui.c:6524
void ami_get_msg(void)
Definition: gui.c:3531
STRPTR ami_gui_get_screen_title(void)
Get the string for NetSurf's screen titlebar.
Definition: gui.c:976
static bool ami_gui_hscroll_remove(struct gui_window_2 *gwin)
Definition: gui.c:2141
static void ami_redraw_callback(void *p)
Definition: gui.c:5628
#define NSA_QUAL_ALT
Definition: gui.c:183
static void ami_change_tab(struct gui_window_2 *gwin, int direction)
Definition: gui.c:3599
static void gui_window_set_title(struct gui_window *g, const char *restrict title)
Definition: gui.c:3622
struct ami_menu_data ** ami_gui2_get_menu_data(struct gui_window_2 *gwin)
Get menu_data from gui_window_2.
Definition: gui.c:600
static struct gui_globals * browserglob
Definition: gui.c:344
nserror ami_gui_new_blank_tab(struct gui_window_2 *gwin)
Definition: gui.c:4402
static void ami_schedule_redraw_remove(struct gui_window_2 *gwin)
Definition: gui.c:5660
#define SCROLL_PAGE_UP
Definition: gui.c:171
static char * ami_gui_read_tooltypes(struct WBArg *wbarg)
Definition: gui.c:1391
void ami_gui2_set_menu(struct gui_window_2 *gwin, struct Menu *menu)
Set imenu to gui_window_2.
Definition: gui.c:591
static struct MsgPort * sport
Definition: gui.c:329
static void gui_window_place_caret(struct gui_window *g, int x, int y, int height, const struct rect *clip)
Definition: gui.c:6090
void ami_gui2_set_closed(struct gui_window_2 *gwin, bool closed)
Set closed in gui_window_2.
Definition: gui.c:630
nserror ami_gui_get_space_box(Object *obj, struct IBox **bbox)
Compatibility function to get space.gadget render area.
Definition: gui.c:1859
Object * ami_gui2_get_object(struct gui_window_2 *gwin, int object_type)
Get object from gui_window.
Definition: gui.c:536
const char * ami_gui_get_win_title(struct gui_window *gw)
Get window title from gui_window.
Definition: gui.c:451
static void ami_gui_window_update_box_deferred(struct gui_window *g, bool draw)
Definition: gui.c:5665
static int ami_gui_hotlist_scan(struct List *speed_button_list, struct gui_window_2 *gwin)
Definition: gui.c:4082
static struct gui_window * cur_gw
Definition: gui.c:330
#define NSA_KBD_SCROLL_PX
Definition: gui.c:167
static nserror gui_window_set_scroll(struct gui_window *g, const struct rect *rect)
Set the scroll position of a amiga browser window.
Definition: gui.c:5871
int ami_gui_get_throbber_frame(struct gui_window *gw)
Get throbbing frame from gui_window.
Definition: gui.c:522
static char * users_dir
Definition: gui.c:356
const char * ami_gui_get_tab_title(struct gui_window *gw)
Get tab title from gui_window.
Definition: gui.c:458
static void gui_window_set_icon(struct gui_window *g, struct hlcache_handle *icon)
function to add retrieved favicon to gui
Definition: gui.c:2464
static char * current_user_dir
Definition: gui.c:357
static void ami_gui_resources_free(void)
Definition: gui.c:880
void ami_gui_set_history_window(struct gui_window *gw, struct ami_history_local_window *hw)
Set local history window in gui_window.
Definition: gui.c:494
struct gui_window * ami_gui2_get_gui_window(struct gui_window_2 *gwin)
Get gui_window from gui_window_2.
Definition: gui.c:445
static void ami_handle_applib(void)
Definition: gui.c:3443
STRPTR ami_locale_langs(int *codeset)
Definition: gui.c:704
struct List * ami_gui_get_download_list(struct gui_window *gw)
Get download list from gui_window.
Definition: gui.c:433
#define NSA_QUAL_SHIFT
Definition: gui.c:182
Object * ami_gui2_get_ctxmenu_history(struct gui_window_2 *gwin, ULONG direction)
Get ctxmenu history from gui_window_2.
Definition: gui.c:618
static void gui_window_new_content(struct gui_window *g)
Definition: gui.c:6148
static bool gui_window_get_scroll(struct gui_window *g, int *restrict sx, int *restrict sy)
Definition: gui.c:5851
#define AMINS_SCROLLERPEN
Definition: gui.c:166
#define BOOL_MISMATCH(a, b)
Definition: gui.c:194
static bool ami_spacebox_to_ns_coords(struct gui_window_2 *gwin, int *restrict x, int *restrict y, int space_x, int space_y)
Definition: gui.c:1885
static void ami_openscreen(void)
Definition: gui.c:1236
#define SCROLL_PAGE_DOWN
Definition: gui.c:172
static struct Hook newprefs_hook
Definition: gui.c:350
ULONG ami_gui2_get_tabs(struct gui_window_2 *gwin)
Get tabs from gui_window_2.
Definition: gui.c:470
void ami_gui_beep(void)
Beep.
Definition: gui.c:416
void ami_gui_free_space_box(struct IBox *bbox)
Free any data obtained via ami_gui_get_space_box().
Definition: gui.c:1876
bool ami_mouse_to_ns_coords(struct gui_window_2 *gwin, int *restrict x, int *restrict y, int mouse_x, int mouse_y)
Definition: gui.c:1900
static nserror colour_option_from_pen(UWORD pen, enum nsoption_e option, struct Screen *screen, colour def_colour)
set option from pen
Definition: gui.c:936
static bool ami_gui_hotlist_add(void *userdata, int level, int item, const char *title, nsurl *url, bool is_folder)
Definition: gui.c:4026
static void ami_switch_tab(struct gui_window_2 *gwin, bool redraw)
Definition: gui.c:3750
static void ami_gui_trap_mouse(struct gui_window_2 *gwin)
Definition: gui.c:2037
static void ami_gui_hotlist_toolbar_free(struct gui_window_2 *gwin, struct List *speed_button_list)
Definition: gui.c:4141
struct hlcache_handle * ami_gui_get_favicon(struct gui_window *gw)
Get favicon from gui_window.
Definition: gui.c:482
HOOKF(void, ami_gui_newprefs_hook, APTR, window, APTR)
Definition: gui.c:1231
static void ami_do_redraw_limits(struct gui_window *g, struct browser_window *bw, bool busy, int x0, int y0, int x1, int y1)
Redraw an area of the browser window - Amiga-specific function.
Definition: gui.c:4529
void ami_gui_set_scale(struct gui_window *gw, float scale)
Set the scale of a gui window.
Definition: gui.c:4377
struct List * ami_gui2_get_tab_list(struct gui_window_2 *gwin)
Get tab list from gui_window_2.
Definition: gui.c:476
static const struct ami_win_event_table ami_gui_table
Definition: gui.c:4710
void ami_gui_win_list_remove(void *win)
Remove a window from the NetSurf window list.
Definition: gui.c:4699
int ami_gui_count_windows(int window, int *tabs)
Count windows, and optionally tabs.
Definition: gui.c:4349
static BOOL ami_gui_event(void *w)
Definition: gui.c:2632
static bool win_destroyed
Definition: gui.c:342
static void ami_quit_netsurf_delayed(void)
Definition: gui.c:3852
int ami_gui_get_quals(Object *win_obj)
Get which qualifier keys are being pressed.
Definition: gui.c:1828
static BOOL ami_handle_msg(void)
Definition: gui.c:2586
void ami_gui_update_hotlist_button(struct gui_window_2 *gwin)
Definition: gui.c:4001
static nserror gui_page_info_change(struct gui_window *gw)
Definition: gui.c:3278
void ami_schedule_redraw(struct gui_window_2 *gwin, bool full_redraw)
Schedule a redraw of the browser window - Amiga-specific function.
Definition: gui.c:5652
static bool gui_window_drag_start(struct gui_window *g, gui_drag_type type, const struct rect *rect)
Definition: gui.c:6169
static void gui_window_console_log(struct gui_window *g, browser_window_console_source src, const char *msg, size_t msglen, browser_window_console_flags flags)
Definition: gui.c:2350
static void ami_openscreenfirst(void)
Definition: gui.c:1323
static bool ami_gui_check_resource(char *fullpath, const char *file)
Definition: gui.c:794
static void ami_gui_menu_update_all(void)
Definition: gui.c:2058
static void ami_gui_close_screen(struct Screen *scrn, BOOL locked_screen, BOOL donotwait)
Definition: gui.c:3877
static bool ami_gui_hscroll_add(struct gui_window_2 *gwin)
Definition: gui.c:2113
struct Window * ami_gui2_get_window(struct gui_window_2 *gwin)
Get window from gui_window_2.
Definition: gui.c:572
#define SCROLL_TOP
Definition: gui.c:170
struct browser_window * ami_gui_get_browser_window(struct gui_window *gw)
Get browser window from gui_window.
Definition: gui.c:421
static struct MsgPort * schedulermsgport
Definition: gui.c:334
static struct MsgPort * appport
Definition: gui.c:335
static struct RDArgs * ami_gui_commandline(int *restrict argc, char **argv, int *restrict nargc, char **nargv)
Definition: gui.c:1330
static char * current_user_faviconcache
Definition: gui.c:358
static struct gui_window_table amiga_window_table
Definition: gui.c:6494
struct MinList * ami_gui_get_window_list(void)
Get the window list.
Definition: gui.c:410
char * ami_gui_get_cache_favicon_name(nsurl *url, bool only_if_avail)
Definition: gui.c:3971
struct gui_window_2 * ami_gui_get_gui_window_2(struct gui_window *gw)
Get gui_window_2 from gui_window.
Definition: gui.c:439
static struct gui_search_web_table amiga_search_web_table
Definition: gui.c:6530
void ami_gui_tabs_toggle_all(void)
Definition: gui.c:4313
static STRPTR ami_gui_read_all_tooltypes(int argc, char **argv)
Definition: gui.c:1409
static void ami_gui_scroll_internal(struct gui_window_2 *gwin, int xs, int ys)
Definition: gui.c:1925
static char * ami_gui_get_user_dir(STRPTR current_user)
Definition: gui.c:6372
BOOL ami_gadget_hit(Object *obj, int x, int y)
Definition: gui.c:6221
#define nsoption_default_set_int(OPTION, VALUE)
void ami_gui_set_throbber_frame(struct gui_window *gw, int frame)
Set throbbing frame in gui_window.
Definition: gui.c:529
static void ami_get_hscroll_pos(struct gui_window_2 *gwin, ULONG *xs)
Definition: gui.c:5832
void ami_quit_netsurf(void)
Definition: gui.c:3818
#define NSA_MAX_HOTLIST_BUTTON_LEN
Definition: gui.c:168
#define AMI_GUI_TOOLBAR_MAX
Definition: gui.h:57
struct MsgPort * ami_gui_get_shared_msgport(void)
Get shared message port.
@ AMI_WIN_MAIN
Definition: gui.h:47
@ AMI_GAD_URL
Definition: gui.h:45
@ AMI_GAD_TABS
Definition: gui.h:44
@ AMI_GAD_SEARCH
Definition: gui.h:46
@ AMI_GAD_THROBBER
Definition: gui.h:43
void ami_help_new_screen(struct Screen *screen)
Definition: help.c:66
ULONG ami_help_signal(void)
Definition: help.c:72
void ami_help_process(void)
Definition: help.c:80
void ami_help_open(ULONG node, struct Screen *screen)
Definition: help.c:50
void ami_help_free(void)
Definition: help.c:57
@ AMI_HELP_GUI
Definition: help.h:26
void ami_menu_free_glyphs(void)
Definition: menu.c:182
void ami_misc_fatal_error(const char *message)
Definition: misc.c:73
int32 amiga_warn_user_multi(const char *body, const char *opt1, const char *opt2, struct Window *win)
Definition: misc.c:93
nserror amiga_warn_user(const char *warning, const char *detail)
Warn the user of an event.
Definition: misc.c:79
char * translate_escape_chars(const char *s)
returns a string with escape chars translated and string converted to local charset (based on remove_...
Definition: misc.c:246
struct gui_file_table * amiga_file_table
Definition: misc.c:463
nserror ami_pageinfo_open(struct browser_window *bw, ULONG left, ULONG top)
Open the page info window.
Definition: pageinfo.c:224
const struct plotter_table amiplot
Definition: plotters.c:1180
bool ami_plot_screen_is_palettemapped(void)
Definition: plotters.c:610
void ami_plot_ra_free(struct gui_globals *gg)
Free a plotter render area.
Definition: plotters.c:258
struct BitMap * ami_plot_ra_get_bitmap(struct gui_globals *gg)
Get a drawing BitMap associated with a render area.
Definition: plotters.c:295
void ami_plot_clear_bbox(struct RastPort *rp, struct IBox *bbox)
Definition: plotters.c:412
void ami_plot_ra_set_pen_list(struct gui_globals *gg, struct MinList *pen_list)
Set a list of shared pens for a render area to use Only relevant for palette-mapped screens.
Definition: plotters.c:306
void ami_plot_ra_get_size(struct gui_globals *gg, int *width, int *height)
Get size of BitMap associated with a render area.
Definition: plotters.c:300
void ami_clearclipreg(struct gui_globals *gg)
Definition: plotters.c:311
struct gui_globals * ami_plot_ra_alloc(ULONG width, ULONG height, bool force32bit, bool alloc_pen_list)
Alloc a plotter render area.
Definition: plotters.c:113
void ami_plot_release_pens(struct MinList *shared_pens)
Definition: plotters.c:356
void ami_schedule_free(void)
Finalise amiga scheduler.
Definition: schedule.c:320
nserror ami_schedule(int t, void(*callback)(void *p), void *p)
Schedule a callback.
Definition: schedule.c:331
void ami_schedule_handle(struct MsgPort *nsmsgport)
Handle a message received from the scheduler process.
Definition: schedule.c:369
nserror ami_schedule_create(struct MsgPort *msgport)
Initialise amiga scheduler.
Definition: schedule.c:302
void ami_mouse_pointers_free(void)
Definition: theme.c:396
void ami_theme_throbber_free(void)
Definition: theme.c:191
int ami_theme_throbber_get_width(void)
Definition: theme.c:163
void ami_theme_init(void)
Definition: theme.c:134
void ami_init_mouse_pointers(void)
Definition: theme.c:284
void ami_theme_throbber_setup(void)
Definition: theme.c:173
void ami_throbber_redraw_schedule(int t, struct gui_window *g)
Definition: theme.c:517
int ami_theme_throbber_get_height(void)
Definition: theme.c:168
void ami_update_pointer(struct Window *win, gui_pointer_shape shape)
Definition: theme.c:221
void ami_get_theme_filename(char *filename, const char *themestring, bool protocol)
Definition: theme.c:198
void ami_arexx_cleanup(void)
Definition: arexx.c:185
STATIC char result[100]
Definition: arexx.c:77
bool ami_arexx_init(ULONG *rxsig)
Definition: arexx.c:127
void ami_arexx_self(const char *cmd)
Definition: arexx.c:167
void ami_arexx_execute(char *script)
Definition: arexx.c:172
void ami_arexx_handle(void)
Definition: arexx.c:156
void gui_window_set_pointer(struct gui_window *gw, gui_pointer_shape shape)
set the pointer shape
Definition: gui.c:482
Low-level source data cache backing store interface.
struct gui_llcache_table * filesystem_llcache_table
nserror browser_window_history_get_thumbnail(struct browser_window *bw, struct bitmap **bitmap_out)
Get the thumbnail bitmap for the current history entry.
nserror browser_window_history_forward(struct browser_window *bw, bool new_window)
Go forward in the history.
nserror browser_window_history_back(struct browser_window *bw, bool new_window)
Go back in the history.
Interface to browser history operations.
Browser window creation and manipulation interface.
nserror browser_window_schedule_reformat(struct browser_window *bw)
Reformat the browser window contents in a safe context.
bool browser_window_redraw_ready(struct browser_window *bw)
Check whether browser window is ready for redraw.
nserror browser_window_refresh_url_bar(struct browser_window *bw)
Update URL bar for a given browser window to bw's content's URL.
nserror browser_window_get_features(struct browser_window *bw, int x, int y, struct browser_window_features *data)
Get access to any page features at the given coordinates.
nserror browser_window_navigate(struct browser_window *bw, struct nsurl *url, struct nsurl *referrer, enum browser_window_nav_flags flags, char *post_urlenc, struct fetch_multipart_data *post_multipart, struct hlcache_handle *parent)
Start fetching a page in a browser window.
bool browser_window_redraw(struct browser_window *bw, int x, int y, const struct rect *clip, const struct redraw_context *ctx)
Redraw an area of a window.
bool browser_window_has_content(struct browser_window *bw)
Find out if a browser window is currently showing a content.
bool browser_window_back_available(struct browser_window *bw)
Check availability of Back action for a given browser window.
nserror browser_window_get_scrollbar_type(struct browser_window *bw, browser_scrolling *h, browser_scrolling *v)
Get the browser window's scrollbar details.
void browser_window_mouse_click(struct browser_window *bw, browser_mouse_state mouse, int x, int y)
Handle mouse clicks in a browser window.
bool browser_window_scroll_at_point(struct browser_window *bw, int x, int y, int scrx, int scry)
Send a scroll request to a browser window at a particular point.
void browser_window_destroy(struct browser_window *bw)
Close and destroy a browser window.
nserror browser_window_reload(struct browser_window *bw, bool all)
Reload the page in a browser window.
browser_scrolling
@ BW_SCROLLING_NO
@ BW_SCROLLING_YES
bool browser_window_reload_available(struct browser_window *bw)
Check availability of Reload action for a given browser window.
bool browser_window_forward_available(struct browser_window *bw)
Check availability of Forward action for a given browser window.
browser_window_page_info_state
Browser window page information states.
@ PAGE_STATE_INSECURE
Insecure page load.
@ PAGE_STATE_SECURE_ISSUES
Secure load, but has insecure elements.
@ PAGE_STATE_SECURE
Secure load.
@ PAGE_STATE_SECURE_OVERRIDE
Secure load, but had to override.
@ PAGE_STATE_LOCAL
Page loaded from file:/// etc.
@ PAGE_STATE_INTERNAL
Page loaded from internal handler.
const char * browser_window_get_title(struct browser_window *bw)
Get the title of a browser_window.
nserror browser_window_get_extents(struct browser_window *bw, bool scaled, int *width, int *height)
Get a browser window's content extents.
nserror browser_window_create(enum browser_window_create_flags flags, struct nsurl *url, struct nsurl *referrer, struct browser_window *existing, struct browser_window **bw)
Create and open a new root browser window with the given page.
void browser_window_stop(struct browser_window *bw)
Stop all fetching activity in a browser window.
bool browser_window_is_frameset(struct browser_window *bw)
Find out if a browser window contains a frameset.
nserror browser_window_set_scale(struct browser_window *bw, float scale, bool absolute)
Sets the scale of a browser window.
browser_window_page_info_state browser_window_get_page_info_state(const struct browser_window *bw)
Request the current browser window page info state.
struct hlcache_handle * browser_window_get_content(struct browser_window *bw)
Get a cache handle for the content within a browser window.
@ BW_CREATE_HISTORY
this will form a new history node (don't set for back/reload/etc)
@ BW_CREATE_TAB
New gui_window to be tab in same window as "existing" gui_window.
@ BW_CREATE_CLONE
New gui_window to be clone of "existing" gui_window.
bool browser_window_stop_available(struct browser_window *bw)
Check availability of Stop action for a given browser window.
bool browser_window_drop_file_at_point(struct browser_window *bw, int x, int y, char *file)
Drop a file onto a browser window at a particular point, or determine if a file may be dropped onto t...
@ BW_NAVIGATE_HISTORY
this will form a new history node (don't set for back/reload/etc)
void browser_window_mouse_track(struct browser_window *bw, browser_mouse_state mouse, int x, int y)
Handle non-click mouse action in a browser window.
void browser_window_set_gadget_filename(struct browser_window *bw, struct form_control *gadget, const char *fn)
set filename on form control.
static osspriteop_area * buffer
The buffer characteristics.
Definition: buffer.c:55
browser_window_console_source
Sources of messages which end up in the browser window console.
Definition: console.h:30
@ BW_CS_SCRIPT_CONSOLE
Logging from some running script.
Definition: console.h:33
@ BW_CS_INPUT
Input from the client.
Definition: console.h:31
@ BW_CS_SCRIPT_ERROR
Error from some running script.
Definition: console.h:32
browser_window_console_flags
Flags for browser window console logging.
Definition: console.h:41
@ BW_CS_FLAG_LEVEL_LOG
Logged at the 'log' level, please only use one of the LEVEL flags.
Definition: console.h:55
@ BW_CS_FLAG_LEVEL_DEBUG
Logged at the 'debug' level, please use only one of the LEVEL flags.
Definition: console.h:53
@ BW_CS_FLAG_LEVEL_INFO
Logged at the 'info' level, please use only one of the LEVEL flags.
Definition: console.h:57
@ BW_CS_FLAG_LEVEL_MASK
Mask for the error level to allow easy comparison using the above.
Definition: console.h:64
@ BW_CS_FLAG_LEVEL_WARN
Logged at the 'warn' level, please use only one of the LEVEL flags.
Definition: console.h:59
@ BW_CS_FLAG_LEVEL_ERROR
Logged at the 'error' level, please use only one of the LEVEL flags.
Definition: console.h:61
@ BW_CS_FLAG_FOLDABLE
The log entry is foldable.
Definition: console.h:50
nserror fetch_fdset(fd_set *read_fd_set, fd_set *write_fd_set, fd_set *except_fd_set, int *maxfd_out)
Get the set of file descriptors the fetchers are currently using.
Definition: fetch.c:385
Fetching of data from a URL (interface).
Unified cookie database public interface.
void urldb_save_cookies(const char *filename)
Save persistent cookies to file.
Definition: urldb.c:4448
void urldb_load_cookies(const char *filename)
Load a cookie file into the database.
Definition: urldb.c:4281
#define amiga_datatypes_init()
Definition: datatypes.h:37
nserror hotlist_fini(void)
Finalise the hotlist.
Definition: hotlist.c:1387
nserror hotlist_add_url(nsurl *url)
Add an entry to the hotlist for given URL.
Definition: hotlist.c:1430
nserror hotlist_init(const char *load_path, const char *save_path)
Initialise the hotlist.
Definition: hotlist.c:1290
bool hotlist_has_url(nsurl *url)
Check whether given URL is present in hotlist.
Definition: hotlist.c:1493
void hotlist_remove_url(nsurl *url)
Remove any entries matching the given URL from the hotlist.
Definition: hotlist.c:1535
#define NSOPTION_SYS_COLOUR_END
Definition: options.h:38
#define NSOPTION_SYS_COLOUR_START
Definition: options.h:37
nserror search_web_omni(const char *term, enum search_web_omni_flags flags, struct nsurl **url_out)
Generate a nsurl from a search term.
Definition: searchweb.c:318
nserror search_web_init(const char *provider_fname)
Initialise the web search operations.
Definition: searchweb.c:525
nserror search_web_select_provider(const char *selection)
Change the currently selected web search provider.
Definition: searchweb.c:397
bool ami_drag_has_data(void)
Definition: drag.c:329
void gui_drag_save_selection(struct gui_window *g, const char *selection)
Definition: drag.c:303
void ami_drag_save(struct Window *win)
Definition: drag.c:307
bool ami_drag_icon_move(void)
Definition: drag.c:319
void gui_drag_save_object(struct gui_window *g, struct hlcache_handle *c, gui_save_type type)
Definition: drag.c:298
#define AMI_DRAG_THRESHOLD
Definition: drag.h:28
nserror
Enumeration of error codes.
Definition: errors.h:29
@ NSERROR_BAD_PARAMETER
Bad Parameter.
Definition: errors.h:48
@ NSERROR_NOMEM
Memory exhaustion.
Definition: errors.h:32
@ NSERROR_OK
No error.
Definition: errors.h:30
const char * type
Definition: filetype.cpp:44
static void gui_window_start_throbber(struct gui_window *g)
Definition: gui.c:2056
static void gui_window_stop_throbber(struct gui_window *gw)
Definition: gui.c:2063
struct BitMap * ami_bitmap_get_native(struct bitmap *bitmap, int width, int height, bool palette_mapped, struct BitMap *friendbm)
Definition: bitmap.c:666
void ami_bitmap_fini(void)
Cleanup bitmap allocations.
Definition: bitmap.c:678
bool amiga_bitmap_save(void *bitmap, const char *path, unsigned flags)
Save a bitmap in the platform's native format.
Definition: bitmap.c:255
PLANEPTR ami_bitmap_get_mask(struct bitmap *bitmap, int width, int height, struct BitMap *n_bm)
Definition: bitmap.c:626
struct gui_bitmap_table * amiga_bitmap_table
Definition: bitmap.c:777
bool amiga_bitmap_get_opaque(void *bitmap)
Gets whether a bitmap should be plotted opaque.
Definition: bitmap.c:309
#define AMI_BITMAP_SCALE_ICON
Definition: bitmap.h:31
void ami_free_download_list(struct List *dllist)
Definition: download.c:407
nserror gui_window_save_link(struct gui_window *g, nsurl *url, const char *title)
Definition: download.c:428
struct gui_download_table * amiga_download_table
Definition: download.c:534
void ami_download_parse_backmsg(const char *backmsg)
Definition: download.c:520
struct FileRequester * filereq
Definition: file.c:52
void ami_file_req_free(void)
Definition: file.c:300
void ami_file_req_init(void)
Definition: file.c:281
struct TextFont * ami_font_open_disk_font(struct TextAttr *tattr)
Definition: font.c:101
void ami_font_close_disk_font(struct TextFont *tfont)
Definition: font.c:107
void ami_font_init(void)
Definition: font.c:113
struct gui_layout_table * ami_layout_table
Definition: font.c:162
void ami_font_setdevicedpi(int id)
Definition: font.c:48
void ami_font_fini(void)
Definition: font.c:122
nserror ami_hotlist_scan(void *userdata, int first_item, const char *folder, bool(*cb_add_item)(void *userdata, int level, int item, const char *title, nsurl *url, bool folder))
Scan the hotlist.
Definition: hotlist.c:151
nserror ami_nsoption_read(void)
Definition: nsoption.c:29
nserror ami_nsoption_set_location(const char *current_user_dir)
Definition: nsoption.c:39
void ami_nsoption_free(void)
Definition: nsoption.c:52
nserror ami_nsoption_write(void)
Definition: nsoption.c:34
struct MinList * ami_AllocMinList(void)
List abstraction as OS3 appears to have problems with NewMinList()
Definition: object.c:63
struct MinList * NewObjList(void)
Definition: object.c:71
void FreeObjList(struct MinList *objlist)
Definition: object.c:117
void ami_object_fini(void)
Definition: object.c:50
bool ami_object_init(void)
Initialisation for itempool.
Definition: object.c:42
void DelObject(struct nsObject *dtzo)
Definition: object.c:107
struct nsObject * AddObject(struct MinList *objlist, ULONG otype)
Definition: object.c:77
void DelObjectNoFree(struct nsObject *dtzo)
Definition: object.c:112
@ AMINS_WINDOW
Definition: object.h:28
@ AMINS_GUIOPTSWINDOW
Definition: object.h:34
@ AMINS_TVWINDOW
Definition: object.h:31
@ AMINS_RECT
Definition: object.h:39
bool ami_print_cont(void)
Definition: print.c:460
struct MsgPort * ami_print_get_msgport(void)
Definition: print.c:494
struct gui_window * ami_search_get_gwin(struct find_window *fw)
Obtain gui window associated with find window.
Definition: search.c:127
struct gui_search_table * amiga_search_table
Definition: search.c:125
void ami_search_close(void)
Close search.
Definition: search.c:229
void ami_utf8_free(char *ptr)
Definition: utf8.c:104
nserror utf8_to_local_encoding(const char *string, size_t len, char **result)
Definition: utf8.c:89
char * ami_to_utf8_easy(const char *string)
Definition: utf8.c:119
char * ami_utf8_easy(const char *string)
Definition: utf8.c:109
nserror utf8_from_local_encoding(const char *string, size_t len, char **result)
Definition: utf8.c:80
struct atari_hotlist hl
Definition: hotlist.c:47
void ami_gui_menu_update_checked(struct gui_window_2 *gwin)
Definition: gui_menu.c:691
void ami_gui_menu_refresh_hotlist(void)
Refresh the Hotlist menu.
Definition: gui_menu.c:1163
void ami_gui_menu_update_disabled(struct gui_window *g, struct hlcache_handle *c)
Definition: gui_menu.c:735
struct Menu * ami_gui_menu_create(struct gui_window_2 *gwin)
Definition: gui_menu.c:1062
bool ami_gui_menu_get_check_toggled(void)
Gets if the menu needs updating because an item linked to a toggle menu item has been changed.
Definition: gui_menu.c:818
void ami_gui_menu_freemenus(struct Menu *menu, struct ami_menu_data **md)
Frees a menu.
Definition: gui_menu.c:1127
bool ami_gui_menu_quit_selected(void)
Gets if NetSurf has been quit from the menu.
Definition: gui_menu.c:1158
void ami_gui_menu_free(struct gui_window_2 *gwin)
Definition: gui_menu.c:1138
void ami_gui_menu_set_disabled(struct Window *win, struct Menu *menu, int item, bool disable)
Set disabled state of a menu item almost generic, but not quite.
Definition: gui_menu.c:679
const char *const verdate
Definition: gui_menu.c:93
const char *const netsurf_version
User friendly version string.
Definition: gui_menu.c:92
@ AMI_MENU_AREXX_MAX
Definition: gui_menu.h:102
@ M_CLOSETAB
Definition: gui_menu.h:47
@ M_PASTE
Definition: gui_menu.h:57
static CONST_STRPTR tabs[OPTS_MAX_TABS]
Definition: gui_options.c:254
void ami_gui_opts_websearch_free(struct List *websearchlist)
Definition: gui_options.c:2368
struct List * ami_gui_opts_websearch(int *idx)
Definition: gui_options.c:2339
void ami_gui_opts_open(void)
Definition: gui_options.c:527
nserror ami_history_local_destroy(struct ami_history_local_window *history_local_win)
destroy a previously created local history view
Definition: history_local.c:74
struct DiskObject * amiga_icon_from_bitmap(struct bitmap *bm)
Definition: icon.c:521
void amiga_icon_free(struct DiskObject *dobj)
Definition: icon.c:569
void amiga_icon_superimpose_favicon_internal(struct hlcache_handle *icon, struct DiskObject *dobj)
Definition: icon.c:390
Content for image/x-amiga-icon (icon.library interface).
#define amiga_icon_init()
Definition: icon.h:36
struct fbtk_bitmap reload_g
struct fbtk_bitmap reload
Public content interface.
struct bitmap * content_get_bitmap(struct hlcache_handle *h)
Retrieve the bitmap contained in an image content.
Definition: content.c:1264
Interface to platform-specific fetcher operations.
Interface to platform-specific miscellaneous browser operation table.
Core mouse and pointer states.
browser_mouse_state
Mouse state: 1 is primary mouse button.
Definition: mouse.h:52
@ BROWSER_MOUSE_PRESS_1
primary button pressed
Definition: mouse.h:59
@ BROWSER_MOUSE_CLICK_2
button 2 clicked.
Definition: mouse.h:72
@ BROWSER_MOUSE_PRESS_2
auxillary button pressed
Definition: mouse.h:61
@ BROWSER_MOUSE_TRIPLE_CLICK
button triple clicked
Definition: mouse.h:83
@ BROWSER_MOUSE_CLICK_1
button 1 clicked.
Definition: mouse.h:70
@ BROWSER_MOUSE_MOD_2
2nd modifier key pressed (eg.
Definition: mouse.h:101
@ BROWSER_MOUSE_DOUBLE_CLICK
button double clicked
Definition: mouse.h:81
@ BROWSER_MOUSE_MOD_3
3rd modifier key pressed (eg.
Definition: mouse.h:103
@ BROWSER_MOUSE_MOD_1
1st modifier key pressed (eg.
Definition: mouse.h:99
@ BROWSER_MOUSE_DRAG_1
start of button 1 drag
Definition: mouse.h:86
@ BROWSER_MOUSE_HOLDING_2
during button 2 drag
Definition: mouse.h:96
@ BROWSER_MOUSE_HOLDING_1
during button 1 drag
Definition: mouse.h:94
@ BROWSER_MOUSE_DRAG_ON
a drag operation was started and a mouse button is still pressed
Definition: mouse.h:91
@ BROWSER_MOUSE_DRAG_2
start of button 2 drag
Definition: mouse.h:88
gui_pointer_shape
Definition: mouse.h:112
@ GUI_POINTER_WAIT
Definition: mouse.h:127
@ GUI_POINTER_DEFAULT
Definition: mouse.h:113
Interface to platform-specific graphical user interface window operations.
gui_window_create_flags
Window creation control flags.
Definition: window.h:66
@ GW_CREATE_TAB
Create tab in same window as existing.
Definition: window.h:69
gui_drag_type
Definition: window.h:56
@ GDRAGGING_NONE
Definition: window.h:57
@ GDRAGGING_SCROLLBAR
Definition: window.h:58
@ GDRAGGING_OTHER
Definition: window.h:60
gui_window_event
Window events.
Definition: window.h:80
@ GW_EVENT_PAGE_INFO_CHANGE
Page status has changed and so the padlock should be updated.
Definition: window.h:129
@ GW_EVENT_REMOVE_CARET
Remove the caret, if present.
Definition: window.h:98
@ GW_EVENT_NEW_CONTENT
Called when the gui_window has new content.
Definition: window.h:118
@ GW_EVENT_STOP_THROBBER
stop the navigation throbber.
Definition: window.h:108
@ GW_EVENT_UPDATE_EXTENT
Update the extent of the inside of a browser window to that of the current content.
Definition: window.h:93
@ GW_EVENT_START_SELECTION
selection started
Definition: window.h:123
@ GW_EVENT_START_THROBBER
start the navigation throbber.
Definition: window.h:103
Interface to key press operations.
@ NS_KEY_REDO
Definition: keypress.h:71
@ NS_KEY_DELETE_LINE_START
Definition: keypress.h:68
@ NS_KEY_SHIFT_TAB
Definition: keypress.h:39
@ NS_KEY_LINE_START
Definition: keypress.h:57
@ NS_KEY_RIGHT
Definition: keypress.h:51
@ NS_KEY_LEFT
Definition: keypress.h:50
@ NS_KEY_SELECT_ALL
Definition: keypress.h:32
@ NS_KEY_PASTE
Definition: keypress.h:43
@ NS_KEY_TAB
Definition: keypress.h:36
@ NS_KEY_COPY_SELECTION
Definition: keypress.h:33
@ NS_KEY_DOWN
Definition: keypress.h:53
@ NS_KEY_CUT_SELECTION
Definition: keypress.h:44
@ NS_KEY_WORD_LEFT
Definition: keypress.h:61
@ NS_KEY_DELETE_LINE_END
Definition: keypress.h:67
@ NS_KEY_PAGE_UP
Definition: keypress.h:65
@ NS_KEY_PAGE_DOWN
Definition: keypress.h:66
@ NS_KEY_UNDO
Definition: keypress.h:70
@ NS_KEY_TEXT_START
Definition: keypress.h:59
@ NS_KEY_LINE_END
Definition: keypress.h:58
@ NS_KEY_TEXT_END
Definition: keypress.h:60
@ NS_KEY_DELETE_RIGHT
Definition: keypress.h:55
@ NS_KEY_CLEAR_SELECTION
Definition: keypress.h:45
@ NS_KEY_WORD_RIGHT
Definition: keypress.h:63
@ NS_KEY_DELETE_LEFT
Definition: keypress.h:35
@ NS_KEY_UP
Definition: keypress.h:52
@ NS_KEY_ESCAPE
Definition: keypress.h:47
bool browser_window_key_press(struct browser_window *bw, uint32_t key)
Handle key presses in a browser window.
Definition: textinput.c:107
void ami_openurl_open(void)
Initialise the fetcher.
Definition: launch.c:127
void ami_openurl_close(void)
Definition: launch.c:140
Fetching of data from a URL (Registration).
bool ami_libs_open(void)
Definition: libs.c:221
void ami_libs_close(void)
Definition: libs.c:301
#define SpeedBarObj
Definition: libs.h:75
#define LayoutHObj
Definition: libs.h:64
#define ListBrowserObj
Definition: libs.h:66
#define LabelObj
Definition: libs.h:63
#define WindowObj
Definition: libs.h:77
#define BitMapObj
Definition: libs.h:53
#define ChooserObj
Definition: libs.h:56
#define LayoutVObj
Definition: libs.h:65
#define ScrollerObj
Definition: libs.h:73
#define SpaceObj
Definition: libs.h:74
#define ButtonObj
Definition: libs.h:54
#define BevelObj
Definition: libs.h:52
#define StringObj
Definition: libs.h:76
#define ClickTabObj
Definition: libs.h:57
nserror nslog_init(nslog_ensure_t *ensure, int *pargc, char **argv)
Initialise the logging system.
Definition: log.c:190
void nslog_finalise(void)
Shut down the logging system.
Definition: log.c:299
#define NSLOG(catname, level, logmsg, args...)
Definition: log.h:116
void ami_memory_fini(struct Interrupt *memhandler)
Definition: memory.c:179
struct Interrupt * ami_memory_init(void)
Definition: memory.c:165
#define ami_memory_itempool_create(s)
Definition: memory.h:54
#define ami_memory_itempool_alloc(p, s)
Definition: memory.h:56
#define ami_memory_itempool_free(p, i, s)
Definition: memory.h:57
#define ami_memory_itempool_delete(p)
Definition: memory.h:55
nserror messages_add_from_file(const char *path)
Read keys and values from messages file into the standard Messages hash.
Definition: messages.c:177
const char * messages_get_errorcode(nserror code)
lookup of a message by errorcode from the standard Messages hash.
Definition: messages.c:248
const char * messages_get(const char *key)
Fast lookup of a message by key from the standard Messages hash.
Definition: messages.c:241
Localised message support (interface).
NetSurf core interface registration, construction and destruction.
void netsurf_exit(void)
Finalise NetSurf core.
Definition: netsurf.c:232
nserror netsurf_init(const char *store_path)
Initialise netsurf core.
Definition: netsurf.c:107
nserror netsurf_register(struct netsurf_table *table)
Register operation table.
Definition: gui_factory.c:777
NetSurf URL handling (interface).
nserror nsurl_get_utf8(const nsurl *url, char **url_s, size_t *url_l)
Get a UTF-8 string (for human readable IDNs) from a NetSurf URL object.
nserror nsurl_create(const char *const url_s, nsurl **url)
Create a NetSurf URL object from a URL string.
void nsurl_unref(nsurl *url)
Drop a reference to a NetSurf URL object.
uint32_t nsurl_hash(const nsurl *url)
Get a URL's hash value.
const char * nsurl_access(const nsurl *url)
Access a NetSurf URL object as a string.
struct nsurl nsurl
NetSurf URL object.
Definition: nsurl.h:31
struct Node * GetPred(struct Node *node)
Definition: os3support.c:375
void FreeSysObject(ULONG type, APTR obj)
Definition: os3support.c:350
APTR NewObject(struct IClass *classPtr, CONST_STRPTR classID, ULONG tagList,...)
Definition: os3support.c:434
char * ASPrintf(const char *fmt,...)
Definition: os3support.c:139
uint32 GetAttrs(Object *obj, Tag tag1,...)
Definition: os3support.c:389
struct Node * GetHead(struct List *list)
Definition: os3support.c:364
ULONG RefreshSetGadgetAttrs(struct Gadget *g, struct Window *w, struct Requester *r, Tag tag1,...)
Definition: os3support.c:429
struct Node * GetSucc(struct Node *node)
Definition: os3support.c:381
#define AllocSysObjectTags(A, B, C, D)
Definition: os3support.h:157
#define LBS_ROWS
Definition: os3support.h:128
#define MINTERM_SRCMASK
Definition: os3support.h:139
#define SetCurrentDir(L)
Definition: os3support.h:161
#define RAWKEY_DEL
Definition: os3support.h:99
#define LBNCA_SoftStyle
Definition: os3support.h:82
#define RAWKEY_BACKSPACE
Definition: os3support.h:96
#define RAWKEY_F12
Definition: os3support.h:110
#define LIB_IS_AT_LEAST(B, V, R)
Definition: os3support.h:55
#define DN_FULLPATH
Definition: os3support.h:123
#define RAWKEY_PAGEUP
Definition: os3support.h:100
#define TNA_HintInfo
Definition: os3support.h:88
#define RAWKEY_ESC
Definition: os3support.h:98
#define RAWKEY_CRSRRIGHT
Definition: os3support.h:104
#define ASO_NoTrack
Definition: os3support.h:64
#define GA_ContextMenu
Definition: os3support.h:77
#define CLICKTAB_LabelTruncate
Definition: os3support.h:71
#define RAWKEY_F8
Definition: os3support.h:107
#define WINDOW_NewPrefsHook
Definition: os3support.h:93
#define WA_ContextMenuHook
Definition: os3support.h:89
#define WINDOW_BuiltInScroll
Definition: os3support.h:91
#define RAWKEY_END
Definition: os3support.h:113
#define IDoMethod
Definition: os3support.h:169
#define CLICKTAB_FlagImage
Definition: os3support.h:70
#define RAWKEY_F10
Definition: os3support.h:109
#define RPTAG_APenColor
Definition: os3support.h:76
#define RAWKEY_HOME
Definition: os3support.h:112
#define BITMAP_HasAlpha
Definition: os3support.h:66
#define RAWKEY_CRSRUP
Definition: os3support.h:102
#define RAWKEY_TAB
Definition: os3support.h:97
#define CLICKTAB_CloseImage
Definition: os3support.h:69
#define RAWKEY_F9
Definition: os3support.h:108
#define RAWKEY_CRSRLEFT
Definition: os3support.h:105
#define IDCMP_EXTENDEDMOUSE
Definition: os3support.h:121
#define IA_InBorder
Definition: os3support.h:80
#define SBNA_HintInfo
Definition: os3support.h:86
#define BLITA_UseSrcAlpha
Definition: os3support.h:67
#define BLITA_MaskPlane
Definition: os3support.h:68
#define CLICKTAB_NodeClosed
Definition: os3support.h:72
#define GAUGEIA_Level
Definition: os3support.h:79
#define DevNameFromLock(A, B, C, D)
Definition: os3support.h:162
#define IA_Label
Definition: os3support.h:81
#define RAWKEY_CRSRDOWN
Definition: os3support.h:103
#define BITMAP_DisabledSourceFile
Definition: os3support.h:65
#define RAWKEY_HELP
Definition: os3support.h:111
#define DISABLEDTEXTPEN
Definition: os3support.h:116
@ ASOT_PORT
Definition: os3support.h:226
#define GA_HintInfo
Definition: os3support.h:78
#define FOpen(A, B, C)
Definition: os3support.h:158
int32_t int32
Definition: os3support.h:183
#define ObtainCharsetInfo(A, B, C)
Definition: os3support.h:154
uint16_t uint16
Definition: os3support.h:182
#define IsMinListEmpty(L)
Definition: os3support.h:54
#define TNA_CloseGadget
Definition: os3support.h:87
uint32_t uint32
Definition: os3support.h:184
#define RAWKEY_PAGEDOWN
Definition: os3support.h:101
#define ShowWindow(...)
Definition: os3support.h:172
#define LISTBROWSER_Striping
Definition: os3support.h:83
#define WINDOW_BACKMOST
Definition: os3support.h:122
#define CreateDirTree(D)
Definition: os3support.h:160
#define WA_ToolBox
Definition: os3support.h:90
#define RAWKEY_F5
Definition: os3support.h:106
#define FClose(A)
Definition: os3support.h:159
#define SA_Compositing
Definition: os3support.h:84
nserror amiga_plugin_hack_init(void)
Definition: plugin_hack.c:75
int width
Definition: gui.c:160
static nserror gui_launch_url(struct nsurl *url)
Broadcast an URL that we can't handle.
Definition: gui.c:2034
int height
Definition: gui.c:161
void save_complete_init(void)
Initialise save complete module.
Save HTML document with dependencies (interface).
core web search facilities interface.
@ SEARCH_WEB_OMNI_NONE
no changes to default operation
Definition: searchweb.h:50
@ SEARCH_WEB_OMNI_SEARCHONLY
The search does not attempt to interpret the url as a url before using it as a search term.
Definition: searchweb.h:55
void gui_create_form_select_menu(struct gui_window *g, struct form_control *control)
Definition: selectmenu.c:190
Interface to utility string handling.
Class * MakeStringClass(void)
#define STRINGVIEW_Header
Definition: stringview.h:50
void FreeStringClass(Class *)
struct nsObject * node
Definition: gui.h:74
const struct ami_win_event_table * tbl
Definition: gui.h:75
struct gui_window_2 * gw
Definition: gui.c:323
struct List * sblist
Definition: gui.c:322
Amiga local history viewing window context.
Definition: history_local.c:57
struct gui_window * gw
Amiga GUI stuff.
Definition: history_local.c:62
BOOL(* event)(void *w)
Definition: gui.h:65
void(* close)(void *w)
Definition: gui.h:70
RISC OS wimp toolkit bitmap.
Definition: bitmap.c:68
Page features at a specific spatial location.
enum browser_window_features::@56 form_features
type of form feature.
Browser window data.
struct browser_window * bw
Form control.
Definition: form_internal.h:73
function table for fetcher operations.
Definition: fetch.h:33
const char *(* filetype)(const char *unix_path)
Determine the MIME type of a local file.
Definition: fetch.h:45
Graphical user interface browser misc function table.
Definition: misc.h:39
nserror(* schedule)(int t, void(*callback)(void *p), void *p)
Schedule a callback.
Definition: misc.h:58
Graphical user interface browser web search function table.
Definition: searchweb.h:34
nserror(* provider_update)(const char *provider_name, struct bitmap *ico_bitmap)
called when the search provider details are updated.
Definition: searchweb.h:42
User interface utf8 characterset conversion routines.
Definition: utf8.h:31
browser_mouse_state mouse_state
Definition: gui.c:258
char *restrict helphints[GID_LAST]
Definition: gui.c:277
browser_mouse_state prev_mouse_state
Definition: gui.c:278
int throbber_frame
Definition: gui.c:252
Object *restrict objects[GID_LAST]
Definition: gui.c:249
struct List hotlist_toolbar_list
Definition: gui.c:270
bool closed
Definition: gui.c:294
char *restrict wintitle
Definition: gui.c:275
ULONG oldh
Definition: gui.c:262
Object *restrict hotlist_toolbar_lab[AMI_GUI_TOOLBAR_MAX]
Definition: gui.c:269
ULONG tabs
Definition: gui.c:254
struct ami_menu_data * menu_data[AMI_MENU_AREXX_MAX+1]
Definition: gui.c:267
ULONG oldv
Definition: gui.c:263
gui_pointer_shape mouse_pointer
Definition: gui.c:292
Object * search_bm
Definition: gui.c:272
char *restrict status
Definition: gui.c:274
gui_drag_type drag_op
Definition: gui.c:288
struct DiskObject * dobj
Definition: gui.c:281
browser_mouse_state key_state
Definition: gui.c:259
ULONG hotlist_items
Definition: gui.c:268
struct find_window * searchwin
Definition: gui.c:261
ULONG next_tab
Definition: gui.c:255
struct Hook * ctxmenu_hook
Definition: gui.c:285
struct Menu * imenu
Definition: gui.c:293
struct Hook throbber_hook
Definition: gui.c:283
char icontitle[24]
Definition: gui.c:276
bool new_content
Definition: gui.c:266
Object * clicktab_ctxmenu
Definition: gui.c:287
struct ami_generic_window w
Definition: gui.c:247
struct List * web_search_list
Definition: gui.c:271
struct gui_window * gw
Definition: gui.c:250
ULONG throbber_update_count
Definition: gui.c:260
struct AppIcon * appicon
Definition: gui.c:280
struct Hook browser_hook
Definition: gui.c:284
struct Hook scrollerhook
Definition: gui.c:257
struct Node * last_new_tab
Definition: gui.c:256
Object *restrict history_ctxmenu[2]
Definition: gui.c:286
bool redraw_scroll
Definition: gui.c:265
struct AppWindow * appwin
Definition: gui.c:290
struct timeval lastclick
Definition: gui.c:279
struct List tab_list
Definition: gui.c:253
int temp
Definition: gui.c:264
struct Hook favicon_hook
Definition: gui.c:282
struct IBox * ptr_lock
Definition: gui.c:289
struct MinList * shared_pens
Definition: gui.c:291
char *restrict svbuffer
Definition: gui.c:273
struct Window * win
Definition: gui.c:248
bool redraw_required
Definition: gui.c:251
Graphical user interface window function table.
Definition: window.h:137
struct gui_window *(* create)(struct browser_window *bw, struct gui_window *existing, gui_window_create_flags flags)
Create and open a gui window for a browsing context.
Definition: window.h:164
first entry in window list
Definition: gui.c:298
int c_h_temp
Definition: gui.c:306
struct gui_window_2 * shared
Definition: gui.c:299
bool throbbing
whether currently throbbing
Definition: gui.c:312
struct ColumnInfo * logcolumns
Definition: gui.c:317
char * tabtitle
Definition: gui.c:313
struct MinList * deferred_rects
Definition: gui.c:315
char * url
Definition: gui.h:154
APTR deferred_rects_pool
Definition: gui.c:314
int scrollx
current scroll location
Definition: gui.c:307
int tab
Definition: gui.c:300
struct List loglist
Definition: gui.c:318
int c_y
Definition: gui.c:303
struct List dllist
Definition: gui.c:310
struct hlcache_handle * favicon
Definition: gui.c:311
struct fbtk_widget_s * stop
Definition: gui.h:37
struct ami_history_local_window * hw
Definition: gui.c:309
int c_h
Definition: gui.c:305
struct Node * tab_node
Definition: gui.c:301
int scrolly
current scroll location
Definition: gui.c:308
int c_x
Definition: gui.c:302
int c_w
Definition: gui.c:304
struct browser_window * bw
The 'content' window that is rendered in the gui_window.
Definition: gui.c:316
High-level cache handle.
Definition: hlcache.c:66
NetSurf operation function table.
Definition: gui_table.h:48
struct gui_misc_table * misc
Browser table.
Definition: gui_table.h:57
ULONG Type
Definition: object.h:45
void * objstruct
Definition: object.h:46
union nsoption_s::@149 value
colour c
Definition: nsoption.h:120
Rectangle coordinates.
Definition: types.h:40
int x0
Definition: types.h:41
int y0
Top left.
Definition: types.h:41
int x1
Definition: types.h:42
int y1
Bottom right.
Definition: types.h:42
Redraw context.
Definition: plotters.h:51
bool interactive
Redraw to show interactive features.
Definition: plotters.h:59
void * priv
Private context.
Definition: plotters.h:81
Definition: theme.h:64
uint32_t colour
Colour type: XBGR.
Definition: types.h:35
struct rect rect
Rectangle coordinates.
static int mouse_x
Definition: url_complete.c:66
static int mouse_y
Definition: url_complete.c:67
Unified URL information database public interface.
nserror urldb_save(const char *filename)
Export the current database to file.
Definition: urldb.c:3094
nserror urldb_load(const char *filename)
Import an URL database from file, replacing any existing database.
Definition: urldb.c:2876
struct List * URLHistory_GetList(void)
nserror netsurf_path_to_nsurl(const char *path, struct nsurl **url)
Create a nsurl from a path.
Definition: file.c:307
nserror netsurf_mkpath(char **str, size_t *size, size_t nelm,...)
Generate a path from one or more component elemnts.
Definition: file.c:288
Default operations table for files.
struct nsoption_s * nsoptions_default
global default option table.
Definition: nsoption.c:46
static struct nsoption_s defaults[]
The table of compiled in default options.
Definition: nsoption.c:64
struct nsoption_s * nsoptions
global active option table.
Definition: nsoption.c:45
nserror nsoption_commandline(int *pargc, char **argv, struct nsoption_s *opts)
Process commandline and set options approriately.
Definition: nsoption.c:856
nserror nsoption_init(nsoption_set_default_t *set_defaults, struct nsoption_s **popts, struct nsoption_s **pdefs)
Initialise option system.
Definition: nsoption.c:608
nserror nsoption_finalise(struct nsoption_s *opts, struct nsoption_s *defs)
Finalise option system.
Definition: nsoption.c:663
Option reading and saving interface.
#define nsoption_charp(OPTION)
Get the value of a string option.
Definition: nsoption.h:331
#define nsoption_setnull_charp(OPTION, VALUE)
set string option in default table if currently unset
Definition: nsoption.h:376
#define nsoption_int(OPTION)
Get the value of an integer option.
Definition: nsoption.h:313
#define nsoption_set_int(OPTION, VALUE)
set an integer option in the default table
Definition: nsoption.h:348
nsoption_e
Definition: nsoption.h:131
#define nsoption_set_bool(OPTION, VALUE)
set a boolean option in the default table
Definition: nsoption.h:344
#define nsoption_set_charp(OPTION, VALUE)
set string option in default table
Definition: nsoption.h:372
@ OPTION_COLOUR
Option is a netsurf colour.
Definition: nsoption.h:107
#define nsoption_bool(OPTION)
Get the value of a boolean option.
Definition: nsoption.h:304
uint32_t utf8_to_ucs4(const char *s_in, size_t l)
Convert a UTF-8 multibyte sequence into a single UCS4 character.
Definition: utf8.c:41
size_t utf8_char_byte_length(const char *s)
Calculate the length (in bytes) of a UTF-8 character.
Definition: utf8.c:104
UTF-8 manipulation functions (interface).
Interface to a number of general purpose functionality.
Version information interface.
static nserror path(const struct redraw_context *ctx, const plot_style_t *pstyle, const float *p, unsigned int n, const float transform[6])
Plots a path.
Definition: plot.c:821
static nserror text(const struct redraw_context *ctx, const struct plot_font_style *fstyle, int x, int y, const char *text, size_t length)
Text plotting.
Definition: plot.c:978
static nserror clip(const struct redraw_context *ctx, const struct rect *clip)
Sets a clip rectangle for subsequent plot operations.
Definition: plot.c:357