Search code examples
libxml2

libxml2: center text in comment section


I try to center the text horizontally and vertically in xml doc, comment section (necessary to automated this when text are translated in po files).

For this I mixed glib and libxml2 api:

static const xmlChar *text[] = {
    N_("Configuration file"),
    N_("This file was automatically generated."),
    N_("Please MAKE SURE TO BACKUP THIS FILE before making changes."),
    NULL
};

xmlChar *centered_text (const xmlChar **array)
{
    GString *string;
    guint    i;

    string = g_string_new ("\n");
    for (i = 0; array[i]; i++)
    {
        gint width;

        width = (80 - strlen (array[i])) / 2 + strlen (array[i]);
        g_string_append_printf (string, "%*s\n", width, array[i]);
    }

    return g_string_free (string, FALSE);
}

.......................

xmlDocPtr  doc;
xmlChar   *content;
xmlNodePtr comment;

doc = xmlNewDoc ((const xmlChar *) "1.0");

content = centered_text (text);
comment = xmlNewDocComment (doc, (const xmlChar *) content);
xmlFree (content);

xmlAddChild ((xmlNodePtr) doc, comment);

And output file look like this:

<?xml version="1.0" encoding="UTF-8"?>
<!--                                 
                               Configuration file
                    This file was automatically generated.
          Please MAKE SURE TO BACKUP THIS FILE before making changes.
-->

Here is for example a italian translation without alignment:

File di configurazione
Questo file è stato generato automaticamente.
Assicurati di file di questo backup prima di apportare modifiche.

There is a way to do this using only libxml2 ?


Solution

  • You can append text content to comment nodes with xmlNodeAddContent and xmlNodeAddContentLen. libxml2 also supports a couple of functions for string manipulation, but there's no equivalent to g_string_append_printf. I'd go with the following approach:

    xmlDocPtr doc;
    xmlNodePtr comment;
    int i;
    
    doc = xmlNewDoc((const xmlChar *)"1.0");
    comment = xmlNewDocComment(doc, (const xmlChar *)"");
    
    for (i = 0; array[i]; i++) {
        /* 40 space characters. */
        static const char space[] = "                                        ";
        int len = strlen(array[i]);
    
        if (len < 80)
            xmlNodeAddContentLen(comment, (const xmlChar *)space, (80 - len) / 2);
        xmlNodeAddContentLen(comment, (const xmlChar *)array[i], len);
        xmlNodeAddContentLen(comment, (const xmlChar *)"\n", 1);
    }