using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Wordprocessing;
using DocumentFormat.OpenXml.Drawing;
using Microsoft.AspNetCore.Mvc;
using Newtonsoft.Json;
using OfficeOpenXml;
using System;
using System.Data;
using System.IO;
using System.Linq;
using System.Threading.Tasks;
using HtmlAgilityPack; namespace FilePreview.Controllers
{
[Route("api/[controller]/[action]")]
[ApiController]
public class PreviewController : ControllerBase
{
static PreviewController()
{
ExcelPackage.LicenseContext = LicenseContext.NonCommercial;
} /// <summary>
/// 预览Excel
/// </summary>
/// <param name="filePath"></param>
/// <returns></returns>
[HttpGet]
public async Task<IActionResult> PreviewExcel(string filePath)
{
//需要安装一个名为"EPPlus"的NuGet包
try
{
using (ExcelPackage excelPackage = new ExcelPackage(new FileInfo(filePath)))
{
DataSet dataSet = new DataSet(); foreach (ExcelWorksheet worksheet in excelPackage.Workbook.Worksheets)
{
System.Data.DataTable dataTable = new System.Data.DataTable(worksheet.Name);
for (int col = 1; col <= worksheet.Dimension.Columns; col++)
{
string columnName = worksheet.Cells[1, col].Value?.ToString();
dataTable.Columns.Add(columnName);
}
for (int row = 2; row <= worksheet.Dimension.Rows; row++)
{
DataRow dataRow = dataTable.NewRow();
for (int col = 1; col <= worksheet.Dimension.Columns; col++)
{
object cellValue = worksheet.Cells[row, col].Value;
dataRow[col - 1] = cellValue;
}
dataTable.Rows.Add(dataRow);
}
dataSet.Tables.Add(dataTable);
}
string json = JsonConvert.SerializeObject(dataSet);
return Ok(json);
}
}
catch (System.Exception ex)
{
return Ok(ex.Message);
} } /// <summary>
/// 预览word
/// </summary>
/// <param name="filePath"></param>
/// <returns></returns>
[HttpGet]
public async Task<IActionResult> PreviewWord(string filePath)
{
//需要安装一个名为"Open XML SDK"的NuGet包
try
{
// 打开 Word 文档
using (WordprocessingDocument doc = WordprocessingDocument.Open(filePath, false))
{
// 获取文档主体部分
MainDocumentPart mainPart = doc.MainDocumentPart;
Document document = mainPart.Document;
Body body = document.Body; string html = "<html><body>";
// 遍历文档中的所有段落
foreach (DocumentFormat.OpenXml.Wordprocessing.Paragraph paragraph in body.Elements<DocumentFormat.OpenXml.Wordprocessing.Paragraph>())
{
// 将段落转换为 HTML
string paragraphHtml = ConvertParagraphToHtml(paragraph, mainPart); // 添加段落 HTML 到总体 HTML 字符串中
html += paragraphHtml;
} html += "</body></html>"; return Ok(html);
}
}
catch (System.Exception ex)
{
return Ok(ex.Message);
}
}
private static string ConvertParagraphToHtml(DocumentFormat.OpenXml.Wordprocessing.Paragraph paragraph, MainDocumentPart mainPart)
{
string html = "<p>"; // 遍历段落中的所有运行
foreach (DocumentFormat.OpenXml.Wordprocessing.Run run in paragraph.Elements<DocumentFormat.OpenXml.Wordprocessing.Run>())
{
// 遍历运行中的所有图片
foreach (DocumentFormat.OpenXml.Wordprocessing.Drawing drawing in run.Elements<DocumentFormat.OpenXml.Wordprocessing.Drawing>())
{
// 获取图片的嵌入对象
Blip blip = drawing.Descendants<Blip>().FirstOrDefault();
if (blip != null)
{
// 获取图片的 ID
string imageId = blip.Embed.Value; // 获取与图片关联的图像部分
ImagePart imagePart = (ImagePart)mainPart.GetPartById(imageId); // 将图像部分的内容转换为 Base64 字符串
string base64String = ConvertImagePartToBase64(imagePart); // 构建 <img> 标签
string imgTag = $"<img src=\"data:image/png;base64,{base64String}\" alt=\"Image\" />"; // 添加到段落 HTML 中
html += imgTag;
}
} // 获取运行的文本内容
//string text = run.InnerText; string text = ConvertWordXmlToHtml(run.InnerText,run.InnerXml);
// 添加文本内容到段落 HTML 中
html += text;
} html += "</p>"; return html;
}
private static string ConvertImagePartToBase64(ImagePart imagePart)
{
using (Stream stream = imagePart.GetStream())
{
using (MemoryStream memoryStream = new MemoryStream())
{
stream.CopyTo(memoryStream);
byte[] imageBytes = memoryStream.ToArray();
return Convert.ToBase64String(imageBytes);
}
}
}
public static string ConvertWordXmlToHtml(string text,string wordXml)
{
// 创建 HTML 文档对象
HtmlDocument htmlDoc = new HtmlDocument();
htmlDoc.OptionAutoCloseOnEnd = true; // 创建 <span> 元素并设置样式
var spanNode = htmlDoc.CreateElement("span"); var family = Substr(wordXml, "w:ascii=\"");
var size = "12";
int number;
if (int.TryParse(Substr(wordXml, "w:val=\""), out number)) {
size = (int.Parse(Substr(wordXml, "w:val=\"")) / 2).ToString();
}
var style = "font-family: " + family + "; font-size: " + size + "px;";
spanNode.SetAttributeValue("style", style); // 将文本内容添加到 <span> 元素中
var textNode = htmlDoc.CreateTextNode(text);
spanNode.AppendChild(textNode); // 将 <span> 元素添加到 HTML 文档中
htmlDoc.DocumentNode.AppendChild(spanNode); // 将 HTML 文档转换为字符串
using (var writer = new System.IO.StringWriter())
{
htmlDoc.Save(writer);
return writer.ToString();
}
}
public static string Substr(string originalString, string substring)
{
// 查找子字符串的索引
int startIndex = originalString.IndexOf(substring); if (startIndex != -1)
{
// 截取子字符串后的一部分字符串
string remainingString = originalString.Substring(startIndex + substring.Length); // 查找第一个引号的索引
int endIndex = remainingString.IndexOf('"'); if (endIndex != -1)
{
// 利用 Substring 方法截取第一个引号之前的值
string result = remainingString.Substring(0, endIndex);
return result;
}
}
return "";
}
}
}

方法调用

Excel文件预览:https://localhost:44368/api/Preview/PreviewExcel?filePath=C:\Users\Administrator\Desktop\001.xlsx
返回一个json结构的dataset 

Word文件预览:https://localhost:44368/api/Preview/PreviewWord?filePath=C:\Users\Administrator\Desktop\002.docx
返回一个前端的html页面

c# 文件在线预览功能的更多相关文章

  1. kkFileView对接svn服务完成文件在线预览功能

    1.需求: 之前在公司内部搭建了svn服务器,给部门存放文档.视频,做成了一个文档服务器来用,随着视频文件太大,每次下载太慢 需要把文件在线打开查看 2.解决: kkFileView https:// ...

  2. svn服务支持网页显示并增加在线预览功能,支持视频在线播放

    1.svn服务器支持网页显示 VisualSVN Server是一个非常不错的SVN Server程序,方便,直观,用户管理也异常方便.不过,它本身并没有提供在线修改密码的功能.由于在实际使用过程中, ...

  3. Java实现office文档与pdf文档的在线预览功能

    最近项目有个需求要java实现office文档与pdf文档的在线预览功能,刚刚接到的时候就觉得有点难,以自己的水平难以在三四天做完.压力略大.后面查找百度资料.以及在同事与网友的帮助下,四天多把它做完 ...

  4. Java实现在线预览功能

    java实现在线预览功能,需要用到  jacob.dll jacob.jar   预览pdf所需js  pdfobject.min.js 将上传文件转为pdf保存. <div class=&qu ...

  5. pdf文件在线预览

    使用pdfjs技术实现PDF的在线预览功能. 目录 1.官网下载pdf.js 2. 将下载下来的文件全部复制 3. js使用 4. java IO流 1.官网下载pdf.js 2. 将下载下来的文件全 ...

  6. 基于开源方案构建统一的文件在线预览与office协同编辑平台的架构与实现历程

    大家好,又见面了. 在构建业务系统的时候,经常会涉及到对附件的支持,继而又会引申出对附件在线预览.在线编辑.多人协同编辑等种种能力的诉求. 对于人力不是特别充裕.或者项目投入预期规划不是特别大的公司或 ...

  7. asp.net word ecxel类型文件在线预览

    asp.net word ecxel类型文件在线预览 首先得引用COM: Microsoft Excel 10 Object Library Microsoft Word 10 Object Libr ...

  8. 使用PDF.JS实现pdf文件在线预览时,报文件被损坏的错误

    首先大概说明一下问题出现的背景:我用PDF.JS实现文件在线预览,参考网上的办法,在jsp文件中使用 <iframe src="<c:url value="js/gen ...

  9. 文件在线预览doc,docx转换pdf(一)

    文件在线预览doc,docx转换pdf(一) 1. 前言 文档转换是一个是一块硬骨头,但是也是必不可少的,我们正好做的知识库产品中,也面临着同样的问题,文档转换,精准的全文搜索,知识的转换率,是知识库 ...

  10. 网页中动态嵌入PDF文件/在线预览PDF内容https://www.cnblogs.com/xgyy/p/6119459.html

    #网页中动态嵌入PDF文件/在线预览PDF内容# 摘要:在web开发时我们有时会需要在线预览PDF内容,在线嵌入pdf文件: 问题1:如何网页中嵌入PDF: 在网页中: 常用的几种PDF预览代码片段如 ...

随机推荐

  1. if elseif else 怎么用?

    问题:求三个数中的最大值 上代码-- 第一种  两两比较  每次取较大值 和第三个值比较  最终得到最大值 private static void maxIf2() { int a = (int) ( ...

  2. win10环境下 VMware Workstation Pro 安装centos7无法上网

    一.安装centos7 网上类似的教程太多了,我就不一一写了,提供两个网址,先按照教程安装 VMware Workstation Pro ,秘钥在第二个链接里面(亲测可用), 安装完VMware在根据 ...

  3. python_7 退出、结束循环和嵌套循环

    一.查缺补漏 1. end=' 任意值 ' 表示换行,任意值会显示在换行前,不写默认换行 2. input() 用户键盘输入 默认输入str类型,如要和int类型比较需要强制类型转换二.退出.结束循环 ...

  4. 去中心化金融-Lec3

    区块链 (什么是区块链?)区块链提供了一种无需可信的参与方,能够让多个参与方实现合作的方式(若存在可信的第三方,则不需要区块链:但是金融系统中往往没有可信的第三方) 终端用户工具:user inter ...

  5. Linux下ftp常见问题总结

    Linux下ftp常见问题总结 似乎拖欠了几篇文章了@_@,来公司半年了,成长了不少!从大学毕业,直到看到http://blog.csdn.net/leixiaohua1020  雷霄骅(然而天妒英才 ...

  6. ToF技术全解读

    文章目录 ToF技术全解读 1. 什么是ToF 2. ToF的原理 3. ToF 优缺点 ToF技术全解读 1. 什么是ToF ToF: Time of flight. 飞行时间.当然这只是一种翻译的 ...

  7. Python 使用列表一部分(切片)

    使用列表的一部分(切片) 处理列表的部分元素 切片 指定第一个元素的索引和最后一个元素索引加1 列表名[索引:索引+1] 索引加1:列表中第索引个元素 (左包括右不包括) 未指定索引 列表名[:] 提 ...

  8. 集线程池应用、多次HttpWebRequest请求,自动切换账号等等的移动信息查询软件

    具体内容就不说了,只是自己留着未来好找而已 主窗体: using System; using System.Collections.Generic; using System.ComponentMod ...

  9. 2022-06-01:给定一个数组arr,可能有正、有负、有0,无序。 只能挑选两个数字,想尽量让两个数字加起来的绝对值尽量小。 返回可能的最小的值。

    2022-06-01:给定一个数组arr,可能有正.有负.有0,无序. 只能挑选两个数字,想尽量让两个数字加起来的绝对值尽量小. 返回可能的最小的值. 答案2022-06-01: 排序,双指针. 代码 ...

  10. Django4全栈进阶之路14 项目实战(用户管理):base.html基础模板设计

    在 Django 中,我们可以使用模板继承来避免代码的重复.模板继承是指我们可以在一个模板中定义一些公共的 HTML 代码,然后在其他模板中继承这个基础模板,并根据需要添加或覆盖一些内容. 通常情况下 ...