static void composer_move_caret (EMsgComposer *composer) { EHTMLEditor *editor; EHTMLEditorView *view; EHTMLEditorSelection *editor_selection; GSettings *settings; gboolean start_bottom, top_signature; gboolean is_message_from_draft; gboolean is_message_from_edit_as_new; gboolean has_paragraphs_in_body = TRUE; WebKitDOMDocument *document; WebKitDOMElement *element, *signature; WebKitDOMHTMLElement *body; WebKitDOMNodeList *list; /* When there is an option composer-reply-start-bottom set we have * to move the caret between reply and signature. */ settings = e_util_ref_settings ("org.gnome.evolution.mail"); start_bottom = g_settings_get_boolean (settings, "composer-reply-start-bottom"); g_object_unref (settings); editor = e_msg_composer_get_editor (composer); view = e_html_editor_get_view (editor); editor_selection = e_html_editor_view_get_selection (view); is_message_from_draft = e_html_editor_view_is_message_from_draft (view); is_message_from_edit_as_new = e_html_editor_view_is_message_from_edit_as_new (view); top_signature = use_top_signature (composer) && !is_message_from_edit_as_new && !composer->priv->is_from_new_message; document = webkit_web_view_get_dom_document (WEBKIT_WEB_VIEW (view)); body = webkit_dom_document_get_body (document); webkit_dom_element_set_attribute ( WEBKIT_DOM_ELEMENT (body), "data-message", "", NULL); /* If editing message as new don't handle with caret */ if (is_message_from_edit_as_new || is_message_from_draft) { if (is_message_from_edit_as_new) webkit_dom_element_set_attribute ( WEBKIT_DOM_ELEMENT (body), "data-edit-as-new", "", NULL); if (is_message_from_edit_as_new && !is_message_from_draft) { element = WEBKIT_DOM_ELEMENT (body); e_html_editor_selection_block_selection_changed (editor_selection); goto move_caret; } else e_html_editor_selection_scroll_to_caret (editor_selection); return; } e_html_editor_selection_block_selection_changed (editor_selection); /* When the new message is written from the beginning - note it into body */ if (composer->priv->is_from_new_message) webkit_dom_element_set_attribute ( WEBKIT_DOM_ELEMENT (body), "data-new-message", "", NULL); list = webkit_dom_document_get_elements_by_class_name (document, "-x-evo-paragraph"); signature = webkit_dom_document_query_selector (document, ".-x-evo-signature-wrapper", NULL); /* Situation when wrapped paragraph is just in signature and not in message body */ if (webkit_dom_node_list_get_length (list) == 1) if (signature && webkit_dom_element_query_selector (signature, ".-x-evo-paragraph", NULL)) has_paragraphs_in_body = FALSE; /* * * Keeping Signatures in the beginning of composer * ------------------------------------------------ * * Purists are gonna blast me for this. * But there are so many people (read Outlook users) who want this. * And Evo is an exchange-client, Outlook-replacement etc. * So Here it goes :( * * -- Sankar * */ if (signature && top_signature) { WebKitDOMElement *spacer; spacer = prepare_top_signature_spacer (editor_selection, document); webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (spacer), webkit_dom_node_get_next_sibling (WEBKIT_DOM_NODE (signature)), NULL); } if (webkit_dom_node_list_get_length (list) == 0) has_paragraphs_in_body = FALSE; element = webkit_dom_document_get_element_by_id (document, "-x-evo-input-start"); if (!signature) { if (start_bottom) { if (!element) { element = prepare_paragraph (editor_selection, document); webkit_dom_node_append_child ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), NULL); } } else element = WEBKIT_DOM_ELEMENT (body); g_object_unref (list); goto move_caret; } if (!has_paragraphs_in_body) { element = prepare_paragraph (editor_selection, document); if (top_signature) { if (start_bottom) { webkit_dom_node_append_child ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), NULL); } else { webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), WEBKIT_DOM_NODE (signature), NULL); } } else { if (start_bottom) webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), WEBKIT_DOM_NODE (signature), NULL); else element = WEBKIT_DOM_ELEMENT (body); } } else { if (!element && top_signature) { element = prepare_paragraph (editor_selection, document); if (start_bottom) { webkit_dom_node_append_child ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), NULL); } else { webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), WEBKIT_DOM_NODE (signature), NULL); } } else if (element && top_signature && !start_bottom) { webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), WEBKIT_DOM_NODE (signature), NULL); } else if (element && start_bottom) { /* Leave it how it is */ } else element = WEBKIT_DOM_ELEMENT (body); } g_object_unref (list); move_caret: if (element) { WebKitDOMDOMSelection *dom_selection; WebKitDOMDOMWindow *dom_window; WebKitDOMRange *range; dom_window = webkit_dom_document_get_default_view (document); dom_selection = webkit_dom_dom_window_get_selection (dom_window); range = webkit_dom_document_create_range (document); webkit_dom_range_select_node_contents ( range, WEBKIT_DOM_NODE (element), NULL); webkit_dom_range_collapse (range, TRUE, NULL); webkit_dom_dom_selection_remove_all_ranges (dom_selection); webkit_dom_dom_selection_add_range (dom_selection, range); g_clear_object (&dom_selection); g_clear_object (&dom_window); g_clear_object (&range); if (start_bottom) e_html_editor_selection_scroll_to_caret (editor_selection); } if (start_bottom) g_signal_connect ( view, "size-allocate", G_CALLBACK (composer_size_allocate_cb), NULL); e_html_editor_view_force_spell_check_in_viewport (view); e_html_editor_selection_unblock_selection_changed (editor_selection); }
/** * Add observers to doc event for given document and all the contained iframes * too. */ static void add_onload_event_observers(WebKitDOMDocument *doc, WebKitWebPage *page) { WebKitDOMEventTarget *target; /* Add the document to the table of known documents or if already exists * return to not apply observers multiple times. */ if (!g_hash_table_add(ext.documents, doc)) { return; } /* We have to use default view instead of the document itself in case this * function is called with content document of an iframe. Else the event * observing does not work. */ target = WEBKIT_DOM_EVENT_TARGET(webkit_dom_document_get_default_view(doc)); webkit_dom_event_target_add_event_listener(target, "focus", G_CALLBACK(on_editable_change_focus), TRUE, page); webkit_dom_event_target_add_event_listener(target, "blur", G_CALLBACK(on_editable_change_focus), TRUE, page); /* Check for focused editable elements also if they where focused before * the event observer where set up. */ /* TODO this is not needed for strict-focus=on */ on_editable_change_focus(target, NULL, page); /* Observe scroll events to get current position in the document. */ webkit_dom_event_target_add_event_listener(target, "scroll", G_CALLBACK(on_document_scroll), FALSE, page); /* Call the callback explicitly to make sure we have the right position * shown in statusbar also in cases the user does not scroll. */ on_document_scroll(target, NULL, page); }
static void load_status_callback(WebKitWebView* webView, GParamSpec* spec, DomDomviewFixture* fixture) { WebKitLoadStatus status = webkit_web_view_get_load_status(webView); if (status == WEBKIT_LOAD_FINISHED) { WebKitDOMDocument* document; WebKitDOMDOMWindow* domWindow; WebKitDOMElement* element; WebKitDOMEvent* event; glong clientX, clientY; document = webkit_web_view_get_dom_document(WEBKIT_WEB_VIEW(fixture->webView)); g_assert(document); domWindow = webkit_dom_document_get_default_view(document); g_assert(domWindow); fixture->domWindow = domWindow; element = webkit_dom_document_get_element_by_id(document, "test"); g_assert(element); event = webkit_dom_document_create_event(document, "MouseEvent", NULL); g_assert(event); g_assert(WEBKIT_DOM_IS_EVENT(event)); g_assert(WEBKIT_DOM_IS_MOUSE_EVENT(event)); clientX = webkit_dom_element_get_client_left(element); clientY = webkit_dom_element_get_client_top(element); webkit_dom_mouse_event_init_mouse_event(WEBKIT_DOM_MOUSE_EVENT(event), "click", TRUE, TRUE, fixture->domWindow, 0, 0, 0, clientX, clientY, FALSE, FALSE, FALSE, FALSE, 1, WEBKIT_DOM_EVENT_TARGET(element)); webkit_dom_event_target_add_event_listener(WEBKIT_DOM_EVENT_TARGET(element), "click", G_CALLBACK(clicked_cb), false, fixture); g_assert(fixture->clicked == FALSE); webkit_dom_event_target_dispatch_event(WEBKIT_DOM_EVENT_TARGET(element), event, NULL); } }
void plugins_create_click_element(WebKitDOMElement *element, GList *gl) { WebKitDOMNode *parent = webkit_dom_node_get_parent_node(WEBKIT_DOM_NODE(element)); View *v = VIEW(gl); WebKitDOMElement *div; if (parent == NULL) return; WebKitDOMDocument *doc = webkit_dom_node_get_owner_document(WEBKIT_DOM_NODE(element)); WebKitDOMDOMWindow *win = webkit_dom_document_get_default_view(doc); WebKitDOMCSSStyleDeclaration *style = webkit_dom_dom_window_get_computed_style(win, element, ""); char *width = webkit_dom_css_style_declaration_get_property_value(style, "width"); char *height = webkit_dom_css_style_declaration_get_property_value(style, "height"); char *top = webkit_dom_css_style_declaration_get_property_value(style, "top"); char *left = webkit_dom_css_style_declaration_get_property_value(style, "left"); char *position = webkit_dom_css_style_declaration_get_property_value(style, "position"); int w, h; if (sscanf(width, "%dpx", &w) == 1 && w<72) w = 72; if (sscanf(height, "%dpx", &h) == 1 && h<24) h = 24; if (v->plugins->max <= v->plugins->created) { div = webkit_dom_document_create_element(doc, "div", NULL); v->plugins->clicks = g_slist_prepend(v->plugins->clicks, div); v->plugins->max++; } else div = g_slist_nth_data(v->plugins->clicks, v->plugins->created); webkit_dom_html_element_set_inner_html(WEBKIT_DOM_HTML_ELEMENT(div), "<div style='display:table-cell;vertical-align:middle;text-align:center;color:#fff;background:#000;border:1px solid #666;font:11px monospace bold'>click to enable flash</div>", NULL); char *new_style = g_strdup_printf("position:%s;width:%dpx;height:%dpx;top:%s;left:%s;display:table;z-index:37000;", position, w, h, top, left); webkit_dom_element_set_attribute(div, "style", new_style, NULL); g_free(new_style); webkit_dom_element_set_attribute(div, "onclick", "return", NULL); g_object_set_data((gpointer)div, "dwb-plugin-element", element); webkit_dom_node_remove_child(parent, WEBKIT_DOM_NODE(element), NULL); webkit_dom_node_append_child(parent, WEBKIT_DOM_NODE(div), NULL); v->plugins->elements = g_slist_prepend(v->plugins->elements, element); webkit_dom_event_target_add_event_listener(WEBKIT_DOM_EVENT_TARGET(div), "click", G_CALLBACK(plugins_onclick_cb), true, gl); g_object_unref(style); g_object_unref(parent); v->plugins->created++; }
// frame_document_loaded watches signals emitted from the given document. static void frame_document_loaded(WebKitDOMDocument *doc, Exten *exten) { // Track document, and don't register multiple times. if(!g_hash_table_add(exten->registered_documents, doc)) { return; } WebKitDOMEventTarget *target = WEBKIT_DOM_EVENT_TARGET( webkit_dom_document_get_default_view(doc)); // listen for focus changes webkit_dom_event_target_add_event_listener( target, "blur", G_CALLBACK(active_element_change_cb), true, exten); webkit_dom_event_target_add_event_listener( target, "focus", G_CALLBACK(active_element_change_cb), true, exten); // listen for resource loads. webkit_dom_event_target_add_event_listener( target, "beforeload", G_CALLBACK(adblock_before_load_cb), true, exten); // Scan for existing iframes, and add them as new frames. WebKitDOMNodeList *nodes = webkit_dom_document_get_elements_by_tag_name( WEBKIT_DOM_DOCUMENT(doc), "IFRAME"); gulong i; gulong len; if(nodes == NULL) { len = 0; } else { len = webkit_dom_node_list_get_length(nodes); } for(i = 0; i < len; i++) { WebKitDOMDocument *subdoc = webkit_dom_html_iframe_element_get_content_document( WEBKIT_DOM_HTML_IFRAME_ELEMENT( webkit_dom_node_list_item(nodes, i))); frame_document_loaded(subdoc, exten); } // Element hider inject_adblock_css(doc, exten); }
void plugins_load_status_cb(WebKitWebView *wv, GParamSpec *p, GList *gl) { WebKitLoadStatus status = webkit_web_view_get_load_status(wv); if (status == WEBKIT_LOAD_COMMITTED) { WebKitDOMDocument *doc = webkit_web_view_get_dom_document(wv); WebKitDOMDOMWindow *win = webkit_dom_document_get_default_view(doc); webkit_dom_event_target_add_event_listener(WEBKIT_DOM_EVENT_TARGET(win), "beforeload", G_CALLBACK(plugins_before_load_cb), true, gl); webkit_dom_event_target_add_event_listener(WEBKIT_DOM_EVENT_TARGET(win), "beforeunload", G_CALLBACK(plugins_before_unload_cb), true, gl); } }
void wxWebViewWebKit::ClearSelection() { WebKitDOMDocument* doc; WebKitDOMDOMWindow* win; WebKitDOMDOMSelection* sel; doc = webkit_web_view_get_dom_document(WEBKIT_WEB_VIEW(web_view)); win = webkit_dom_document_get_default_view(WEBKIT_DOM_DOCUMENT(doc)); sel = webkit_dom_dom_window_get_selection(WEBKIT_DOM_DOM_WINDOW(win)); webkit_dom_dom_selection_remove_all_ranges(WEBKIT_DOM_DOM_SELECTION(sel)); }
wxString wxWebViewWebKit::GetSelectedText() const { WebKitDOMDocument* doc; WebKitDOMDOMWindow* win; WebKitDOMDOMSelection* sel; WebKitDOMRange* range; doc = webkit_web_view_get_dom_document(WEBKIT_WEB_VIEW(web_view)); win = webkit_dom_document_get_default_view(WEBKIT_DOM_DOCUMENT(doc)); sel = webkit_dom_dom_window_get_selection(WEBKIT_DOM_DOM_WINDOW(win)); range = webkit_dom_dom_selection_get_range_at(WEBKIT_DOM_DOM_SELECTION(sel), 0, NULL); return wxString(webkit_dom_range_get_text(WEBKIT_DOM_RANGE(range)), wxConvUTF8); }
/** * Callback called if a editable element changes it focus state. * Event target may be a WebKitDOMDocument (in case of iframe) or a * WebKitDOMDOMWindow. */ static void on_editable_change_focus(WebKitDOMEventTarget *target, WebKitDOMEvent *event, WebKitWebPage *page) { WebKitDOMDocument *doc; WebKitDOMDOMWindow *dom_window; WebKitDOMElement *active; GVariant *variant; char *message; if (WEBKIT_DOM_IS_DOM_WINDOW(target)) { g_object_get(target, "document", &doc, NULL); } else { /* target is a doc document */ doc = WEBKIT_DOM_DOCUMENT(target); } dom_window = webkit_dom_document_get_default_view(doc); if (!dom_window) { return; } active = webkit_dom_document_get_active_element(doc); /* Don't do anything if there is no active element */ if (!active) { return; } if (WEBKIT_DOM_IS_HTML_IFRAME_ELEMENT(active)) { WebKitDOMHTMLIFrameElement *iframe; WebKitDOMDocument *subdoc; iframe = WEBKIT_DOM_HTML_IFRAME_ELEMENT(active); subdoc = webkit_dom_html_iframe_element_get_content_document(iframe); add_onload_event_observers(subdoc, page); return; } /* Check if the active element is an editable element. */ variant = g_variant_new("(tb)", webkit_web_page_get_id(page), ext_dom_is_editable(active)); message = g_variant_print(variant, FALSE); g_variant_unref(variant); if (!webkit_dom_dom_window_webkit_message_handlers_post_message(dom_window, "focus", message)) { g_warning("Error sending focus message"); } g_free(message); g_object_unref(dom_window); }
static void documentLoadedCallback(WebKitWebPage* webPage, WebKitWebExtension* extension) { // FIXME: Too much code just to send a message, we need convenient custom API for this. WebKitDOMDocument* document = webkit_web_page_get_dom_document(webPage); GRefPtr<WebKitDOMDOMWindow> window = adoptGRef(webkit_dom_document_get_default_view(document)); if (WebKitDOMWebKitNamespace* webkit = webkit_dom_dom_window_get_webkit_namespace(window.get())) { WebKitDOMUserMessageHandlersNamespace* messageHandlers = webkit_dom_webkit_namespace_get_message_handlers(webkit); if (WebKitDOMUserMessageHandler* handler = webkit_dom_user_message_handlers_namespace_get_handler(messageHandlers, "dom")) webkit_dom_user_message_handler_post_message(handler, "DocumentLoaded", nullptr); } webkit_dom_dom_window_webkit_message_handlers_post_message(window.get(), "dom-convenience", "DocumentLoaded"); gpointer data = g_object_get_data(G_OBJECT(extension), "dbus-connection"); if (data) emitDocumentLoaded(G_DBUS_CONNECTION(data)); else delayedSignalsQueue.append(DelayedSignal(DocumentLoadedSignal)); }
static gint get_caret_position (EHTMLEditorView *view) { WebKitDOMDocument *document; WebKitDOMDOMWindow *window; WebKitDOMDOMSelection *selection; WebKitDOMRange *range; gint range_count; WebKitDOMNodeList *nodes; gulong ii, length; document = webkit_web_view_get_dom_document (WEBKIT_WEB_VIEW (view)); window = webkit_dom_document_get_default_view (document); selection = webkit_dom_dom_window_get_selection (window); if (webkit_dom_dom_selection_get_range_count (selection) < 1) return 0; range = webkit_dom_dom_selection_get_range_at (selection, 0, NULL); range_count = 0; nodes = webkit_dom_node_get_child_nodes ( webkit_dom_node_get_parent_node ( webkit_dom_dom_selection_get_anchor_node ( selection))); length = webkit_dom_node_list_get_length (nodes); for (ii = 0; ii < length; ii++) { WebKitDOMNode *node; node = webkit_dom_node_list_item (nodes, ii); if (webkit_dom_node_is_same_node ( node, webkit_dom_dom_selection_get_anchor_node (selection))) { break; } else if (WEBKIT_DOM_IS_TEXT (node)) { gchar *text = webkit_dom_node_get_text_content (node); range_count += strlen (text); g_free (text); } } g_object_unref (nodes); return webkit_dom_range_get_start_offset (range, NULL) + range_count; }
static WebKitDOMRange * editor_selection_get_current_range (EEditorSelection *selection) { WebKitDOMDocument *document; WebKitDOMDOMWindow *window; WebKitDOMDOMSelection *dom_selection; document = webkit_web_view_get_dom_document (selection->priv->webview); window = webkit_dom_document_get_default_view (document); if (!window) return NULL; dom_selection = webkit_dom_dom_window_get_selection (window); if (webkit_dom_dom_selection_get_range_count (dom_selection) < 1) return NULL; return webkit_dom_dom_selection_get_range_at (dom_selection, 0, NULL); }
/** * Set focus to the first found editable element and returns if a element was * found to focus. */ gboolean dom_focus_input(WebKitWebView *view) { gboolean found = false; WebKitDOMNode *html, *node; WebKitDOMDocument *doc; WebKitDOMDOMWindow *win; WebKitDOMNodeList *list; WebKitDOMXPathNSResolver *resolver; WebKitDOMXPathResult* result; doc = webkit_web_view_get_dom_document(view); win = webkit_dom_document_get_default_view(doc); list = webkit_dom_document_get_elements_by_tag_name(doc, "html"); if (!list) { return false; } html = webkit_dom_node_list_item(list, 0); resolver = webkit_dom_document_create_ns_resolver(doc, html); if (!resolver) { return false; } result = webkit_dom_document_evaluate( doc, "//input[not(@type) or @type='text' or @type='password']|//textarea", html, resolver, 0, NULL, NULL ); if (!result) { return false; } while ((node = webkit_dom_xpath_result_iterate_next(result, NULL))) { if (element_is_visible(win, WEBKIT_DOM_ELEMENT(node))) { webkit_dom_element_focus(WEBKIT_DOM_ELEMENT(node)); found = true; break; } } g_object_unref(list); return found; }
void e_editor_selection_replace_caret_word (EEditorSelection *selection, const gchar *replacement) { WebKitDOMDocument *document; WebKitDOMDOMWindow *window; WebKitDOMDOMSelection *dom_selection; WebKitDOMRange *range; g_return_if_fail (E_IS_EDITOR_SELECTION (selection)); g_return_if_fail (replacement); range = editor_selection_get_current_range (selection); document = webkit_web_view_get_dom_document (selection->priv->webview); window = webkit_dom_document_get_default_view (document); dom_selection = webkit_dom_dom_window_get_selection (window); webkit_dom_range_expand (range, "word", NULL); webkit_dom_dom_selection_add_range (dom_selection, range); e_editor_selection_insert_html (selection, replacement); }
static void test_dom_domview_signals(DomDomviewFixture* fixture, gconstpointer data) { g_assert(fixture); WebKitWebView* view = (WebKitWebView*)fixture->webView; g_assert(view); WebKitDOMDocument* document = webkit_web_view_get_dom_document(view); g_assert(document); WebKitDOMDOMWindow* domWindow = webkit_dom_document_get_default_view(document); g_assert(domWindow); fixture->domWindow = domWindow; webkit_dom_event_target_add_event_listener(WEBKIT_DOM_EVENT_TARGET(fixture->domWindow), "load", G_CALLBACK(loadedCallback), false, fixture); g_signal_connect(fixture->window, "map-event", G_CALLBACK(map_event_cb), fixture); g_signal_connect(fixture->webView, "notify::load-status", G_CALLBACK(load_event_callback), fixture); gtk_widget_show_all(fixture->window); gtk_window_present(GTK_WINDOW(fixture->window)); g_main_loop_run(fixture->loop); g_assert(fixture->loaded); g_assert(fixture->clicked); }
wxString wxWebViewWebKit::GetSelectedSource() const { WebKitDOMDocument* doc; WebKitDOMDOMWindow* win; WebKitDOMDOMSelection* sel; WebKitDOMRange* range; WebKitDOMElement* div; WebKitDOMDocumentFragment* clone; WebKitDOMHTMLElement* html; doc = webkit_web_view_get_dom_document(WEBKIT_WEB_VIEW(web_view)); win = webkit_dom_document_get_default_view(WEBKIT_DOM_DOCUMENT(doc)); sel = webkit_dom_dom_window_get_selection(WEBKIT_DOM_DOM_WINDOW(win)); range = webkit_dom_dom_selection_get_range_at(WEBKIT_DOM_DOM_SELECTION(sel), 0, NULL); div = webkit_dom_document_create_element(WEBKIT_DOM_DOCUMENT(doc), "div", NULL); clone = webkit_dom_range_clone_contents(WEBKIT_DOM_RANGE(range), NULL); webkit_dom_node_append_child(&div->parent_instance, &clone->parent_instance, NULL); html = (WebKitDOMHTMLElement*)div; return wxString(webkit_dom_html_element_get_inner_html(WEBKIT_DOM_HTML_ELEMENT(html)), wxConvUTF8); }
static gboolean mail_shell_view_key_press_event_cb (EMailShellView *mail_shell_view, GdkEventKey *event) { EShellView *shell_view; EShellWindow *shell_window; EShellContent *shell_content; EMailView *mail_view; EMailReader *reader; EMailDisplay *mail_display; GtkAction *action; shell_view = E_SHELL_VIEW (mail_shell_view); shell_window = e_shell_view_get_shell_window (shell_view); if ((event->state & (GDK_CONTROL_MASK | GDK_SHIFT_MASK | GDK_MOD1_MASK)) != 0) return FALSE; shell_content = e_shell_view_get_shell_content (shell_view); mail_view = e_mail_shell_content_get_mail_view (E_MAIL_SHELL_CONTENT (shell_content)); reader = E_MAIL_READER (mail_view); mail_display = e_mail_reader_get_mail_display (reader); switch (event->keyval) { case GDK_KEY_space: action = ACTION (MAIL_SMART_FORWARD); break; case GDK_KEY_BackSpace: action = ACTION (MAIL_SMART_BACKWARD); break; case GDK_KEY_Home: case GDK_KEY_Left: case GDK_KEY_Up: case GDK_KEY_Right: case GDK_KEY_Down: case GDK_KEY_Next: case GDK_KEY_End: case GDK_KEY_Begin: /* If Caret mode is enabled don't try to process these keys */ if (e_web_view_get_caret_mode (E_WEB_VIEW (mail_display))) return FALSE; case GDK_KEY_Prior: if (!mail_shell_view_mail_display_needs_key (mail_display, FALSE) && webkit_web_view_get_main_frame (WEBKIT_WEB_VIEW (mail_display)) != webkit_web_view_get_focused_frame (WEBKIT_WEB_VIEW (mail_display))) { WebKitDOMDocument *document; WebKitDOMDOMWindow *window; document = webkit_web_view_get_dom_document (WEBKIT_WEB_VIEW (mail_display)); window = webkit_dom_document_get_default_view (document); /* Workaround WebKit bug for key navigation, when inner IFRAME is focused. * EMailView's inner IFRAMEs have disabled scrolling, but WebKit doesn't post * key navigation events to parent's frame, thus the view doesn't scroll. * This is a poor workaround for this issue, the main frame is focused, * which has scrolling enabled. */ webkit_dom_dom_window_focus (window); } return FALSE; default: return FALSE; } if (mail_shell_view_mail_display_needs_key (mail_display, TRUE)) return FALSE; gtk_action_activate (action); return TRUE; }
static void html_editor_link_dialog_ok (EHTMLEditorLinkDialog *dialog) { EHTMLEditor *editor; EHTMLEditorView *view; EHTMLEditorSelection *selection; WebKitDOMDocument *document; WebKitDOMDOMWindow *dom_window; WebKitDOMDOMSelection *dom_selection; WebKitDOMRange *range; WebKitDOMElement *link; editor = e_html_editor_dialog_get_editor (E_HTML_EDITOR_DIALOG (dialog)); view = e_html_editor_get_view (editor); selection = e_html_editor_view_get_selection (view); document = webkit_web_view_get_dom_document (WEBKIT_WEB_VIEW (view)); dom_window = webkit_dom_document_get_default_view (document); dom_selection = webkit_dom_dom_window_get_selection (dom_window); g_object_unref (dom_window); if (!dom_selection || (webkit_dom_dom_selection_get_range_count (dom_selection) == 0)) { gtk_widget_hide (GTK_WIDGET (dialog)); g_object_unref (dom_selection); return; } range = webkit_dom_dom_selection_get_range_at (dom_selection, 0, NULL); link = e_html_editor_dom_node_find_parent_element ( webkit_dom_range_get_start_container (range, NULL), "A"); if (!link) { if ((webkit_dom_range_get_start_container (range, NULL) != webkit_dom_range_get_end_container (range, NULL)) || (webkit_dom_range_get_start_offset (range, NULL) != webkit_dom_range_get_end_offset (range, NULL))) { WebKitDOMDocumentFragment *fragment; fragment = webkit_dom_range_extract_contents (range, NULL); link = e_html_editor_dom_node_find_child_element ( WEBKIT_DOM_NODE (fragment), "A"); webkit_dom_range_insert_node ( range, WEBKIT_DOM_NODE (fragment), NULL); webkit_dom_dom_selection_set_base_and_extent ( dom_selection, webkit_dom_range_get_start_container (range, NULL), webkit_dom_range_get_start_offset (range, NULL), webkit_dom_range_get_end_container (range, NULL), webkit_dom_range_get_end_offset (range, NULL), NULL); } else { WebKitDOMNode *node; /* get element that was clicked on */ node = webkit_dom_range_get_common_ancestor_container (range, NULL); if (node && !WEBKIT_DOM_IS_HTML_ANCHOR_ELEMENT (node)) { link = e_html_editor_dom_node_find_parent_element (node, "A"); if (link && !WEBKIT_DOM_IS_HTML_ANCHOR_ELEMENT (link)) link = NULL; } else link = WEBKIT_DOM_ELEMENT (node); } } if (link) { webkit_dom_html_anchor_element_set_href ( WEBKIT_DOM_HTML_ANCHOR_ELEMENT (link), gtk_entry_get_text (GTK_ENTRY (dialog->priv->url_edit))); webkit_dom_html_element_set_inner_html ( WEBKIT_DOM_HTML_ELEMENT (link), gtk_entry_get_text (GTK_ENTRY (dialog->priv->label_edit)), NULL); } else { gchar *text; /* Check whether a text is selected or not */ text = webkit_dom_range_get_text (range); if (text && *text) { e_html_editor_selection_create_link ( selection, gtk_entry_get_text ( GTK_ENTRY (dialog->priv->url_edit))); } else { gchar *html = g_strdup_printf ( "<a href=\"%s\">%s</a>", gtk_entry_get_text ( GTK_ENTRY (dialog->priv->url_edit)), gtk_entry_get_text ( GTK_ENTRY (dialog->priv->label_edit))); e_html_editor_view_exec_command ( view, E_HTML_EDITOR_VIEW_COMMAND_INSERT_HTML, html); g_free (html); } g_free (text); } g_object_unref (range); g_object_unref (dom_selection); gtk_widget_hide (GTK_WIDGET (dialog)); }
static void html_editor_link_dialog_show (GtkWidget *widget) { EHTMLEditor *editor; EHTMLEditorView *view; EHTMLEditorLinkDialog *dialog; WebKitDOMDocument *document; WebKitDOMDOMWindow *dom_window; WebKitDOMDOMSelection *dom_selection; WebKitDOMRange *range; WebKitDOMElement *link; dialog = E_HTML_EDITOR_LINK_DIALOG (widget); editor = e_html_editor_dialog_get_editor (E_HTML_EDITOR_DIALOG (dialog)); view = e_html_editor_get_view (editor); document = webkit_web_view_get_dom_document (WEBKIT_WEB_VIEW (view)); dom_window = webkit_dom_document_get_default_view (document); dom_selection = webkit_dom_dom_window_get_selection (dom_window); g_object_unref (dom_window); /* Reset to default values */ gtk_entry_set_text (GTK_ENTRY (dialog->priv->url_edit), "http://"); gtk_entry_set_text (GTK_ENTRY (dialog->priv->label_edit), ""); gtk_widget_set_sensitive (dialog->priv->label_edit, TRUE); gtk_widget_set_sensitive (dialog->priv->remove_link_button, TRUE); dialog->priv->label_autofill = TRUE; /* No selection at all */ if (!dom_selection || webkit_dom_dom_selection_get_range_count (dom_selection) < 1) { gtk_widget_set_sensitive (dialog->priv->remove_link_button, FALSE); goto chainup; } range = webkit_dom_dom_selection_get_range_at (dom_selection, 0, NULL); link = e_html_editor_dom_node_find_parent_element ( webkit_dom_range_get_start_container (range, NULL), "A"); if (!link) { if ((webkit_dom_range_get_start_container (range, NULL) != webkit_dom_range_get_end_container (range, NULL)) || (webkit_dom_range_get_start_offset (range, NULL) != webkit_dom_range_get_end_offset (range, NULL))) { WebKitDOMDocumentFragment *fragment; fragment = webkit_dom_range_clone_contents (range, NULL); link = e_html_editor_dom_node_find_child_element ( WEBKIT_DOM_NODE (fragment), "A"); } else { WebKitDOMNode *node; node = webkit_dom_range_get_common_ancestor_container (range, NULL); if (node && !WEBKIT_DOM_IS_HTML_ANCHOR_ELEMENT (node)) { link = e_html_editor_dom_node_find_parent_element (node, "A"); if (link && !WEBKIT_DOM_IS_HTML_ANCHOR_ELEMENT (link)) link = NULL; } else link = WEBKIT_DOM_ELEMENT (node); } } if (link) { gchar *href, *text; href = webkit_dom_html_anchor_element_get_href ( WEBKIT_DOM_HTML_ANCHOR_ELEMENT (link)); text = webkit_dom_html_element_get_inner_text ( WEBKIT_DOM_HTML_ELEMENT (link)); gtk_entry_set_text ( GTK_ENTRY (dialog->priv->url_edit), href); gtk_entry_set_text ( GTK_ENTRY (dialog->priv->label_edit), text); g_free (text); g_free (href); } else { gchar *text; text = webkit_dom_range_get_text (range); if (text && *text) { gtk_entry_set_text ( GTK_ENTRY (dialog->priv->label_edit), text); gtk_widget_set_sensitive ( dialog->priv->label_edit, FALSE); gtk_widget_set_sensitive ( dialog->priv->remove_link_button, FALSE); } g_free (text); } g_object_unref (range); chainup: g_object_unref (dom_selection); /* Chain up to parent implementation */ GTK_WIDGET_CLASS (e_html_editor_link_dialog_parent_class)->show (widget); }
static void move_caret_after_signature_inserted (EEditorPage *editor_page) { WebKitDOMDocument *document; WebKitDOMElement *element, *signature; WebKitDOMHTMLElement *body; WebKitDOMNodeList *paragraphs = NULL; gboolean top_signature; gboolean start_bottom; gboolean has_paragraphs_in_body = TRUE; g_return_if_fail (E_IS_EDITOR_PAGE (editor_page)); document = e_editor_page_get_document (editor_page); top_signature = use_top_signature (); start_bottom = start_typing_at_bottom (); body = webkit_dom_document_get_body (document); e_editor_page_block_selection_changed (editor_page); paragraphs = webkit_dom_document_query_selector_all (document, "[data-evo-paragraph]", NULL); signature = webkit_dom_document_query_selector (document, ".-x-evo-signature-wrapper", NULL); /* Situation when wrapped paragraph is just in signature and not in message body */ if (webkit_dom_node_list_get_length (paragraphs) == 1) { WebKitDOMNode *node; node = webkit_dom_node_list_item (paragraphs, 0); if (signature && webkit_dom_element_query_selector (signature, "[data-evo-paragraph]", NULL)) has_paragraphs_in_body = FALSE; /* Don't take the credentials into account. */ if (!webkit_dom_node_get_previous_sibling (node) && !element_has_id (WEBKIT_DOM_ELEMENT (node), "-x-evo-input-start")) has_paragraphs_in_body = FALSE; } /* * * Keeping Signatures in the beginning of composer * ------------------------------------------------ * * Purists are gonna blast me for this. * But there are so many people (read Outlook users) who want this. * And Evo is an exchange-client, Outlook-replacement etc. * So Here it goes :( * * -- Sankar * */ if (signature && top_signature) { WebKitDOMElement *spacer; spacer = prepare_top_signature_spacer (editor_page); webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (spacer), webkit_dom_node_get_next_sibling (WEBKIT_DOM_NODE (signature)), NULL); } if (webkit_dom_node_list_get_length (paragraphs) == 0) has_paragraphs_in_body = FALSE; element = webkit_dom_document_get_element_by_id (document, "-x-evo-input-start"); if (!signature) { if (start_bottom) { if (!element) { element = e_editor_dom_prepare_paragraph (editor_page, FALSE); webkit_dom_element_set_id (element, "-x-evo-input-start"); webkit_dom_node_append_child ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), NULL); } } else element = WEBKIT_DOM_ELEMENT (body); goto move_caret; } /* When there is an option composer-reply-start-bottom set we have * to move the caret between reply and signature. */ if (!has_paragraphs_in_body) { element = e_editor_dom_prepare_paragraph (editor_page, FALSE); webkit_dom_element_set_id (element, "-x-evo-input-start"); if (top_signature) { if (start_bottom) { webkit_dom_node_append_child ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), NULL); } else { webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), WEBKIT_DOM_NODE (signature), NULL); } } else { if (start_bottom) webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), WEBKIT_DOM_NODE (signature), NULL); else element = WEBKIT_DOM_ELEMENT (body); } } else { if (!element && top_signature) { element = e_editor_dom_prepare_paragraph (editor_page, FALSE); webkit_dom_element_set_id (element, "-x-evo-input-start"); if (start_bottom) { webkit_dom_node_append_child ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), NULL); } else { webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), WEBKIT_DOM_NODE (signature), NULL); } } else if (element && top_signature && !start_bottom) { webkit_dom_node_insert_before ( WEBKIT_DOM_NODE (body), WEBKIT_DOM_NODE (element), WEBKIT_DOM_NODE (signature), NULL); } else if (element && start_bottom) { /* Leave it how it is */ } else element = WEBKIT_DOM_ELEMENT (body); } move_caret: if (element) { WebKitDOMDOMSelection *dom_selection = NULL; WebKitDOMDOMWindow *dom_window = NULL; WebKitDOMRange *range = NULL; dom_window = webkit_dom_document_get_default_view (document); dom_selection = webkit_dom_dom_window_get_selection (dom_window); range = webkit_dom_document_create_range (document); webkit_dom_range_select_node_contents ( range, WEBKIT_DOM_NODE (element), NULL); webkit_dom_range_collapse (range, TRUE, NULL); webkit_dom_dom_selection_remove_all_ranges (dom_selection); webkit_dom_dom_selection_add_range (dom_selection, range); g_clear_object (&dom_selection); g_clear_object (&dom_window); g_clear_object (&range); } if (start_bottom) e_editor_dom_scroll_to_caret (editor_page); g_clear_object (¶graphs); e_editor_dom_force_spell_check_in_viewport (editor_page); e_editor_page_unblock_selection_changed (editor_page); }
/** * Find the first editable element and set the focus on it and enter input * mode. * Returns true if there was an editable element focused. */ gboolean dom_focus_input(Document *doc) { WebKitDOMNode *html, *node; WebKitDOMDOMWindow *win; WebKitDOMNodeList *list; WebKitDOMXPathNSResolver *resolver; WebKitDOMXPathResult* result; Document *frame_doc; guint i, len; win = webkit_dom_document_get_default_view(doc); list = webkit_dom_document_get_elements_by_tag_name(doc, "html"); if (!list) { return false; } html = webkit_dom_node_list_item(list, 0); g_object_unref(list); resolver = webkit_dom_document_create_ns_resolver(doc, html); if (!resolver) { return false; } /* Use translate to match xpath expression case insensitive so that also * intput filed of type="TEXT" are matched. */ result = webkit_dom_document_evaluate( doc, "//input[not(@type) " "or translate(@type,'ETX','etx')='text' " "or translate(@type,'ADOPRSW','adoprsw')='password' " "or translate(@type,'CLOR','clor')='color' " "or translate(@type,'ADET','adet')='date' " "or translate(@type,'ADEIMT','adeimt')='datetime' " "or translate(@type,'ACDEILMOT','acdeilmot')='datetime-local' " "or translate(@type,'AEILM','aeilm')='email' " "or translate(@type,'HMNOT','hmnot')='month' " "or translate(@type,'BEMNRU','bemnru')='number' " "or translate(@type,'ACEHRS','acehrs')='search' " "or translate(@type,'ELT','elt')='tel' " "or translate(@type,'EIMT','eimt')='time' " "or translate(@type,'LRU','lru')='url' " "or translate(@type,'EKW','ekw')='week' " "]|//textarea", html, resolver, 5, NULL, NULL ); if (!result) { return false; } while ((node = webkit_dom_xpath_result_iterate_next(result, NULL))) { if (element_is_visible(win, WEBKIT_DOM_ELEMENT(node))) { vb_enter('i'); webkit_dom_element_focus(WEBKIT_DOM_ELEMENT(node)); return true; } } /* Look for editable elements in frames too. */ list = webkit_dom_document_get_elements_by_tag_name(doc, "iframe"); len = webkit_dom_node_list_get_length(list); for (i = 0; i < len; i++) { node = webkit_dom_node_list_item(list, i); frame_doc = webkit_dom_html_iframe_element_get_content_document(WEBKIT_DOM_HTML_IFRAME_ELEMENT(node)); /* Stop on first frame with focused element. */ if (dom_focus_input(frame_doc)) { g_object_unref(list); return true; } } g_object_unref(list); return false; }
static void window_object_cleared_callback(WebKitScriptWorld *world, WebKitWebPage *web_page, WebKitFrame *frame, LightDMGreeter *greeter) { JSObjectRef gettext_object, lightdm_greeter_object, config_file_object, greeter_util_object; JSGlobalContextRef jsContext; JSObjectRef globalObject; WebKitDOMDocument *dom_document; WebKitDOMDOMWindow *dom_window; gchar *message = "LockHint"; page_id = webkit_web_page_get_id(web_page); jsContext = webkit_frame_get_javascript_context_for_script_world(frame, world); globalObject = JSContextGetGlobalObject(jsContext); gettext_class = JSClassCreate(&gettext_definition); lightdm_greeter_class = JSClassCreate(&lightdm_greeter_definition); lightdm_user_class = JSClassCreate(&lightdm_user_definition); lightdm_language_class = JSClassCreate(&lightdm_language_definition); lightdm_layout_class = JSClassCreate(&lightdm_layout_definition); lightdm_session_class = JSClassCreate(&lightdm_session_definition); config_file_class = JSClassCreate(&config_file_definition); greeter_util_class = JSClassCreate(&greeter_util_definition); gettext_object = JSObjectMake(jsContext, gettext_class, NULL); JSObjectSetProperty(jsContext, globalObject, JSStringCreateWithUTF8CString("gettext"), gettext_object, kJSPropertyAttributeNone, NULL); lightdm_greeter_object = JSObjectMake(jsContext, lightdm_greeter_class, greeter); JSObjectSetProperty(jsContext, globalObject, JSStringCreateWithUTF8CString("lightdm"), lightdm_greeter_object, kJSPropertyAttributeNone, NULL); config_file_object = JSObjectMake(jsContext, config_file_class, greeter); JSObjectSetProperty(jsContext, globalObject, JSStringCreateWithUTF8CString("config"), config_file_object, kJSPropertyAttributeNone, NULL); greeter_util_object = JSObjectMake(jsContext, greeter_util_class, NULL); JSObjectSetProperty(jsContext, globalObject, JSStringCreateWithUTF8CString("greeterutil"), greeter_util_object, kJSPropertyAttributeNone, NULL); /* If the greeter was started as a lock-screen, send message to our UI process. */ if (lightdm_greeter_get_lock_hint(greeter)) { dom_document = webkit_web_page_get_dom_document(web_page); dom_window = webkit_dom_document_get_default_view(dom_document); if (dom_window) { webkit_dom_dom_window_webkit_message_handlers_post_message(dom_window, "GreeterBridge", message); } } }