Add a couple of context menu items for links for testing.

This commit is contained in:
Chris Young 2015-09-03 19:57:04 +01:00
parent 944248ce32
commit cdaae7b30e
4 changed files with 161 additions and 41 deletions

View File

@ -23,29 +23,43 @@
#ifdef __amigaos4__
#include <string.h>
#include <proto/exec.h>
#include <proto/intuition.h>
#include <classes/window.h>
#include <proto/bitmap.h>
#include <images/bitmap.h>
#include <proto/window.h>
#include <classes/window.h>
#include <intuition/menuclass.h>
#include <reaction/reaction_macros.h>
#include "amiga/ctxmenu.h"
#include "amiga/gui.h"
#include "amiga/libs.h"
#include "amiga/theme.h"
#include "amiga/utf8.h"
#include "desktop/browser.h"
#include "desktop/mouse.h"
#include "utils/log.h"
#include "utils/messages.h"
#include "utils/nsoption.h"
enum {
AMI_CTX_ID_TEST = 1,
AMI_CTX_ID_URLOPEN,
AMI_CTX_ID_URLOPENWIN,
AMI_CTX_ID_URLOPENTAB,
AMI_CTX_ID_MAX
};
static Object *ctxmenu_obj = NULL;
static struct Hook ctxmenu_hook;
static struct Hook ctxmenu_item_hook[AMI_CTX_ID_MAX];
static char *ctxmenu_item_label[AMI_CTX_ID_MAX];
static char *ctxmenu_item_image[AMI_CTX_ID_MAX];
static Object *ctxmenu_item_image[AMI_CTX_ID_MAX];
/** Menu functions - called automatically by RA_HandleInput **/
HOOKF(void, ami_ctxmenu_item_test, APTR, window, struct IntuiMessage *)
@ -53,57 +67,143 @@ HOOKF(void, ami_ctxmenu_item_test, APTR, window, struct IntuiMessage *)
printf("testing\n");
}
/** Hook function called by Intuition, creates context menu structure **/
static uint32 ctxmenu_hook_func(struct Hook *hook, struct Window *window, struct ContextMenuMsg *msg)
HOOKF(void, ami_ctxmenu_item_urlopentab, APTR, window, struct IntuiMessage *)
{
if(msg->State != CM_QUERY) return 0;
struct browser_window *bw;
nsurl *url = (nsurl *)hook->h_Data;
struct gui_window_2 *gwin;
ctxmenu_item_hook[AMI_CTX_ID_TEST].h_Entry = (void *)ami_ctxmenu_item_test;
ctxmenu_item_hook[AMI_CTX_ID_TEST].h_Data = 0;
GetAttr(WINDOW_UserData, (Object *)window, (ULONG *)&gwin);
nserror error = browser_window_create(BW_CREATE_CLONE | BW_CREATE_HISTORY | BW_CREATE_TAB,
url,
browser_window_get_url(gwin->gw->bw),
gwin->gw->bw,
&bw);
if (error != NSERROR_OK)
warn_user(messages_get_errorcode(error), 0);
}
HOOKF(void, ami_ctxmenu_item_urlopenwin, APTR, window, struct IntuiMessage *)
{
struct browser_window *bw;
nsurl *url = (nsurl *)hook->h_Data;
struct gui_window_2 *gwin;
GetAttr(WINDOW_UserData, (Object *)window, (ULONG *)&gwin);
nserror error = browser_window_create(BW_CREATE_CLONE | BW_CREATE_HISTORY,
url,
browser_window_get_url(gwin->gw->bw),
gwin->gw->bw,
&bw);
if (error != NSERROR_OK)
warn_user(messages_get_errorcode(error), 0);
}
/** Add an initialised item to a context menu **/
static void ami_ctxmenu_add_item(Object *root_menu, int id, APTR data)
{
ctxmenu_item_hook[id].h_Data = data;
IDoMethod(root_menu, OM_ADDMEMBER, MStrip,
MA_Type, T_ITEM,
MA_Label, ctxmenu_item_label[id],
MA_ID, id,
MA_Image, ctxmenu_item_image[id],
MA_UserData, &ctxmenu_item_hook[id],
MEnd);
}
/** Hook function called by Intuition, creates context menu structure **/
static uint32 ami_ctxmenu_hook_func(struct Hook *hook, struct Window *window, struct ContextMenuMsg *msg)
{
Object *root_menu;
bool ctxmenu_has_content = false;
struct gui_window_2 *gwin = hook->h_Data;
struct hlcache_handle *cc = browser_window_get_content(gwin->gw->bw);
struct browser_window_features ccdata;
int mx = window->MouseX;
int my = window->MouseY;
int x, y;
if(msg->State != CM_QUERY) return 0;
if(nsoption_bool(kiosk_mode) == true) return 0;
// check window is active
if(ctxmenu_obj != NULL) DisposeObject(ctxmenu_obj);
ctxmenu_obj = MStrip,
MA_Type, T_ROOT,
MA_AddChild, MStrip,
MA_AddChild, root_menu = MStrip,
MA_Type, T_MENU,
MA_Label, NULL, //"NetSurf",
MA_AddChild, MStrip,
MA_Type, T_ITEM,
MA_Label, ctxmenu_item_label[AMI_CTX_ID_TEST],
MA_ID, AMI_CTX_ID_TEST,
MA_Image, BitMapObj,
IA_Scalable, TRUE,
BITMAP_SourceFile, ctxmenu_item_image[AMI_CTX_ID_TEST],
BITMAP_Screen, scrn,
BITMAP_Masking, TRUE,
BITMAP_Width, 16,
BITMAP_Height, 16,
BitMapEnd,
MA_UserData, &ctxmenu_item_hook[AMI_CTX_ID_TEST],
MEnd,
MA_EmbeddedKey, FALSE,
MA_FreeImage, FALSE,
MEnd,
MEnd;
msg->Menu = ctxmenu_obj;
if(ami_mouse_to_ns_coords(gwin, &x, &y, mx, my) == false) {
/* Outside browser render area */
return 0;
}
browser_window_get_features(gwin->gw->bw, x, y, &ccdata);
if(ccdata.link) {
ami_ctxmenu_add_item(root_menu, AMI_CTX_ID_URLOPENTAB, ccdata.link);
ami_ctxmenu_add_item(root_menu, AMI_CTX_ID_URLOPENWIN, ccdata.link);
ctxmenu_has_content = true;
}
if(ctxmenu_has_content == true) {
msg->Menu = ctxmenu_obj;
ami_set_pointer(gwin, GUI_POINTER_DEFAULT, false);
}
return 0;
}
/** Exported interface documented in ctxmenu.h **/
struct Hook *ami_ctxmenu_get_hook(void)
/** Initial menu item creation **/
static void ami_ctxmenu_alloc_item(int id, const char *label, const char *image, void *func)
{
return &ctxmenu_hook;
ctxmenu_item_label[id] = ami_utf8_easy(messages_get(label));
ctxmenu_item_image[id] = BitMapObj,
BITMAP_Screen, scrn,
BITMAP_SourceFile, image,
BITMAP_Masking, TRUE,
BitMapEnd;
SetAttrs(ctxmenu_item_image[id],
BITMAP_Width, 16,
BITMAP_Height, 16,
TAG_DONE);
ctxmenu_item_hook[id].h_Entry = func;
ctxmenu_item_hook[id].h_Data = 0;
}
/** Exported interface documented in ctxmenu.h **/
struct Hook *ami_ctxmenu_get_hook(APTR data)
{
return AllocSysObjectTags(ASOT_HOOK,
ASOHOOK_Entry, (HOOKFUNC)ami_ctxmenu_hook_func,
ASOHOOK_Data, data,
TAG_DONE);
}
/** Exported interface documented in ctxmenu.h **/
void ami_ctxmenu_release_hook(struct Hook *hook)
{
FreeSysObject(ASOT_HOOK, hook);
}
/** Exported interface documented in ctxmenu.h **/
void ami_ctxmenu_init(void)
{
ctxmenu_hook.h_Entry = (HOOKFUNC)ctxmenu_hook_func;
ctxmenu_hook.h_Data = 0;
ctxmenu_item_label[AMI_CTX_ID_TEST] = strdup("test item");
ctxmenu_item_image[AMI_CTX_ID_TEST] = strdup("TBimages:list_info");
ami_ctxmenu_alloc_item(AMI_CTX_ID_URLOPENWIN, "LinkNewWin", "TBImages:list_app", ami_ctxmenu_item_urlopenwin);
ami_ctxmenu_alloc_item(AMI_CTX_ID_URLOPENTAB, "LinkNewTab", "TBImages:list_add", ami_ctxmenu_item_urlopentab);
}
/** Exported interface documented in ctxmenu.h **/
@ -111,11 +211,12 @@ void ami_ctxmenu_free(void)
{
for(int i = 1; i < AMI_CTX_ID_MAX; i++) {
if(ctxmenu_item_label[i] != NULL) {
free(ctxmenu_item_label[i]);
ami_utf8_free(ctxmenu_item_label[i]);
ctxmenu_item_label[i] = NULL;
}
if(ctxmenu_item_image[i] != NULL) {
free(ctxmenu_item_image[i]);
DisposeObject(ctxmenu_item_image[i]);
ctxmenu_item_image[i] = NULL;
}
}

View File

@ -26,7 +26,8 @@
struct Hook;
/**
* Initialise context menus code
* Initialise context menus code (allocate label text, etc)
* Must be called *after* NetSurf's screen pointer is obtained.
*/
void ami_ctxmenu_init(void);
@ -38,8 +39,20 @@ void ami_ctxmenu_free(void);
/**
* Get a Hook for WA_ContextMenuHook
*
* \param data ptr for the hook to use (struct gui_window_2 *)
* \returns pointer to a struct Hook
*/
struct Hook *ami_ctxmenu_get_hook(void);
#endif
struct Hook *ami_ctxmenu_get_hook(APTR data);
/**
* Release a Hook for WA_ContextMenuHook
*
* \param hook ptr to hook
*/
void ami_ctxmenu_release_hook(struct Hook *hook);
#else
inline void ami_ctxmenu_init(void) {}
inline void ami_ctxmenu_free(void) {}
inline struct Hook *ami_ctxmenu_get_hook(APTR data) {return NULL;}
inline void ami_ctxmenu_release_hook(struct Hook *hook) {}
#endif

View File

@ -1318,7 +1318,7 @@ static bool ami_spacebox_to_ns_coords(struct gui_window_2 *gwin, int *x, int *y,
return true;
}
static bool ami_mouse_to_ns_coords(struct gui_window_2 *gwin, int *x, int *y,
bool ami_mouse_to_ns_coords(struct gui_window_2 *gwin, int *x, int *y,
int mouse_x, int mouse_y)
{
int ns_x, ns_y;
@ -3769,6 +3769,8 @@ gui_window_create(struct browser_window *bw,
newprefs_hook.h_Entry = (void *)ami_gui_newprefs_hook;
newprefs_hook.h_Data = 0;
g->shared->ctxmenu_hook = ami_ctxmenu_get_hook(g->shared);
if(nsoption_bool(window_simple_refresh) == true) {
refresh_mode = WA_SimpleRefresh;
@ -3932,7 +3934,7 @@ gui_window_create(struct browser_window *bw,
WA_ReportMouse,TRUE,
refresh_mode, TRUE,
WA_SizeBBottom, TRUE,
WA_ContextMenuHook, ami_ctxmenu_get_hook(),
WA_ContextMenuHook, g->shared->ctxmenu_hook,
WA_IDCMP, IDCMP_MENUPICK | IDCMP_MOUSEMOVE |
IDCMP_MOUSEBUTTONS | IDCMP_NEWSIZE |
IDCMP_RAWKEY | idcmp_sizeverify |
@ -4376,7 +4378,6 @@ static void gui_window_destroy(struct gui_window *g)
DisposeObject(g->shared->objects[OID_MAIN]);
ami_gui_appicon_remove(g->shared);
if(g->shared->appwin) RemoveAppWindow(g->shared->appwin);
ami_gui_hotlist_toolbar_free(g->shared, &g->shared->hotlist_toolbar_list);
/* These aren't freed by the above.
@ -4390,6 +4391,7 @@ static void gui_window_destroy(struct gui_window *g)
ami_gui_opts_websearch_free(g->shared->web_search_list);
if(g->shared->search_bm) DisposeObject(g->shared->search_bm);
ami_ctxmenu_release_hook(g->shared->ctxmenu_hook);
ami_free_menulabs(g->shared);
#ifndef __amigaos4__
ami_menu_free_os3(g->shared);
@ -5433,7 +5435,6 @@ int main(int argc, char** argv)
ami_amiupdate(); /* set env-vars for AmiUpdate */
ami_init_fonts();
ami_context_menu_init();
ami_ctxmenu_init();
save_complete_init();
ami_theme_init();
ami_init_mouse_pointers();
@ -5449,6 +5450,8 @@ int main(int argc, char** argv)
gui_init2(argc, argv);
ami_ctxmenu_init(); /* Requires screen pointer */
ami_gui_splash_close(splash_window);
strlcpy(script, nsoption_charp(arexx_dir), 1024);

3
amiga/gui.h Executable file → Normal file
View File

@ -132,6 +132,7 @@ struct gui_window_2 {
struct DiskObject *dobj; /* iconify appicon */
struct Hook favicon_hook;
struct Hook throbber_hook;
struct Hook *ctxmenu_hook;
gui_drag_type drag_op;
struct IBox *ptr_lock;
struct AppWindow *appwin;
@ -174,6 +175,8 @@ void ami_schedule_redraw(struct gui_window_2 *gwin, bool full_redraw);
STRPTR ami_locale_langs(void);
int ami_key_to_nskey(ULONG keycode, struct InputEvent *ie);
bool ami_text_box_at_point(struct gui_window_2 *gwin, ULONG *x, ULONG *y);
bool ami_mouse_to_ns_coords(struct gui_window_2 *gwin, int *x, int *y,
int mouse_x, int mouse_y);
BOOL ami_gadget_hit(Object *obj, int x, int y);
void ami_gui_history(struct gui_window_2 *gwin, bool back);
void ami_gui_hotlist_update_all(void);