【问题标题】:How do I print image on their original size in Excel using libxlsxwriter?如何使用 libxlsxwriter 在 Excel 中以原始尺寸打印图像?
【发布时间】:2017-09-20 13:33:02
【问题描述】:

我刚开始使用 libxlsxwriter 创建 Excel 表格。我的问题是我不知道如何集中图片以及如何以原始尺寸打印图片。只需考虑只有 3 列且每列具有不同大小的集合,例如 30、10、20。我需要知道我需要什么计算才能找到偏移量和比例值。

lxw_image_options options = {.x_offset = 0,  .y_offset = 0,.x_scale  = 0.9, .y_scale  = 0.9};
worksheet_insert_image_opt(worksheet, row, 0, img_path, &options);

这样,我需要知道图片可以容纳多少行。然后只有我可以创建即将到来的集合而不重叠。

【问题讨论】:

    标签: libxlsxwriter


    【解决方案1】:

    如何以原始尺寸打印图片

    libxlsxwriter 根据图像中的宽度、高度和 DPI 信息以原始大小将图像插入 xlsx 文件。它应该以与通过用户界面在 Excel 中插入图像完全相同的方式插入图像。

    但是,OpenOffice 或 LibreOffice 中的图像尺寸可能不正确。这不是 libxlsxwriter 问题:Excel 也会发生同样的事情。

    要在精确位置插入图像,您需要知道图像的尺寸(以像素为单位)以及 DPI,因为 Excel 根据其默认 DPI(通常为 96)进行缩放以下是连续插入两个图像的示例:

    /*
     * An example of inserting images with the libxlsxwriter library.
     */
    #include "xlsxwriter.h"
    
    int main() {
    
        /* Create a new workbook and add a worksheet. */
        lxw_workbook  *workbook   = workbook_new("demo.xlsx");
        lxw_worksheet *worksheet  = workbook_add_worksheet(workbook, NULL);
        lxw_image_options options = {.x_offset = 0, .y_offset = 0,
                                     .x_scale  = 1, .y_scale = 1};
    
        double default_dpi   = 96.0;
        double image_dpi     = 90.0;
        int32_t image_height = 138;
        int32_t image_offset = (int32_t)(image_height * default_dpi/image_dpi);
    
        /* Insert the first image. */
        worksheet_insert_image(worksheet, 1, 2, "logo.png");
    
        /* Insert the second image relative to the first. */
        options.y_offset += image_offset;
        worksheet_insert_image_opt(worksheet, 1, 2, "logo.png", &options);    
    
        workbook_close(workbook);
    
        return 0;
    }
    

    输出:

    【讨论】:

      【解决方案2】:

      图片有多少行?

      我想在这里展示我的发现以即兴发挥结果。

      int row=1;
      lxw_image_options options = {.x_offset = 0,  .y_offset = 0};
      worksheet_insert_image_opt(worksheet, row, 2,"logo.png", &options);
      row+=(options.height/worksheet->default_row_pixels);        
      

      这里我使用变量options.height来计算图片有多少行。 libxlsxwriter 确实从图像文件中读取了高度(以像素为单位)。它使用 struct variable option 仅用于读取初始化变量,它永远不会在集合中写入任何内容。但我通过在 worksheet.c 的函数 worksheet_insert_image_opt 中添加行 user_options->height=options->height; 来做到这一点。

       lxw_error worksheet_insert_image_opt(lxw_worksheet *self,
                                 lxw_row_t row_num, lxw_col_t col_num,
                                 const char *filename,
                                 lxw_image_options *user_options)
      {
          FILE *image_stream;
          char *short_name;
          lxw_image_options *options;
      
          if (!filename) {
              LXW_WARN("worksheet_insert_image()/_opt(): "
                       "filename must be specified.");
              return LXW_ERROR_NULL_PARAMETER_IGNORED;
          }
      
          /* Check that the image file exists and can be opened. */
          image_stream = fopen(filename, "rb");
          if (!image_stream) {
              LXW_WARN_FORMAT1("worksheet_insert_image()/_opt(): "
                               "file doesn't exist or can't be opened: %s.",
                               filename);
              return LXW_ERROR_PARAMETER_VALIDATION;
          }
      
          /* Get the filename from the full path to add to the Drawing object. */
          short_name = lxw_basename(filename);
          if (!short_name) {
              LXW_WARN_FORMAT1("worksheet_insert_image()/_opt(): "
                               "couldn't get basename for file: %s.", filename);
              fclose(image_stream);
              return LXW_ERROR_PARAMETER_VALIDATION;
          }
      
          /* Create a new object to hold the image options. */
          options = calloc(1, sizeof(lxw_image_options));
          if (!options) {
              fclose(image_stream);
              return LXW_ERROR_MEMORY_MALLOC_FAILED;
          }
      
          if (user_options) {
              memcpy(options, user_options, sizeof(lxw_image_options));
              options->url = lxw_strdup(user_options->url);
              options->tip = lxw_strdup(user_options->tip);
          }
      
          /* Copy other options or set defaults. */
          options->filename = lxw_strdup(filename);
          options->short_name = lxw_strdup(short_name);
          options->stream = image_stream;
          options->row = row_num;
          options->col = col_num;
      
          if (!options->x_scale)
              options->x_scale = 1;
      
          if (!options->y_scale)
              options->y_scale = 1;
      
          if (_get_image_properties(options) == LXW_NO_ERROR) {
              user_options->height=options->height;
              STAILQ_INSERT_TAIL(self->image_data, options, list_pointers);
              return LXW_NO_ERROR;
          }
          else {
              free(options);
              return LXW_ERROR_IMAGE_DIMENSIONS;
          }
      }
      

      这就是我计算行数的方式。如果有更好的方法请告诉我。

      【讨论】:

      • “它使用 struct variable 选项仅用于读取初始化变量,它永远不会在集合中写入任何内容”。那是对的。 Libxlsxwriter 从不修改用户传递的任何结构。顺便说一句,我是作者。也许 libxlsxwriter 应该公开函数来计算 Excel 所需的图像指标。但是,像您所做的那样,将它们重新添加到用户结构中会更简单并且可能更清洁。我会考虑的。为此打开功能请求可能是个好主意。
      猜你喜欢
      • 1970-01-01
      • 2019-02-02
      • 2016-11-03
      • 2013-04-17
      • 1970-01-01
      • 2012-09-09
      • 2015-12-27
      • 2012-04-16
      相关资源
      最近更新 更多