예제 #1
0
/* split a text buffer into chunks using the passed Pango layout */
GList *
split_for_layout(PangoLayout * layout, const gchar * text,
		 PangoAttrList * attributes, BalsaPrintSetup * psetup,
		 gboolean is_header, GArray ** offsets)
{
    GList *split_list = NULL;
    PangoLayoutIter *iter;
    const gchar *start;
    gint p_offset;
    gboolean add_tab;
    gint p_y0;
    gint p_y1;
    gint p_y_pos;
    gint p_height;

    /* set the text and its attributes, then get an iter */
    pango_layout_set_text(layout, text, -1);
    if (attributes)
	pango_layout_set_attributes(layout, attributes);
    if (offsets)
	*offsets = g_array_new(FALSE, FALSE, sizeof(guint));
    iter = pango_layout_get_iter(layout);

    /* loop over lines */
    start = text;
    p_offset = 0;
    add_tab = FALSE;
    p_y_pos = C_TO_P(psetup->c_y_pos);
    p_height = C_TO_P(psetup->c_height);
    do {
	pango_layout_iter_get_line_yrange(iter, &p_y0, &p_y1);
	if (p_y_pos + p_y1 - p_offset > p_height) {
	    gint index;
	    gint tr;
	    gchar *chunk;
	    gboolean ends_with_nl;

	    if (offsets) {
		guint offs = start - text;

		*offsets = g_array_append_val(*offsets, offs);
	    }
	    pango_layout_xy_to_index(layout, 0, p_y0, &index, &tr);
	    ends_with_nl = text[index - 1] == '\n';
	    if (ends_with_nl)
		index--;
	    chunk = g_strndup(start, text + index - start);
	    if (add_tab)
		split_list =
		    g_list_append(split_list,
				  g_strconcat("\t", chunk, NULL));
	    else
		split_list = g_list_append(split_list, g_strdup(chunk));
	    add_tab = is_header && !ends_with_nl;
	    g_free(chunk);
	    start = text + index;
	    if (ends_with_nl)
		start++;
	    if (*start == '\0')
		p_y_pos = p_height;
	    else {
		p_y_pos = 0;
		psetup->page_count++;
	    }
	    p_offset = p_y0;
	}
    } while (pango_layout_iter_next_line(iter));
    pango_layout_iter_free(iter);

    /* append any remaining stuff */
    if (*start != '\0') {
	p_y_pos += p_y1 - p_offset;
	if (offsets) {
	    guint offs = start - text;

	    *offsets = g_array_append_val(*offsets, offs);
	}
	if (add_tab)
	    split_list =
		g_list_append(split_list, g_strconcat("\t", start, NULL));
	else
	    split_list = g_list_append(split_list, g_strdup(start));
    }

    /* remember the new y position in cairo units */
    psetup->c_y_pos = P_TO_C(p_y_pos);

    /* return the list */
    return split_list;
}
예제 #2
0
GList *
balsa_print_object_default(GList * list,
			   GtkPrintContext * context,
			   LibBalsaMessageBody * body,
			   BalsaPrintSetup * psetup)
{
    BalsaPrintObjectDefault *pod;
    BalsaPrintObject *po;
    gchar *conttype;
    PangoFontDescription *header_font;
    PangoLayout *test_layout;
    PangoTabArray *tabs;
    GString *desc_buf;
    gdouble c_max_height;
    gchar *part_desc;

    pod = g_object_new(BALSA_TYPE_PRINT_OBJECT_DEFAULT, NULL);
    g_assert(pod != NULL);
    po = BALSA_PRINT_OBJECT(pod);

    /* create the part */
    po->depth = psetup->curr_depth;
    po->c_width =
	psetup->c_width - 2 * psetup->curr_depth * C_LABEL_SEP;

    /* get a pixbuf according to the mime type */
    conttype = libbalsa_message_body_get_mime_type(body);
    pod->pixbuf =
	libbalsa_icon_finder(NULL, conttype, NULL, NULL,
                             GTK_ICON_SIZE_DND);
    pod->c_image_width = gdk_pixbuf_get_width(pod->pixbuf);
    pod->c_image_height = gdk_pixbuf_get_height(pod->pixbuf);


    /* create a layout for calculating the maximum label width */
    header_font =
	pango_font_description_from_string(balsa_app.print_header_font);
    test_layout = gtk_print_context_create_pango_layout(context);
    pango_layout_set_font_description(test_layout, header_font);
    pango_font_description_free(header_font);
    desc_buf = g_string_new("");

    /* add type and filename (if available) */
    pod->p_label_width =
	p_string_width_from_layout(test_layout, _("Type:"));
    if ((part_desc = libbalsa_vfs_content_description(conttype)))
	g_string_append_printf(desc_buf, "%s\t%s (%s)", _("Type:"),
			       part_desc, conttype);
    else
	g_string_append_printf(desc_buf, "%s\t%s", _("Type:"), conttype);
    g_free(part_desc);
    g_free(conttype);
    if (body->filename) {
	gint p_fnwidth =
	    p_string_width_from_layout(test_layout, _("File name:"));

	if (p_fnwidth > pod->p_label_width)
	    pod->p_label_width = p_fnwidth;
	g_string_append_printf(desc_buf, "\n%s\t%s", _("File name:"),
			       body->filename);
    }

    /* add a small space between label and value */
    pod->p_label_width += C_TO_P(C_LABEL_SEP);

    /* configure the layout so we can calculate the text height */
    pango_layout_set_indent(test_layout, -pod->p_label_width);
    tabs =
	pango_tab_array_new_with_positions(1, FALSE, PANGO_TAB_LEFT,
					   pod->p_label_width);
    pango_layout_set_tabs(test_layout, tabs);
    pango_tab_array_free(tabs);
    pango_layout_set_width(test_layout,
			   C_TO_P(po->c_width -
				  4 * C_LABEL_SEP - pod->c_image_width));
    pango_layout_set_alignment(test_layout, PANGO_ALIGN_LEFT);
    pod->c_text_height =
	P_TO_C(p_string_height_from_layout(test_layout, desc_buf->str));
    pod->description = g_string_free(desc_buf, FALSE);

    /* check if we should move to the next page */
    c_max_height = MAX(pod->c_text_height, pod->c_image_height);
    if (psetup->c_y_pos + c_max_height > psetup->c_height) {
	psetup->c_y_pos = 0;
	psetup->page_count++;
    }

    /* remember the extent */
    po->on_page = psetup->page_count - 1;
    po->c_at_x = psetup->c_x0 + po->depth * C_LABEL_SEP;
    po->c_at_y = psetup->c_y0 + psetup->c_y_pos;
    po->c_width = psetup->c_width - 2 * po->depth * C_LABEL_SEP;
    po->c_height = c_max_height;

    /* adjust the y position */
    psetup->c_y_pos += c_max_height;

    return g_list_append(list, po);
}