C# 解决Excel边框样式无法复制问题及实现格式刷功能
目录
问题现象
范例运行环境
解决方案
剪贴板加特殊粘贴
自定义样式
直接赋值
完美方案
小结
问题现象
在运行数据表数据导出到 EXCEL 数据输出时遇到了一个问题,开发者设计了单行细线下边框的输出模板,如下图设计:

其中 <%system.excel.title.dyna.by.craneoffice%> 字符标记用于输出报表标题替换。数据从A5列开始至D5列结束,按行输出。期望得到如下输出样式:

虽然已经自定义了复制样式的方法,包括边框风格的复制,但实际输出遇到了如下情况:
实际想要得到的单行细线下边框输出没有实现,使用简单 Borders.LineStyle 赋值没有奏效,以后输出的行复制第一行的样式没有成功,因此需要调整样式输出策略,实现类似格式刷那样的操作,这样即实现了格式输出的完整性,也保证了性能。
范例运行环境
操作系统: Windows Server 2019 DataCenter
.net版本: .netFramework4.0 或以上
Office Excel 2016
开发工具:VS2019 C#
解决方案
剪贴板加特殊粘贴
使用 COM 操作的流程原理如下图:

实现代码,示例如下:
SRange.Copy(); //将源选定范围复制到剪贴板
Range.PasteSpecial(Excel.XlPasteType.xlPasteFormats); //特殊粘贴格式到目标选定范围
Copy() 方法实现了复制所有数据到剪贴板功能,其中也包括了样式。 PasteSpecial() 方法实现了指定粘贴的功能,其中 Excel.XlPasteType.xlPasteFormats 表示只粘贴格式样式,至此实现了模拟格式刷的功能。 但此方法可能会引起多 Excel 应用的复制冲突,因此相对保险的写法可以改成如下代码:
SRange.Copy(Range);
但这样会有一个问题是,如果像模板输出还好,但想要仅粘贴格式则无法实现,因此也有局限性。而且这种实现原理,微软可能也会有所调整,也无法保障以后的应用是否会引起复制冲突。所以我们在下个小节通过自定义样式的方式来模拟格式刷的功能。
自定义样式
使用 COM 操作的流程原理如下图:


示例代码如下:
string stylename = Guid.NewGuid().ToString();
WorkBook xb=WorkBooks[1];Style newStyle = xb.Styles.Add(stylename);设置样式属性
newStyle.Font.Name = "宋体";
newStyle.Font.Size = 11;
newStyle.Font.Bold = true;newStyle.Borders.Weight = XlBorderWeight.xlHairline; //最细的线
newStyle.Borders.LineStyle = XlLineStyle.xlContinuous; //实线
以上是添加样式的示例,因为样式很多,实现格式复制的简单方法,是创建新名称并直接引用源单元格的样式,应用到目标选范围上即可,如果有需要移除或修改的样式,可以继续对新建样式进行赋值,修改后如下代码示例:
string stylename = Guid.NewGuid().ToString();
WorkBook xb=WorkBooks[1];Style newStyle = xb.Styles.Add(stylename);newStyle = SRange.Style; //将源选定范围样式赋值到自定义新建样式newStyle.Font.Name="宋体"; //修改字体为宋体Range.Style = newStyle.Name;
直接赋值
Range.Style 是一个 dynamic 类型,可以赋予任何可以正确实现的类型,如自定义样式名称(newStyle.Name),也可以直接赋值为 Style 类型,简单而暴力,代码如下:
Range.Style = SRange.Style; //将源选定范围样式赋值到目标
完美方案
在实际的运行中,无论是自定义样式还是直接赋值模式,对复制字体时出现了无法复制的问题,因此还是需要结合自定义复制样式方法来弥补问题,代码如下:
public void copyRangeStyle(Excel.Range srcRange,Excel.Range desRange)
{desRange.Font.Background=srcRange.Font.Background;desRange.Font.Bold=srcRange.Font.Bold;desRange.Font.Color=srcRange.Font.Color;desRange.Font.Italic=srcRange.Font.Italic;desRange.Font.Name=srcRange.Font.Name;desRange.Font.OutlineFont=srcRange.Font.OutlineFont;desRange.Font.Shadow=srcRange.Font.Shadow;desRange.Font.Size=srcRange.Font.Size;desRange.Font.Strikethrough=srcRange.Font.Strikethrough;desRange.Font.Underline=srcRange.Font.Underline;desRange.RowHeight=srcRange.RowHeight;desRange.HorizontalAlignment=srcRange.HorizontalAlignment;desRange.VerticalAlignment=srcRange.VerticalAlignment;
}
copyRangeStyle 自定义复制样式方法包括 源选定范围参数(Excel.Range srcRange)和目标选定范围参数(Excel.Range desRange),至此,完整代码可修整如下:
Range.Style = SRange.Style;copyRangeStyle(SRange, Range);
至此结合 copyRangeStyle 方法完美解决样式复制问题。
copyRangeStyle 方法请根据实际需要的样式进行扩充或调整。
小结
关于 Range.Borders 的COM 操作如下图:

这个样式的设定是有点击顺序的,选边框后点击样式是无效的,需要点击样式再进行选边框的切换,才会得到预期效果。正常可通过 Range.Borders 直接表示所有6个框线的集合,直接为其赋值,如下代码:
newStyle.Borders.Weight = XlBorderWeight.xlHairline; //最细的线
newStyle.Borders.LineStyle = XlLineStyle.xlContinuous; //实线类型边框
newStyle.Borders.Color = Color.Red; //红色边框
如果想只设置某一边框,则需要获取 Borders 集合里的 Border,如下几种方式都可以获取其中的某一个 Border 对象:
//右、左、下、上边框
Range.Borders.get_Item(XlBordersIndex.xlEdgeRight).LineStyle = XlLineStyle.xlLineStyleNone;
Range.Borders.get_Item(XlBordersIndex.xlEdgeLeft).LineStyle = XlLineStyle.xlContinuous;
Range.Borders.get_Item(XlBordersIndex.xlEdgeBottom).LineStyle = XlLineStyle.xlContinuous;
Range.Borders.get_Item(XlBordersIndex.xlEdgeTop).LineStyle = XlLineStyle.xlContinuous;//内部交叉斜线
Range.Borders.Item[XlBordersIndex.xlDiagonalDown].LineStyle = XlLineStyle.xlLineStyleNone;
Range.Borders[XlBordersIndex.xlDiagonalUp].LineStyle = XlLineStyle.xlLineStyleNone;
我们可以使用 Borders.get_Item 方法或引用 Item 索引或直接引用索引的方法得到 Border,但实际的使用过程中,预期效果不理想,因此我们使用了样式赋值,类似格式刷的方法来解决。
更多可参考如下文章链接:
https://learn.microsoft.com/zh-cn/dotnet/api/microsoft.office.interop.excel.xlbordersindex?view=excel-pia&source=recommendations
https://learn.microsoft.com/zh-cn/dotnet/api/microsoft.office.interop.excel.styles?view=excel-pia
《C# 实现二维数据数组导出到 Excel》
本文代码仅供您参考使用,感谢您的阅读,希望本文能够对您有所帮助。
相关文章:
C# 解决Excel边框样式无法复制问题及实现格式刷功能
目录 问题现象 范例运行环境 解决方案 剪贴板加特殊粘贴 自定义样式 直接赋值 完美方案 小结 问题现象 在运行数据表数据导出到 EXCEL 数据输出时遇到了一个问题,开发者设计了单行细线下边框的输出模板,如下图设计: 其中 <%syst…...
前端组件化开发
假设这个页面是vue开发的,如果一整个页面都是编写在一个vue文件里面,后期不好维护,会特别的庞大,那么如何这个时候需要进行组件化开发。组件化开发后必然会带来一个问题需要进行组件之间的通信。组要是父子组件之间通信࿰…...
异步操作实现线程池
文章目录 futureasyncpromisepackage task C11线程池实现 future 在C11标准库中,提供了一个future的模板类,它表示的是一个异步操作的结果,当在多线程编程中使用异步任务的时候,使用这个类可以帮助在需要的时候获取到对应的数据处…...
长期提供APX515/B原装二手APX525/B音频分析仪
Audio Precision APx515 是一款针对生产测试而优化的高性能音频分析仪。它因其速度、性能、自动化和易用性而成为一流的仪器。它具有卓越的性能,具有 –106 dB 的典型 THDN、1M 点 FFT 和 192k 数字 I/O,以及所有 APx 系列音频分析仪的一键式自动化和易用…...
【数据库差异研究】update与delete使用表别名的研究
目录 ⚛️总结 ☪️1 Update ♋1.1 测试用例UPDATE users as a SET a.age 111 WHERE a.name Alice; ♏1.2 测试用例UPDATE users as a SET a.age 111 WHERE name Alice; ♐1.3 测试用例UPDATE users as a SET age 111 WHERE a.name Alice; ♑1.4 测试用例UPDATE us…...
idea远程连接docker
idea远程连接docker docker、ubuntu、linux、远程连接、IntelliJ idea注意!本文中开启docker远程连接的方法只能在确定环境安全的内网中使用,不可在公网服务器设置,有极大安全风险! 注意!本文中开启docker远程连接的…...
Docker 安装 ClickHouse 教程
Docker 安装 ClickHouse 教程 创建目录 首先,创建必要的目录用于存放 ClickHouse 的配置、数据和日志文件。 mkdir -p /home/clickhouse/conf mkdir -p /home/clickhouse/data mkdir -p /home/clickhouse/log chmod -R 777 /home/clickhouse/conf chmod -R 777 /…...
过渡到内存安全语言:挑战和注意事项
开放源代码安全基金会 ( OpenSSF )总经理 Omkhar Arasaratnam 讨论了内存安全编程语言的演变及其为应对 C 和 C 等语言的局限性而出现的现象。 内存安全问题已存在五十多年,它要求程序员从内存管理任务中抽离出来。 Java、Rust、Python 和 JavaScript 等现代语言通…...
在Pycharm中安装Cv2
安装OpenCV: 在Terminal中,输入以下pip命令来安装OpenCV: pip install opencv-python pip install opencv-contrib-python 如果下载速度较慢,可以考虑使用国内的pip镜像源,如清华大学源: pip install openc…...
减少重复的请求之promise缓存池(构造器版) —— 缓存promise,多次promise等待并返回第一个promise的结果
减少重复的请求之promise缓存池 —— 缓存promise,多次promise等待并返回第一个promise的结果 背景简介 当一个业务组件初始化调用了接口,统一个页面多吃使用同一个组件,将会请求大量重复的接口 如果将promise当作一个普通的对象࿰…...
cdq+bitset处理高维偏序
高维偏序 CDQ分治 假设处理的区间为 [ l , r ] [l,r] [l,r] ,CDQ分治的过程: 如果 l ≥ r l\geq r l≥r ,返回。设区间中点为 m i d mid mid ,递归处理 [ l , m i d ] [l,mid] [l,mid] 和 [ m i d 1 , r ] [mid1,r] [mid…...
敏捷开发和传统开发,你更适合哪种?
时间:2024年 10月 03日 作者:小蒋聊技术 邮箱:wei_wei10163.com 微信:wei_wei10 音频:喜马拉雅 大家好,欢迎来到“小蒋聊技术”,我是小蒋!今天我们来聊聊两个开发模式的“对决”…...
python之with
with上下文管理是什么呢? 一般都是使用系统提供的一些with语句,列如我要去读取一些数据进行分析,就可以使用with open去读取某些数据,或者我要把一些图片给他保存到某些地方,可以用with给他写入。 上下午管理器with是…...
vue3 升级实战笔记
最近要将公司项目的移动端进行 vue3 的升级工作,就顺便记录下升级过程。 项目迁移的思路 我的想法是最小改动原则。 从 vue2.x 升级到 vue3,且使用 vue3 的 选项式 API。构建工具要从 vue-cli(webpack)升级到 vite。路由需要升级到…...
利用函数模块化代码实操 ← Python
【知识点】 ● 模块化可以使代码易于维护和调试,并且提高代码的重用性。 ● 函数可以用来减少冗余的代码并提高代码的可重用性。函数也可以用来模块化代码并提高程序的质量。 ● 在 Python 中,可以将函数的定义放在一个被称为模块的文件中,这种文件的后缀…...
Java高效编程(12):重写toString方法
解锁Python编程的无限可能:《奇妙的Python》带你漫游代码世界 尽管 Object 类提供了 toString 方法的默认实现,但它返回的字符串通常不是类的使用者想要看到的。默认返回的字符串格式是类名加上“”符号和哈希码的十六进制表示,例如 PhoneNu…...
谷歌给到的185个使用生成式AI的案例
很多公司从利用AI回答问题,进而使用AI进行预测,向使用生成式AI Agent转变。AI Agent的独特之处在于它们可以采取行动以实现特定目标,比如引导购物者找到合适的鞋子,帮助员工寻找合适的健康福利,或在护理人员交接班期间…...
程序员如何通过专业与软技能提升核心竞争力
一、引言 随着AIGC的兴起,AI辅助编程工具如chatgpt、midjourney、claude等接二连三地涌现,编程领域的变革正逐步深化。面对这一变革,程序员们对于未来工作的前景有着种种不同的担忧和期待。他们担心AI可能取代部分编程工作,同时…...
基于YOLOv8的智能植物监测机器人
摘要:针对传统的植物病害检测方法依赖专家的经验,耗时耗力,并且准确性受限于个人的水平等问题。文中提出无线通信模块采用HTTP协议来传输数据图片,采用SoC核心处理器实现了便携化,采用对射式红外避障传感器实现自动避障功能。以YOLOv8算法为控制核心,并添加注意力机制以提…...
2024年OpenAI DevDay发布实时 API、提示缓存等新功能
就在几天前,一些重要人物如前 CTO Mira Murati 离开了 OpenAI。因此,看到 Sam Altman 在 DevDay 上登台,讨论开发者的新产品,感觉有点奇怪。 随着公司内部的这些变化,你不禁会想:我们还应该信任他吗&#…...
Windows系统终极清理指南:用Win11Debloat免费快速释放30%系统性能
Windows系统终极清理指南:用Win11Debloat免费快速释放30%系统性能 【免费下载链接】Win11Debloat A simple, lightweight PowerShell script that allows you to remove pre-installed apps, disable telemetry, as well as perform various other changes to declu…...
别再假努力!应届生面试高效准备路线图
文章目录前言一、为什么你总在"假努力"?1. 简历上的"垃圾回收站"2. 八股文死记硬背3. 项目介绍像流水账二、真高效准备路线图阶段一:简历极简主义(3天)阶段二:项目深挖与"埋雷"…...
FastAPI中间件性能优化:从GZip压缩到异步日志的7个提速技巧
FastAPI中间件性能优化:从GZip压缩到异步日志的7个提速技巧 当你的FastAPI应用开始处理每秒数千甚至百万级的请求时,中间件可能成为性能瓶颈的隐形杀手。本文将揭示如何通过7个关键技巧,让你的中间件处理速度提升300%以上。 1. 理解中间件的性…...
放弃HAL库硬件IIC吧!手把手教你用STM32F103C8T6 GPIO模拟IIC读取MT6701角度(附完整工程)
STM32 GPIO模拟IIC驱动MT6701磁编码器实战指南 在嵌入式开发中,IIC总线因其简单性和多设备支持能力而广受欢迎。然而,许多开发者在使用STM32 HAL库的硬件IIC时都遇到过稳定性问题——从莫名其妙的通信失败到难以调试的时序错误。这些问题在需要高精度角度…...
NifSkope深度解析:从入门到精通掌握专业NIF模型编辑技术
NifSkope深度解析:从入门到精通掌握专业NIF模型编辑技术 【免费下载链接】nifskope A git repository for nifskope. 项目地址: https://gitcode.com/gh_mirrors/ni/nifskope NifSkope是一款专注于NetImmerse文件格式(NIF)的专业开源3…...
光伏电站正在“看不见”地亏钱:峰值报不准、爬坡跟不上、回落抓不住,问题到底出在哪?
关键词: 光伏功率预测、新能源功率预测、电力现货交易、爬坡事件、辐照度预测2026年的春天,光伏电站的运营者们发现了一个越来越尴尬的现象:设备越换越高效,组件越装越密,电表转得越来越快——但月底一算账,…...
Android Studio中文语言包快速上手实用指南
Android Studio中文语言包快速上手实用指南 【免费下载链接】AndroidStudioChineseLanguagePack AndroidStudio中文插件(官方修改版本) 项目地址: https://gitcode.com/gh_mirrors/an/AndroidStudioChineseLanguagePack Android Studio作为主流的Android开发…...
用梦话编程:睡眠开发者的效率革命
在传统认知中,软件开发是高度依赖清醒、理性思维的活动。程序员在屏幕前敲击键盘,与逻辑、算法和Bug进行着日复一日的“搏斗”。然而,一场静默的效率革命正在发生,它挑战着我们对“工作状态”的定义——这场革命的核心,…...
HY-MT1.8B部署避坑指南:从环境配置到Chainlit调用全记录
HY-MT1.8B部署避坑指南:从环境配置到Chainlit调用全记录 1. 引言 1.1 为什么选择HY-MT1.8B 在当今多语言翻译需求日益增长的背景下,找到一个既轻量又高效的翻译模型并非易事。HY-MT1.5-1.8B以其18亿参数的紧凑架构,实现了接近大模型的翻译…...
复古游戏机式AI绘图:像素极光引擎LoRA模块化扩展实战教程
复古游戏机式AI绘图:像素极光引擎LoRA模块化扩展实战教程 1. 像素极光引擎简介 Pixel Aurora(像素极光)是一款将复古游戏机美学与现代AI绘图技术完美融合的创新工具。它采用经典的8-bit像素风格界面,却搭载了最先进的扩散模型技…...
