📄 cairo-pdf-surface.c
字号:
subset_resource = _cairo_pdf_surface_new_object (surface); _cairo_output_stream_printf (surface->output, "%d 0 obj\r\n" "<< /Type /Font\r\n" " /Subtype /TrueType\r\n" " /BaseFont /%s\r\n" " /FirstChar 0\r\n" " /LastChar %d\r\n" " /FontDescriptor %d 0 R\r\n" " /Widths [", subset_resource.id, subset.base_font, font_subset->num_glyphs, descriptor.id); for (i = 0; i < font_subset->num_glyphs; i++) _cairo_output_stream_printf (surface->output, " %d", subset.widths[i]); _cairo_output_stream_printf (surface->output, " ]\r\n" ">>\r\n" "endobj\r\n"); font.font_id = font_subset->font_id; font.subset_id = font_subset->subset_id; font.subset_resource = subset_resource; _cairo_array_append (&surface->fonts, &font); _cairo_truetype_subset_fini (&subset); return CAIRO_STATUS_SUCCESS;}static cairo_int_status_t_cairo_pdf_surface_emit_outline_glyph (cairo_pdf_surface_t *surface, cairo_scaled_font_t *scaled_font, unsigned long glyph_index, cairo_pdf_resource_t *glyph_ret){ cairo_scaled_glyph_t *scaled_glyph; pdf_path_info_t info; cairo_status_t status = CAIRO_STATUS_SUCCESS; status = _cairo_scaled_glyph_lookup (scaled_font, glyph_index, CAIRO_SCALED_GLYPH_INFO_METRICS| CAIRO_SCALED_GLYPH_INFO_PATH, &scaled_glyph); if (status) return status; *glyph_ret = _cairo_pdf_surface_open_stream (surface, NULL); _cairo_output_stream_printf (surface->output, "0 0 %f %f %f %f d1\r\n", _cairo_fixed_to_double (scaled_glyph->bbox.p1.x), -_cairo_fixed_to_double (scaled_glyph->bbox.p2.y), _cairo_fixed_to_double (scaled_glyph->bbox.p2.x), -_cairo_fixed_to_double (scaled_glyph->bbox.p1.y)); info.output = surface->output; info.ctm_inverse = NULL; status = _cairo_path_fixed_interpret (scaled_glyph->path, CAIRO_DIRECTION_FORWARD, _cairo_pdf_path_move_to, _cairo_pdf_path_line_to, _cairo_pdf_path_curve_to, _cairo_pdf_path_close_path, &info); _cairo_output_stream_printf (surface->output, " f"); _cairo_pdf_surface_close_stream (surface); return CAIRO_STATUS_SUCCESS;}static cairo_int_status_t_cairo_pdf_surface_emit_bitmap_glyph (cairo_pdf_surface_t *surface, cairo_scaled_font_t *scaled_font, unsigned long glyph_index, cairo_pdf_resource_t *glyph_ret){ cairo_scaled_glyph_t *scaled_glyph; cairo_status_t status; cairo_image_surface_t *image; unsigned char *row, *byte; int rows, cols, bytes_per_row; status = _cairo_scaled_glyph_lookup (scaled_font, glyph_index, CAIRO_SCALED_GLYPH_INFO_METRICS| CAIRO_SCALED_GLYPH_INFO_SURFACE, &scaled_glyph); if (status) return status; image = scaled_glyph->surface; assert (image->format == CAIRO_FORMAT_A1); *glyph_ret = _cairo_pdf_surface_open_stream (surface, NULL); _cairo_output_stream_printf (surface->output, "0 0 %f %f %f %f d1\r\n", _cairo_fixed_to_double (scaled_glyph->bbox.p1.x), - _cairo_fixed_to_double (scaled_glyph->bbox.p2.y), _cairo_fixed_to_double (scaled_glyph->bbox.p2.x), - _cairo_fixed_to_double (scaled_glyph->bbox.p1.y)); _cairo_output_stream_printf (surface->output, "%f 0.0 0.0 %f %f %f cm\r\n", _cairo_fixed_to_double (scaled_glyph->bbox.p2.x) - _cairo_fixed_to_double (scaled_glyph->bbox.p1.x), _cairo_fixed_to_double (scaled_glyph->bbox.p1.y) - _cairo_fixed_to_double (scaled_glyph->bbox.p2.y), _cairo_fixed_to_double (scaled_glyph->bbox.p1.x), _cairo_fixed_to_double (scaled_glyph->bbox.p2.y)); _cairo_output_stream_printf (surface->output, "BI\r\n" "/IM true\r\n" "/W %d\r\n" "/H %d\r\n" "/BPC 1\r\n" "/D [1 0]\r\n", image->width, image->height); _cairo_output_stream_printf (surface->output, "ID "); bytes_per_row = (image->width + 7) / 8; for (row = image->data, rows = image->height; rows; row += image->stride, rows--) { for (byte = row, cols = (image->width + 7) / 8; cols; byte++, cols--) { unsigned char output_byte = CAIRO_BITSWAP8_IF_LITTLE_ENDIAN (*byte); _cairo_output_stream_write (surface->output, &output_byte, 1); } } _cairo_output_stream_printf (surface->output, "\r\nEI\r\n"); _cairo_pdf_surface_close_stream (surface); return CAIRO_STATUS_SUCCESS;}static void_cairo_pdf_surface_emit_glyph (cairo_pdf_surface_t *surface, cairo_scaled_font_t *scaled_font, unsigned long glyph_index, cairo_pdf_resource_t *glyph_ret){ cairo_status_t status; status = _cairo_pdf_surface_emit_outline_glyph (surface, scaled_font, glyph_index, glyph_ret); if (status == CAIRO_INT_STATUS_UNSUPPORTED) status = _cairo_pdf_surface_emit_bitmap_glyph (surface, scaled_font, glyph_index, glyph_ret); if (status) _cairo_surface_set_error (&surface->base, status);}static cairo_status_t_cairo_pdf_surface_emit_type3_font_subset (cairo_pdf_surface_t *surface, cairo_scaled_font_subset_t *font_subset){ cairo_pdf_resource_t *glyphs, encoding, char_procs, subset_resource; cairo_pdf_font_t font; cairo_matrix_t matrix; int i; glyphs = malloc (font_subset->num_glyphs * sizeof (cairo_pdf_resource_t)); if (glyphs == NULL) { _cairo_surface_set_error (&surface->base, CAIRO_STATUS_NO_MEMORY); return CAIRO_STATUS_NO_MEMORY; } for (i = 0; i < font_subset->num_glyphs; i++) { _cairo_pdf_surface_emit_glyph (surface, font_subset->scaled_font, font_subset->glyphs[i], &glyphs[i]); } encoding = _cairo_pdf_surface_new_object (surface); _cairo_output_stream_printf (surface->output, "%d 0 obj\r\n" "<< /Type /Encoding\r\n" " /Differences [0", encoding.id); for (i = 0; i < font_subset->num_glyphs; i++) _cairo_output_stream_printf (surface->output, " /%d", i); _cairo_output_stream_printf (surface->output, "]\r\n" ">>\r\n" "endobj\r\n"); char_procs = _cairo_pdf_surface_new_object (surface); _cairo_output_stream_printf (surface->output, "%d 0 obj\r\n" "<<\r\n", char_procs.id); for (i = 0; i < font_subset->num_glyphs; i++) _cairo_output_stream_printf (surface->output, " /%d %d 0 R\r\n", i, glyphs[i].id); _cairo_output_stream_printf (surface->output, ">>\r\n" "endobj\r\n"); subset_resource = _cairo_pdf_surface_new_object (surface); matrix = font_subset->scaled_font->scale; cairo_matrix_invert (&matrix); _cairo_output_stream_printf (surface->output, "%d 0 obj\r\n" "<< /Type /Font\r\n" " /Subtype /Type3\r\n" " /FontBBox [0 0 0 0]\r\n" " /FontMatrix [ %f %f %f %f 0 0 ]\r\n" " /Encoding %d 0 R\r\n" " /CharProcs %d 0 R\r\n" " /FirstChar 0\r\n" " /LastChar %d\r\n", subset_resource.id, matrix.xx, matrix.yx, -matrix.xy, -matrix.yy, encoding.id, char_procs.id, font_subset->num_glyphs - 1); _cairo_output_stream_printf (surface->output, " /Widths ["); for (i = 0; i < font_subset->num_glyphs; i++) _cairo_output_stream_printf (surface->output, " 0"); _cairo_output_stream_printf (surface->output, "]\r\n"); _cairo_output_stream_printf (surface->output, ">>\r\n" "endobj\r\n"); font.font_id = font_subset->font_id; font.subset_id = font_subset->subset_id; font.subset_resource = subset_resource; _cairo_array_append (&surface->fonts, &font); return CAIRO_STATUS_SUCCESS;}static void_cairo_pdf_surface_emit_font_subset (cairo_scaled_font_subset_t *font_subset, void *closure){ cairo_pdf_surface_t *surface = closure; cairo_status_t status; status = _cairo_pdf_surface_emit_type1_font_subset (surface, font_subset); if (status != CAIRO_INT_STATUS_UNSUPPORTED) return; status = _cairo_pdf_surface_emit_truetype_font_subset (surface, font_subset); if (status != CAIRO_INT_STATUS_UNSUPPORTED) return; status = _cairo_pdf_surface_emit_type3_font_subset (surface, font_subset); if (status != CAIRO_INT_STATUS_UNSUPPORTED) return;}static cairo_status_t_cairo_pdf_surface_emit_font_subsets (cairo_pdf_surface_t *surface){ cairo_status_t status; status = _cairo_scaled_font_subsets_foreach (surface->font_subsets, _cairo_pdf_surface_emit_font_subset, surface); _cairo_scaled_font_subsets_destroy (surface->font_subsets); surface->font_subsets = NULL; if (status) return status; return CAIRO_STATUS_SUCCESS;}#if 0static cairo_status_t_cairo_pdf_surface_write_fonts (cairo_pdf_surface_t *surface){ cairo_font_subset_t *font; cairo_pdf_resource_t font_resource; int num_fonts, i, j; const char *data; char *compressed; unsigned long data_size, compressed_size; cairo_pdf_resource_t stream, descriptor; cairo_status_t status = CAIRO_STATUS_SUCCESS; num_fonts = _cairo_array_num_elements (&surface->fonts); for (i = 0; i < num_fonts; i++) { _cairo_array_copy_element (&surface->fonts, i, &font); status = _cairo_font_subset_generate (font, &data, &data_size); if (status) goto fail; compressed = compress_dup (data, data_size, &compressed_size); if (compressed == NULL) { status = CAIRO_STATUS_NO_MEMORY; goto fail; } stream = _cairo_pdf_surface_new_object (surface); _cairo_output_stream_printf (surface->output, "%d 0 obj\r\n" "<< /Filter /FlateDecode\r\n" " /Length %lu\r\n" " /Length1 %lu\r\n" ">>\r\n" "stream\r\n", stream.id, compressed_size, data_size); _cairo_output_stream_write (surface->output, compressed, compressed_size); _cairo_output_stream_printf (surface->output, "\r\n" "endstream\r\n" "endobj\r\n"); free (compressed); descriptor = _cairo_pdf_surface_new_object (surface); _cairo_output_stream_printf (surface->output, "%d 0 obj\r\n" "<< /Type /FontDescriptor\r\n" " /FontName /7%s\r\n" " /Flags 4\r\n" " /FontBBox [ %ld %ld %ld %ld ]\r\n" " /ItalicAngle 0\r\n" " /Ascent %ld\r\n" " /Descent %ld\r\n" " /CapHeight 500\r\n" " /StemV 80\r\n" " /StemH 80\r\n" " /FontFile2 %u 0 R\r\n" ">>\r\n" "endobj\r\n", descriptor.id, font->base_font, font->x_min, font->y_min, font->x_max, font->y_max, font->ascent, font->descent, stream.id); font_resource.id = font->font_id; _cairo_pdf_surface_update_object (surface, font_resource); _cairo_output_stream_printf (surface->output, "%d 0 obj\r\n" "<< /Type /Font\r\n" " /Subtype /TrueType\r\n" " /BaseFont /%s\r\n" " /FirstChar 0\r\n" " /LastChar %d\r\n" " /FontDescriptor %d 0 R\r\n" " /Widths ", font->font_id, font->base_font, font->num_glyphs, descriptor.id); _cairo_output_stream_printf (surface->output, "["); for (j = 0; j < font->num_glyphs; j++) _cairo_output_stream_printf (surface->output, " %d", font->widths[j]); _cairo_output_stream_printf (surface->output, " ]\r\n" ">>\r\n" "endobj\r\n"); fail: _cairo_font_subset_destroy (font); } return status;}#endifstatic cairo_pdf_resource_t_cairo_pdf_surface_write_catalog (cairo_pdf_surface_t *surface){ cairo_pdf_resource_t catalog; catalog = _cairo_pdf_surface_new_object (surface); _cairo_output_stream_printf (surface->output, "%d 0 obj\r\n" "<< /Type /Catalog\r\n" " /Pages %d 0 R\r\n" ">>\r\n" "endobj\r\n", catalog.id, surface->pages_resource.id); return catalog;}static long_cairo_pdf_surface_write_xref (cairo_pdf_surface_t *surface){ cairo_pdf_object_t *object; int num_objects, i; long offset; char buffer[11]; num_objects = _cairo_array_num_elements (&surface->objects); offset = _cairo_output_stream_get_position (surface->output); _cairo_output_stream_printf (surface->output, "xref\r\n" "%d %d\r\n", 0, num_objects + 1); _cairo_output_stream_printf (surface->output,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -