xml-tree.cpp revision b34fc740d3561b2172cdf11d3213cda2ebee4ea5
/**
* @file
* XML editor.
*/
/* Authors:
* Lauris Kaplinski <lauris@kaplinski.com>
* MenTaLguY <mental@rydia.net>
* bulia byak <buliabyak@users.sf.net>
* Johan Engelen <goejendaagh@zonnet.nl>
* David Turner
* Jon A. Cruz <jon@joncruz.org>
* Abhishek Sharma
*
* Copyright (C) 1999-2006 Authors
* Released under GNU GPL, read the file 'COPYING' for more information
*
*/
#include "xml-tree.h"
#include <gdk/gdkkeysyms.h>
#include "desktop.h"
#include "desktop-handles.h"
#include "dialogs/dialog-events.h"
#include "document.h"
#include "document-undo.h"
#include "event-context.h"
#include "inkscape.h"
#include "interface.h"
#include "macros.h"
#include "message-context.h"
#include "message-stack.h"
#include "preferences.h"
#include "selection.h"
#include "shortcuts.h"
#include "sp-root.h"
#include "sp-string.h"
#include "sp-tspan.h"
#include "ui/icon-names.h"
#include "verbs.h"
#include "widgets/sp-xmlview-attr-list.h"
#include "widgets/sp-xmlview-content.h"
#include "widgets/sp-xmlview-tree.h"
namespace Inkscape {
namespace UI {
namespace Dialog {
blocked (0),
selected_attr (0),
attributes (NULL),
attr_name (),
status (""),
tree_toolbar(),
xml_element_new_button ( _("New element node")),
xml_text_new_button ( _("New text node")),
xml_node_duplicate_button ( _("Duplicate node")),
attr_toolbar(),
xml_attribute_delete_button (_("Delete attribute")),
text_container (),
attr_container (),
set_attr (_("Set")),
{
if (!desktop) {
return;
}
contents->set_spacing(0);
/* tree view */
xml_element_new_button.set_sensitive(false);
xml_text_new_button.set_sensitive(false);
xml_node_delete_button.set_sensitive(false);
unindent_node_button.set_sensitive(false);
indent_node_button.set_sensitive(false);
raise_node_button.set_sensitive(false);
lower_node_button.set_sensitive(false);
/* node view */
/* attributes */
xml_attribute_delete_button.set_icon_widget(*Gtk::manage(Glib::wrap(sp_icon_new (Inkscape::ICON_SIZE_LARGE_TOOLBAR, INKSCAPE_ICON("xml-attribute-delete")))));
/* text */
/* Signal handlers */
g_signal_connect( G_OBJECT(attributes), "row-value-changed", G_CALLBACK(on_attr_row_changed), this);
xml_element_new_button.signal_clicked().connect(sigc::mem_fun(*this, &XmlTree::cmd_new_element_node));
xml_node_duplicate_button.signal_clicked().connect(sigc::mem_fun(*this, &XmlTree::cmd_duplicate_node));
xml_attribute_delete_button.signal_clicked().connect(sigc::mem_fun(*this, &XmlTree::cmd_delete_attr));
attr_value.signal_key_press_event().connect(sigc::mem_fun(*this, &XmlTree::sp_xml_tree_key_press), false);
desktopChangeConn = deskTrack.connectDesktopChanged( sigc::mem_fun(*this, &XmlTree::set_tree_desktop) );
show_all();
/*
// hide() doesn't seem to work in the constructor, so moved this to present()
text_container.hide();
attr_container.hide();
*/
}
{
}
{
delete _message_context;
}
{
}
/**
* Sets the XML status bar when the tree is selected.
*/
void XmlTree::tree_reset_context()
{
_("<b>Click</b> to select nodes, <b>drag</b> to rearrange."));
}
/**
* Sets the XML status bar, depending on which attr is selected.
*/
{
if (attr == 0) {
_("<b>Click</b> attribute to edit."));
}
else {
gchar *message = g_strdup_printf(_("Attribute <b>%s</b> selected. Press <b>Ctrl+Enter</b> when done editing to commit changes."), name);
}
}
{
SP_SHORTCUT_SHIFT_MASK : 0 ) |
SP_SHORTCUT_CONTROL_MASK : 0 ) |
SP_SHORTCUT_ALT_MASK : 0 );
/* fixme: if you need to add more xml-tree-specific callbacks, you should probably upgrade
* the sp_shortcut mechanism to take into account windows. */
cmd_set_attr();
return true;
}
return false;
}
{
if ( desktop == current_desktop ) {
return;
}
if (current_desktop) {
}
if (desktop) {
sel_changed_connection = sp_desktop_selection(desktop)->connectChanged(sigc::hide(sigc::mem_fun(this, &XmlTree::on_desktop_selection_changed)));
document_replaced_connection = desktop->connectDocumentReplaced(sigc::mem_fun(this, &XmlTree::on_document_replaced));
} else {
}
} // end of set_tree_desktop()
{
if (document == current_document) {
return;
}
if (current_document) {
}
if (current_document) {
document_uri_set_connection = current_document->connectURISet(sigc::bind(sigc::ptr_fun(&on_document_uri_set), current_document));
} else {
}
}
{
if (repr == selected_repr) {
return;
}
if (repr) {
} else {
}
}
{
if (selected_repr) {
}
if (repr) {
} else {
g_message("XmlTree::set_tree_select : Couldnt find repr node");
}
} else {
}
}
{
} else {
}
if (repr && ( repr->type() == Inkscape::XML::TEXT_NODE || repr->type() == Inkscape::XML::COMMENT_NODE || repr->type() == Inkscape::XML::PI_NODE ) ) {
} else {
}
}
{
if (!current_desktop) {
return NULL;
}
}
{
if (!current_desktop) {
return;
}
if (repr) {
{
} // end of while loop
} else {
}
blocked++;
&& !(SP_IS_STRING(object) ||
SP_IS_ROOT(object) ) )
{
/* We cannot set selection to root or string - they are not items and selection is not
* equipped to deal with them */
}
blocked--;
} // end of set_dt_select()
/*void XmlTree::on_tree_select_row(GtkCTree *tree,
GtkCTreeNode *node,
gint column,
gpointer data)*/
{
if (self->selected_repr) {
}
// Nothing selected, update widgets
return;
}
}
{
if (val) {
_("Drag XML subtree"));
} else {
//DocumentUndo::cancel(self->current_document);
/*
* There was a problem with drag & drop,
* data is probably not synchronized, so reload the tree
*/
}
}
void XmlTree::_set_status_message(Inkscape::MessageType /*type*/, const gchar *message, GtkWidget *widget)
{
if (widget) {
}
}
{
if (!node) {
return;
}
//on_tree_select_row_enable_if_mutable
//on_tree_select_row_enable_if_element
xml_text_new_button.set_sensitive(true);
} else {
xml_element_new_button.set_sensitive(false);
xml_text_new_button.set_sensitive(false);
}
//on_tree_select_row_enable_if_has_grandparent
{
} else {
unindent_node_button.set_sensitive(false);
}
} else {
unindent_node_button.set_sensitive(false);
}
}
// on_tree_select_row_enable_if_indentable
if (xml_tree_node_mutable(node)) {
// skip to the child just before the current repr
indentable = TRUE;
}
}
}
//on_tree_select_row_enable_if_not_first_child
{
raise_node_button.set_sensitive(true);
} else {
raise_node_button.set_sensitive(false);
}
}
//on_tree_select_row_enable_if_not_last_child
{
lower_node_button.set_sensitive(true);
} else {
lower_node_button.set_sensitive(false);
}
}
//on_tree_select_row_show_if_element
} else {
}
//on_tree_select_row_show_if_text
if ( repr->type() == Inkscape::XML::TEXT_NODE || repr->type() == Inkscape::XML::COMMENT_NODE || repr->type() == Inkscape::XML::PI_NODE ) {
} else {
}
}
{
// top-level is immutable, obviously
return false;
}
// if not in base level (where namedview, defs, etc go), we're mutable
return true;
}
// don't let "defs" or "namedview" disappear
return false;
}
// everyone else is okay, I guess. :)
return true;
}
void XmlTree::on_tree_unselect_row_disable()
{
xml_text_new_button.set_sensitive(false);
xml_element_new_button.set_sensitive(false);
xml_node_delete_button.set_sensitive(false);
unindent_node_button.set_sensitive(false);
indent_node_button.set_sensitive(false);
raise_node_button.set_sensitive(false);
lower_node_button.set_sensitive(false);
}
void XmlTree::on_tree_unselect_row_hide()
{
}
{
// Nothing selected
self->selected_attr = 0;
return;
}
gtk_tree_model_get (model, &iter, ATTR_COL_NAME, &name, ATTR_COL_VALUE, &value, ATTR_COL_ATTR, &attr, -1);
if (name) {
}
if (value) {
}
}
void XmlTree::on_attr_row_changed(SPXMLViewAttrList *attributes, const gchar * name, gpointer /*data*/)
{
// Reselect the selected row if the data changes to refresh the attribute and value edit boxes.
}
}
}
if (attr_name) {
attr_name = 0;
}
}
{
}
void XmlTree::onNameChanged()
{
/* TODO: need to do checking a little more rigorous than this */
}
void XmlTree::onCreateNameChanged()
{
/* TODO: need to do checking a little more rigorous than this */
}
void XmlTree::on_desktop_selection_changed()
{
if (!blocked++) {
if (!node) {
}
}
blocked--;
}
{
if (current_desktop)
sel_changed_connection = sp_desktop_selection(dt)->connectChanged(sigc::hide(sigc::mem_fun(this, &XmlTree::on_desktop_selection_changed)));
}
{
/*
* Seems to be no way to set the title on a docked dialog
gchar title[500];
sp_ui_dialog_title_string(Inkscape::Verb::get(SP_VERB_DIALOG_XML_EDITOR), title);
gchar *t = g_strdup_printf("%s: %s", document->getName(), title);
//gtk_window_set_title(GTK_WINDOW(dlg), t);
g_free(t);
*/
}
{
switch (get_group0_keyval (event)) {
case GDK_KEY_Escape: // defocus
return TRUE;
case GDK_KEY_Return: // create
case GDK_KEY_KP_Enter:
return TRUE;
}
return FALSE;
}
void XmlTree::cmd_new_element_node()
{
gtk_window_set_transient_for(GTK_WINDOW(new_window), GTK_WINDOW(gtk_widget_get_toplevel(GTK_WIDGET(gobj()))));
#if GTK_CHECK_VERSION(3,0,0)
#else
#endif
#if GTK_CHECK_VERSION(3,0,0)
#else
sep = gtk_hseparator_new();
#endif
#if GTK_CHECK_VERSION(3,0,0)
#else
bbox = gtk_hbutton_box_new();
#endif
G_OBJECT(new_window) );
G_OBJECT(new_window) );
//gtk_window_set_default(GTK_WINDOW(window), GTK_WIDGET(create));
name_entry->grab_focus();
gtk_main();
if (new_name) {
_("Create new element node"));
}
} // end of cmd_new_element_node()
void XmlTree::cmd_new_text_node()
{
_("Create new text node"));
}
void XmlTree::cmd_duplicate_node()
{
_("Duplicate node"));
}
}
void XmlTree::cmd_delete_node()
{
Q_("nodeAsInXMLinHistoryDialog|Delete node"));
}
void XmlTree::cmd_delete_attr()
{
g_assert(selected_attr != 0);
if (updated) {
// force immediate update of dependant attributes
updated->updateRepr();
}
_("Delete attribute"));
}
void XmlTree::cmd_set_attr()
{
if (updated) {
// force immediate update of dependant attributes
updated->updateRepr();
}
_("Change attribute"));
/* TODO: actually, the row won't have been created yet. why? */
}
void XmlTree::cmd_raise_node()
{
}
_("Raise node"));
}
void XmlTree::cmd_lower_node()
{
_("Lower node"));
}
void XmlTree::cmd_indent_node()
{
}
if (prev->firstChild()) {
}
_("Indent node"));
} // end of cmd_indent_node()
void XmlTree::cmd_unindent_node()
{
_("Unindent node"));
} // end of cmd_unindent_node()
/** Returns true iff \a item is suitable to be included in the selection, in particular
whether it has a bounding box in the desktop coordinate system for rendering resize handles.
Descendents of <defs> nodes (markers etc.) return false, for example.
*/
{
/* Definition based on sp_item_i2doc_affine. */
for(;;) {
if (!SP_IS_ITEM(child)) {
return false;
}
break;
}
}
/* Relevance: Otherwise, I'm not sure whether to return true or false. */
return true;
}
}
}
}
/*
Local Variables:
mode:c++
c-file-style:"stroustrup"
c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
indent-tabs-mode:nil
fill-column:99
End:
*/
// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:fileencoding=utf-8:textwidth=99 :