1 /* Sessions action management */
11 #include "bookmarks/dialogs.h"
12 #include "cache/dialogs.h"
13 #include "config/conf.h"
14 #include "config/dialogs.h"
15 #include "config/kbdbind.h"
16 #include "config/options.h"
17 #include "cookies/cookies.h"
18 #include "cookies/dialogs.h"
19 #include "dialogs/document.h"
20 #include "dialogs/download.h"
21 #include "dialogs/exmode.h"
22 #include "dialogs/info.h"
23 #include "dialogs/menu.h"
24 #include "dialogs/options.h"
25 #include "dialogs/status.h"
26 #include "document/document.h"
27 #include "document/view.h"
28 #include "formhist/dialogs.h"
29 #include "globhist/dialogs.h"
30 #include "main/main.h"
31 #include "network/connection.h"
32 #include "protocol/auth/auth.h"
33 #include "protocol/auth/dialogs.h"
34 #include "terminal/tab.h"
35 #include "terminal/terminal.h"
36 #include "terminal/window.h"
37 #include "session/history.h"
38 #include "session/session.h"
39 #include "session/task.h"
40 #include "viewer/action.h"
41 #include "viewer/text/draw.h"
42 #include "viewer/text/form.h"
43 #include "viewer/text/link.h"
44 #include "viewer/text/search.h"
45 #include "viewer/text/view.h"
48 goto_url_action(struct session
*ses
,
49 unsigned char *(*get_url
)(struct session
*, unsigned char *, size_t))
51 unsigned char url
[MAX_STR_LEN
];
53 if (!get_url
|| !get_url(ses
, url
, sizeof(url
)))
56 dialog_goto_url(ses
, url
);
59 /* This could gradually become some multiplexor / switch noodle containing
60 * most if not all default handling of actions (for the main mapping) that
61 * frame_ev() and/or send_event() could use as a backend. */
62 /* Many execution paths may lead to this code so it needs to take appropriate
63 * precausions to stuff like doc_view and doc_view->vs being NULL. */
64 enum frame_event_status
65 do_action(struct session
*ses
, enum main_action action_id
, int verbose
)
67 enum frame_event_status status
= FRAME_EVENT_OK
;
68 struct terminal
*term
= ses
->tab
->term
;
69 struct document_view
*doc_view
= current_frame(ses
);
70 struct link
*link
= NULL
;
72 if (action_id
== -1) goto unknown_action
;
74 if (doc_view
&& doc_view
->vs
) {
75 if (action_prefix_is_link_number(KEYMAP_MAIN
, action_id
)
76 && !try_jump_to_link_number(ses
, doc_view
))
79 link
= get_current_link(doc_view
);
81 } else if (action_requires_view_state(KEYMAP_MAIN
, action_id
)) {
85 if (action_requires_location(KEYMAP_MAIN
, action_id
)
86 && !have_location(ses
))
87 return FRAME_EVENT_OK
;
89 if (action_requires_link(KEYMAP_MAIN
, action_id
)
93 if (action_requires_form(KEYMAP_MAIN
, action_id
)
94 && (!link
|| !link_is_form(link
)))
97 if (!action_is_anonymous_safe(KEYMAP_MAIN
, action_id
)
98 && get_cmd_opt_bool("anonymous"))
101 /* Please keep in alphabetical order for now. Later we can sort by most
102 * used or something. */
104 case ACT_MAIN_ABORT_CONNECTION
:
105 abort_loading(ses
, 1);
106 print_screen_status(ses
);
109 case ACT_MAIN_ADD_BOOKMARK
:
110 #ifdef CONFIG_BOOKMARKS
111 launch_bm_add_doc_dialog(term
, NULL
, ses
);
114 case ACT_MAIN_ADD_BOOKMARK_LINK
:
115 #ifdef CONFIG_BOOKMARKS
116 launch_bm_add_link_dialog(term
, NULL
, ses
);
119 case ACT_MAIN_ADD_BOOKMARK_TABS
:
120 #ifdef CONFIG_BOOKMARKS
121 bookmark_terminal_tabs_dialog(term
);
125 case ACT_MAIN_AUTH_MANAGER
:
129 case ACT_MAIN_BACKSPACE_PREFIX
:
131 if (!ses
->kbdprefix
.repeat_count
) break;
133 set_kbd_repeat_count(ses
,
134 ses
->kbdprefix
.repeat_count
/ 10);
136 /* Keep send_event from resetting repeat_count. */
137 status
= FRAME_EVENT_SESSION_DESTROYED
;
141 case ACT_MAIN_BOOKMARK_MANAGER
:
142 #ifdef CONFIG_BOOKMARKS
143 bookmark_manager(ses
);
147 case ACT_MAIN_CACHE_MANAGER
:
151 case ACT_MAIN_CACHE_MINIMIZE
:
155 case ACT_MAIN_COOKIES_LOAD
:
156 #ifdef CONFIG_COOKIES
157 if (!get_opt_bool("cookies.save", NULL
)) break;
162 case ACT_MAIN_COOKIE_MANAGER
:
163 #ifdef CONFIG_COOKIES
168 case ACT_MAIN_COPY_CLIPBOARD
:
169 status
= copy_current_link_to_clipboard(ses
, doc_view
, 0);
172 case ACT_MAIN_DOCUMENT_INFO
:
173 document_info_dialog(ses
);
176 case ACT_MAIN_DOWNLOAD_MANAGER
:
177 download_manager(ses
);
180 case ACT_MAIN_EXMODE
:
186 case ACT_MAIN_FILE_MENU
:
187 activate_bfu_technology(ses
, 0);
190 case ACT_MAIN_FIND_NEXT
:
191 status
= find_next(ses
, doc_view
, 1);
194 case ACT_MAIN_FIND_NEXT_BACK
:
195 status
= find_next(ses
, doc_view
, -1);
198 case ACT_MAIN_FORGET_CREDENTIALS
:
200 shrink_memory(1); /* flush caches */
203 case ACT_MAIN_FORMHIST_MANAGER
:
204 #ifdef CONFIG_FORMHIST
205 formhist_manager(ses
);
209 case ACT_MAIN_FRAME_EXTERNAL_COMMAND
:
210 status
= pass_uri_to_command(ses
, doc_view
,
214 case ACT_MAIN_FRAME_NEXT
:
216 draw_formatted(ses
, 0);
219 case ACT_MAIN_FRAME_MAXIMIZE
:
220 status
= set_frame(ses
, doc_view
, 0);
223 case ACT_MAIN_FRAME_PREV
:
225 draw_formatted(ses
, 0);
228 case ACT_MAIN_GOTO_URL
:
229 goto_url_action(ses
, NULL
);
232 case ACT_MAIN_GOTO_URL_CURRENT
:
233 goto_url_action(ses
, get_current_url
);
236 case ACT_MAIN_GOTO_URL_CURRENT_LINK
:
237 goto_url_action(ses
, get_current_link_url
);
240 case ACT_MAIN_GOTO_URL_HOME
:
244 case ACT_MAIN_HEADER_INFO
:
245 protocol_header_dialog(ses
);
248 case ACT_MAIN_HISTORY_MANAGER
:
249 #ifdef CONFIG_GLOBHIST
250 history_manager(ses
);
254 case ACT_MAIN_HISTORY_MOVE_BACK
:
256 int count
= int_max(1, eat_kbd_repeat_count(ses
));
258 go_history_by_n(ses
, -count
);
261 case ACT_MAIN_HISTORY_MOVE_FORWARD
:
263 int count
= int_max(1, eat_kbd_repeat_count(ses
));
265 go_history_by_n(ses
, count
);
268 case ACT_MAIN_JUMP_TO_LINK
:
271 case ACT_MAIN_KEYBINDING_MANAGER
:
272 keybinding_manager(ses
);
275 case ACT_MAIN_KILL_BACKGROUNDED_CONNECTIONS
:
276 abort_background_connections();
279 case ACT_MAIN_LINK_DIALOG
:
280 open_link_dialog(ses
);
283 case ACT_MAIN_LINK_DOWNLOAD
:
284 case ACT_MAIN_LINK_DOWNLOAD_IMAGE
:
285 case ACT_MAIN_LINK_DOWNLOAD_RESUME
:
286 status
= download_link(ses
, doc_view
, action_id
);
289 case ACT_MAIN_LINK_EXTERNAL_COMMAND
:
290 status
= pass_uri_to_command(ses
, doc_view
,
294 case ACT_MAIN_LINK_FOLLOW
:
295 status
= enter(ses
, doc_view
, 0);
298 case ACT_MAIN_LINK_FOLLOW_RELOAD
:
299 status
= enter(ses
, doc_view
, 1);
302 case ACT_MAIN_LINK_INFO
:
303 link_info_dialog(ses
);
306 case ACT_MAIN_LINK_MENU
:
307 link_menu(term
, NULL
, ses
);
310 case ACT_MAIN_LINK_FORM_MENU
:
314 case ACT_MAIN_LUA_CONSOLE
:
315 #ifdef CONFIG_SCRIPTING_LUA
316 trigger_event_name("dialog-lua-console", ses
);
320 case ACT_MAIN_MARK_SET
:
322 ses
->kbdprefix
.mark
= KP_MARK_SET
;
323 status
= FRAME_EVENT_REFRESH
;
327 case ACT_MAIN_MARK_GOTO
:
329 /* TODO: Show promptly a menu (or even listbox?)
330 * with all the marks. But the next letter must
331 * still choose a mark directly! --pasky */
332 ses
->kbdprefix
.mark
= KP_MARK_GOTO
;
333 status
= FRAME_EVENT_REFRESH
;
338 activate_bfu_technology(ses
, -1);
341 case ACT_MAIN_MOVE_CURRENT_TOP
:
342 status
= move_current_top(ses
, doc_view
);
345 case ACT_MAIN_MOVE_CURSOR_UP
:
346 status
= move_cursor_up(ses
, doc_view
);
349 case ACT_MAIN_MOVE_CURSOR_DOWN
:
350 status
= move_cursor_down(ses
, doc_view
);
353 case ACT_MAIN_MOVE_CURSOR_LEFT
:
354 status
= move_cursor_left(ses
, doc_view
);
357 case ACT_MAIN_MOVE_CURSOR_RIGHT
:
358 status
= move_cursor_right(ses
, doc_view
);
361 case ACT_MAIN_MOVE_CURSOR_LINE_START
:
362 status
= move_cursor_line_start(ses
, doc_view
);
365 case ACT_MAIN_MOVE_HALF_PAGE_DOWN
:
366 status
= move_half_page_down(ses
, doc_view
);
369 case ACT_MAIN_MOVE_HALF_PAGE_UP
:
370 status
= move_half_page_up(ses
, doc_view
);
373 case ACT_MAIN_MOVE_LINK_DOWN
:
374 status
= move_link_down(ses
, doc_view
);
377 case ACT_MAIN_MOVE_LINK_DOWN_LINE
:
378 status
= move_link_down_line(ses
, doc_view
);
381 case ACT_MAIN_MOVE_LINK_LEFT
:
382 status
= move_link_left(ses
, doc_view
);
385 case ACT_MAIN_MOVE_LINK_LEFT_LINE
:
386 status
= move_link_prev_line(ses
, doc_view
);
389 case ACT_MAIN_MOVE_LINK_NEXT
:
390 status
= move_link_next(ses
, doc_view
);
393 case ACT_MAIN_MOVE_LINK_PREV
:
394 status
= move_link_prev(ses
, doc_view
);
397 case ACT_MAIN_MOVE_LINK_RIGHT
:
398 status
= move_link_right(ses
, doc_view
);
401 case ACT_MAIN_MOVE_LINK_RIGHT_LINE
:
402 status
= move_link_next_line(ses
, doc_view
);
405 case ACT_MAIN_MOVE_LINK_UP
:
406 status
= move_link_up(ses
, doc_view
);
409 case ACT_MAIN_MOVE_LINK_UP_LINE
:
410 status
= move_link_up_line(ses
, doc_view
);
413 case ACT_MAIN_MOVE_PAGE_DOWN
:
414 status
= move_page_down(ses
, doc_view
);
417 case ACT_MAIN_MOVE_PAGE_UP
:
418 status
= move_page_up(ses
, doc_view
);
421 case ACT_MAIN_MOVE_DOCUMENT_START
:
422 status
= move_document_start(ses
, doc_view
);
425 case ACT_MAIN_MOVE_DOCUMENT_END
:
426 status
= move_document_end(ses
, doc_view
);
429 case ACT_MAIN_OPEN_LINK_IN_NEW_TAB
:
430 open_current_link_in_new_tab(ses
, 0);
433 case ACT_MAIN_OPEN_LINK_IN_NEW_TAB_IN_BACKGROUND
:
434 open_current_link_in_new_tab(ses
, 1);
437 case ACT_MAIN_OPEN_LINK_IN_NEW_WINDOW
:
438 open_in_new_window(term
, send_open_in_new_window
, ses
);
441 case ACT_MAIN_OPEN_NEW_TAB
:
442 open_uri_in_new_tab(ses
, NULL
, 0, 1);
445 case ACT_MAIN_OPEN_NEW_TAB_IN_BACKGROUND
:
446 open_uri_in_new_tab(ses
, NULL
, 1, 1);
449 case ACT_MAIN_OPEN_NEW_WINDOW
:
450 open_in_new_window(term
, send_open_new_window
, ses
);
453 case ACT_MAIN_OPEN_OS_SHELL
:
457 case ACT_MAIN_OPTIONS_MANAGER
:
458 options_manager(ses
);
465 case ACT_MAIN_REALLY_QUIT
:
469 case ACT_MAIN_REDRAW
:
470 redraw_terminal_cls(term
);
473 case ACT_MAIN_RELOAD
:
474 reload(ses
, CACHE_MODE_INCREMENT
);
477 case ACT_MAIN_RERENDER
:
478 draw_formatted(ses
, 2);
481 case ACT_MAIN_RESET_FORM
:
482 status
= reset_form(ses
, doc_view
, 0);
485 case ACT_MAIN_RESOURCE_INFO
:
489 case ACT_MAIN_SAVE_AS
:
490 status
= save_as(ses
, doc_view
, 0);
493 case ACT_MAIN_SAVE_FORMATTED
:
494 status
= save_formatted_dlg(ses
, doc_view
, 0);
497 case ACT_MAIN_SAVE_OPTIONS
:
501 case ACT_MAIN_SAVE_URL_AS
:
505 case ACT_MAIN_SCROLL_DOWN
:
506 status
= scroll_down(ses
, doc_view
);
509 case ACT_MAIN_SCROLL_LEFT
:
510 status
= scroll_left(ses
, doc_view
);
513 case ACT_MAIN_SCROLL_RIGHT
:
514 status
= scroll_right(ses
, doc_view
);
517 case ACT_MAIN_SCROLL_UP
:
518 status
= scroll_up(ses
, doc_view
);
521 case ACT_MAIN_SEARCH
:
522 status
= search_dlg(ses
, doc_view
, 1);
525 case ACT_MAIN_SEARCH_BACK
:
526 status
= search_dlg(ses
, doc_view
, -1);
529 case ACT_MAIN_SEARCH_TYPEAHEAD
:
530 case ACT_MAIN_SEARCH_TYPEAHEAD_LINK
:
531 case ACT_MAIN_SEARCH_TYPEAHEAD_TEXT
:
532 case ACT_MAIN_SEARCH_TYPEAHEAD_TEXT_BACK
:
533 status
= search_typeahead(ses
, doc_view
, action_id
);
536 case ACT_MAIN_SHOW_TERM_OPTIONS
:
537 terminal_options(term
, NULL
, ses
);
540 case ACT_MAIN_SUBMIT_FORM
:
541 status
= submit_form(ses
, doc_view
, 0);
544 case ACT_MAIN_SUBMIT_FORM_RELOAD
:
545 status
= submit_form(ses
, doc_view
, 1);
548 case ACT_MAIN_TAB_CLOSE
:
549 close_tab(term
, ses
);
550 status
= FRAME_EVENT_SESSION_DESTROYED
;
553 case ACT_MAIN_TAB_CLOSE_ALL_BUT_CURRENT
:
554 close_all_tabs_but_current(ses
);
557 case ACT_MAIN_TAB_EXTERNAL_COMMAND
:
558 status
= pass_uri_to_command(ses
, doc_view
,
562 case ACT_MAIN_TAB_MOVE_LEFT
:
563 move_current_tab(ses
, -1);
566 case ACT_MAIN_TAB_MOVE_RIGHT
:
567 move_current_tab(ses
, 1);
570 case ACT_MAIN_TAB_MENU
:
571 assert(ses
->tab
== get_current_tab(term
));
573 if (ses
->status
.show_tabs_bar
)
574 tab_menu(ses
, ses
->tab
->xpos
,
576 - ses
->status
.show_status_bar
,
579 tab_menu(ses
, 0, 0, 0);
583 case ACT_MAIN_TAB_NEXT
:
584 switch_current_tab(ses
, 1);
587 case ACT_MAIN_TAB_PREV
:
588 switch_current_tab(ses
, -1);
591 case ACT_MAIN_TERMINAL_RESIZE
:
592 resize_terminal_dialog(term
);
595 case ACT_MAIN_TOGGLE_CSS
:
597 toggle_document_option(ses
, "document.css.enable");
601 case ACT_MAIN_TOGGLE_DISPLAY_IMAGES
:
602 toggle_document_option(ses
, "document.browse.images.show_as_links");
605 case ACT_MAIN_TOGGLE_DISPLAY_TABLES
:
606 toggle_document_option(ses
, "document.html.display_tables");
609 case ACT_MAIN_TOGGLE_DOCUMENT_COLORS
:
610 toggle_document_option(ses
, "document.colors.use_document_colors");
613 case ACT_MAIN_TOGGLE_HTML_PLAIN
:
614 toggle_plain_html(ses
, ses
->doc_view
, 0);
617 case ACT_MAIN_TOGGLE_MOUSE
:
623 case ACT_MAIN_TOGGLE_NUMBERED_LINKS
:
624 toggle_document_option(ses
, "document.browse.links.numbering");
627 case ACT_MAIN_TOGGLE_PLAIN_COMPRESS_EMPTY_LINES
:
628 toggle_document_option(ses
, "document.plain.compress_empty_lines");
631 case ACT_MAIN_TOGGLE_WRAP_TEXT
:
632 toggle_wrap_text(ses
, ses
->doc_view
, 0);
635 case ACT_MAIN_VIEW_IMAGE
:
636 status
= view_image(ses
, doc_view
, 0);
639 case ACT_MAIN_SCRIPTING_FUNCTION
:
645 INTERNAL("No action handling defined for '%s'.",
646 get_action_name(KEYMAP_MAIN
, action_id
));
649 status
= FRAME_EVENT_IGNORED
;
653 /* XXX: At this point the session may have been destroyed */
655 if (status
!= FRAME_EVENT_SESSION_DESTROYED
656 && ses
->insert_mode
== INSERT_MODE_ON
657 && link
!= get_current_link(doc_view
))
658 ses
->insert_mode
= INSERT_MODE_OFF
;
660 if (status
== FRAME_EVENT_REFRESH
&& doc_view
)
661 refresh_view(ses
, doc_view
, 0);