Python xlwings插入Excel图片的实现方法


Posted in Python onFebruary 26, 2021

测试图片

Python xlwings插入Excel图片的实现方法

一、相对路径(报错)

使用相对路径插入会报错(确认路径正确无误)

import xlwings as xw

wb = xw.Book()
sht = wb.sheets['Sheet1']
sht.pictures.add('1.jpg') # 使用相对路径会报错
wb.save('test.xlsx')
wb.close()

File "<COMObject <unknown>>", line 5, in AddPicture
pywintypes.com_error: (-2147352567, '发生意外。', (0, None, '未找到指定文件。', None, 0, -2146827284), None)

二、绝对路径

改为绝对路径即可成功插入

import os
import xlwings as xw

wb = xw.Book()
sht = wb.sheets['Sheet1']
# sht.pictures.add('1.jpg') # 使用相对路径会报错
sht.pictures.add(os.path.join(os.getcwd(), '1.jpg'))
wb.save('test.xlsx')
wb.close()

Python xlwings插入Excel图片的实现方法

三、指定位置和大小

函数原型add(image, link_to_file=False, save_with_document=True, left=0, top=0, width=None, height=None, name=None, update=False)

import os
import xlwings as xw

wb = xw.Book()
sht = wb.sheets['Sheet1']
fileName = os.path.join(os.getcwd(), '1.jpg')
sht.pictures.add(fileName, left=sht.range('B5').left, top=sht.range('B5').top, width=100, height=100)
wb.save('test.xlsx')
wb.close()

指定图片位置为B5单元格的左上角,图片像素为100×100

Python xlwings插入Excel图片的实现方法

四、居中插入

新建Excel文件test.xlsx,设置列宽20行高100

Python xlwings插入Excel图片的实现方法

import os
import xlwings as xw

wb = xw.Book('test.xlsx') # 打开已存在的Excel文件
sht = wb.sheets['Sheet1']
rng = sht.range('B2') # 目标单元格
fileName = os.path.join(os.getcwd(), '1.jpg')
width, height = 80, 80 # 指定图片大小
left = rng.left + (rng.width - width) / 2 # 居中
top = rng.top + (rng.height - height) / 2
sht.pictures.add(fileName, left=left, top=top, width=width, height=height)
wb.save()
wb.close()

Python xlwings插入Excel图片的实现方法

智能居中插入

1.jpg

宽 × 高 = 188 × 282

Python xlwings插入Excel图片的实现方法

2.jpg

宽 × 高 = 200 × 153

Python xlwings插入Excel图片的实现方法

import os
import xlwings as xw
from PIL import Image


def add_center(sht, target, filePath, match=False, width=None, height=None, column_width=None, row_height=None):
  '''Excel智能居中插入图片

  优先级:match > width & height > column_width & row_height
  建议使用column_width或row_height,定义单元格最大宽或高

  :param sht: 工作表
  :param target: 目标单元格,字符串,如'A1'
  :param filePath: 图片绝对路径
  :param width: 图片宽度
  :param height: 图片高度
  :param column_width: 单元格最大宽度,默认100像素,0 <= column_width <= 1557.285
  :param row_height: 单元格最大高度,默认75像素,0 <= row_height <= 409.5
  :param match: 绝对匹配原图宽高,最大宽度1557.285,最大高度409.5
  '''
  unit_width = 6.107 # Excel默认列宽与像素的比
  rng = sht.range(target) # 目标单元格
  name = os.path.basename(filePath) # 文件名
  _width, _height = Image.open(filePath).size # 原图片宽高
  NOT_SET = True # 未设置单元格宽高
  # match
  if match: # 绝对匹配图像
    width, height = _width, _height
  else: # 不绝对匹配图像
    # width & height
    if width or height:
      if not height: # 指定了宽,等比计算高
        height = width / _width * _height
      if not width: # 指定了高,等比计算宽
        width = height / _height * _width
    else:
      # column_width & row_height
      if column_width and row_height: # 同时指定单元格最大宽高
        width = row_height / _height * _width # 根据单元格最大高度假设宽
        height = column_width / _width * _height # 根据单元格最大宽度假设高
        area_width = column_width * height # 假设宽优先的面积
        area_height = row_height * width # 假设高优先的面积
        if area_width > area_height:
          width = column_width
        else:
          height = row_height
      elif not column_width and not row_height: # 均无指定单元格最大宽高
        column_width = 100
        row_height = 75
        rng.column_width = column_width / unit_width # 更新当前宽度
        rng.row_height = row_height # 更新当前高度
        NOT_SET = False
        width = row_height / _height * _width # 根据单元格最大高度假设宽
        height = column_width / _width * _height # 根据单元格最大宽度假设高
        area_width = column_width * height # 假设宽优先的面积
        area_height = row_height * width # 假设高优先的面积
        if area_width > area_height:
          height = row_height
        else:
          width = column_width
      else:
        width = row_height / _height * _width if row_height else column_width # 仅设了单元格最大宽度
        height = column_width / _width * _height if column_width else row_height # 仅设了单元格最大高度
  assert 0 <= width / unit_width <= 255
  assert 0 <= height <= 409.5
  if NOT_SET:
    rng.column_width = width / unit_width # 更新当前宽度
    rng.row_height = height # 更新当前高度
  left = rng.left + (rng.width - width) / 2 # 居中
  top = rng.top + (rng.height - height) / 2
  try:
    sht.pictures.add(filePath, left=left, top=top, width=width, height=height, scale=None, name=name)
  except Exception: # 已有同名图片,采用默认命名
    pass


if __name__ == '__main__':
  wb = xw.Book()
  sht = wb.sheets['Sheet1']
  filePath = os.path.join(os.getcwd(), '1.jpg')
  filePath2 = os.path.join(os.getcwd(), '2.jpg')

  add_center(sht, 'A1', filePath) # 默认值
  add_center(sht, 'B2', filePath2) # 默认值
  add_center(sht, 'C3', filePath, match=True) # 绝对匹配图片宽高
  add_center(sht, 'D4', filePath, width=100) # 图片宽度为100像素
  add_center(sht, 'E5', filePath, height=100) # 图片高度为100像素
  add_center(sht, 'F6', filePath, width=100, height=100) # 图片高度为100像素
  add_center(sht, 'G7', filePath, column_width=100) # 单元格最大宽度为100像素
  add_center(sht, 'H8', filePath, row_height=100) # 单元格最大宽度为100像素
  add_center(sht, 'I9', filePath, column_width=100, row_height=100) # 单元格最大高度或宽度为100像素

效果

Python xlwings插入Excel图片的实现方法

unit_width = 6.107 # Excel默认列宽与像素的比

这个值估计与不同机器、分辨率有关,在5.7-6.2之间

遇到的坑

报错 pywintypes.com_error: (-2147352567, '发生意外。', (0, None, '未找到指定文件。', None, 0, -2146827284), None)
对路径使用os.path.abspath()

参考文献

 xlwings dev documentation

报错pywintypes.com_error: (-2147352567, ‘发生意外。‘, (0, None, ‘未找到指定文件。‘, None, 0, -2146827284), None)

到此这篇关于Python xlwings插入Excel图片的实现方法的文章就介绍到这了,更多相关Python xlwings插入图片内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
Python中asyncore的用法实例
Sep 29 Python
Python实现中文数字转换为阿拉伯数字的方法示例
May 26 Python
pycharm在调试python时执行其他语句的方法
Nov 29 Python
Pytorch中accuracy和loss的计算知识点总结
Sep 10 Python
django中media媒体路径设置的步骤
Nov 15 Python
Python数据正态性检验实现过程
Apr 18 Python
python爬虫实例之获取动漫截图
May 31 Python
python 绘制场景热力图的示例
Sep 23 Python
基于Python实现粒子滤波效果
Dec 01 Python
Python 中 sorted 如何自定义比较逻辑
Feb 02 Python
Python如何快速找到多个字典中的公共键(key)
Apr 29 Python
Python使用pandas导入xlsx格式的excel文件内容操作代码
Dec 24 Python
基于tensorflow __init__、build 和call的使用小结
Feb 26 #Python
python实现MySQL指定表增量同步数据到clickhouse的脚本
Feb 26 #Python
详解python的xlwings库读写excel操作总结
Feb 26 #Python
pytorch 中forward 的用法与解释说明
Feb 26 #Python
浅谈Python xlwings 读取Excel文件的正确姿势
Feb 26 #Python
pycharm Tab键设置成4个空格的操作
Feb 26 #Python
解决pycharm 格式报错tabs和space不一致问题
Feb 26 #Python
You might like
深入PHP curl参数的详解
2013/06/17 PHP
实例讲解php数据访问
2016/05/09 PHP
IE中radio 或checkbox的checked属性初始状态下不能选中显示问题
2009/07/25 Javascript
jQuery+.net实现浏览更多内容(改编php版本)
2013/03/28 Javascript
js计算精度问题小结
2013/04/22 Javascript
jQuery教程 $()包装函数来实现数组元素分页效果
2013/08/13 Javascript
javascript window.open打开新窗口后无法再次打开该窗口问题的解决方法
2014/04/12 Javascript
js实现飞入星星特效代码
2014/10/17 Javascript
JQuery datepicker 用法详解
2015/12/25 Javascript
基于javascript简单实现对身份证校验
2021/01/25 Javascript
js面向对象的写法
2016/02/19 Javascript
JavaScript 函数的执行过程
2016/05/09 Javascript
jquery ezUI 双击行记录弹窗查看明细的实现方法
2016/06/01 Javascript
javascript cookie基础应用之记录用户名的方法
2016/09/20 Javascript
JavaScript基本类型值-Undefined、Null、Boolean
2017/02/23 Javascript
NodeJS学习笔记之Module的简介
2017/03/24 NodeJs
JavaScript定义函数_动力节点Java学院整理
2017/06/27 Javascript
详解Angular CLI + Electron 开发环境搭建
2017/07/20 Javascript
jquery+css3实现熊猫tv导航代码分享
2018/02/12 jQuery
JS实现导航栏楼层特效
2020/01/01 Javascript
[45:52]2018DOTA2亚洲邀请赛 4.1小组赛 A组加赛 LGD vs Liquid
2018/04/02 DOTA
[02:10]探秘浦东源深体育馆 DOTA2 Supermajor不见不散
2018/05/17 DOTA
教你一步步利用python实现贪吃蛇游戏
2019/06/27 Python
int在python中的含义以及用法
2019/06/27 Python
python logging模块的使用总结
2019/07/09 Python
python3 sleep 延时秒 毫秒实例
2020/05/04 Python
Django基于Models定制Admin后台实现过程解析
2020/11/11 Python
回馈慈善的设计师太阳镜:DIFF eyewear
2019/10/17 全球购物
澳洲CFL商城:CHEMIST FOR LESS(中文)
2021/02/28 全球购物
写给学生的新学期寄语
2014/01/18 职场文书
超市促销活动总结
2014/07/01 职场文书
餐饮服务食品安全责任书
2014/07/25 职场文书
煤矿百日安全活动总结
2015/05/07 职场文书
中国梦党课学习心得体会
2016/01/05 职场文书
详解MySQL中timestamp和datetime时区问题导致做DTS遇到的坑
2021/12/06 MySQL
Nebula Graph解决风控业务实践
2022/03/31 MySQL