C# OpenXML如何添加指向其他工作表的超链接

C# OpenXML如何添加指向其他工作表的超链接,c#,.net,excel,hyperlink,openxml,C#,.net,Excel,Hyperlink,Openxml,我正在寻找如何向单元格添加超链接的示例。 似乎这不像添加文本那么容易 我得到了生成正确XML的代码,但在excel中不会出现链接 private SheetData PopulateSheetWithData(SheetData sheetData, IList<Event> events, SpreadsheetDocument document) { int errorIndex = 0; foreach (var @event i

我正在寻找如何向单元格添加超链接的示例。 似乎这不像添加文本那么容易

我得到了生成正确XML的代码,但在excel中不会出现链接

    private SheetData PopulateSheetWithData(SheetData sheetData, IList<Event> events, SpreadsheetDocument document)
    {
        int errorIndex = 0;
        foreach (var @event in events)
        {
            errorIndex++;

            Hyperlinks hyperlinks = new Hyperlinks();
            Hyperlink hyperlink = new Hyperlink()
            {
                Location = "UniqueError_" + errorIndex + "!A1",
                Display = @event.LOG_CORR_KEY,
                Reference = "A"+(errorIndex+1),
                Id = "UniqueError_" + errorIndex
            };
            hyperlinks.AppendChild(hyperlink);
            sheetData.AppendChild(hyperlinks);
        }
        return sheetData;
    }
private SheetData填充SheetWithData(SheetData SheetData、IList事件、电子表格文档)
{
int errorIndex=0;
foreach(事件中的var@event)
{
errorIndex++;
超链接超链接=新的超链接();
超级链接=新建超级链接()
{
Location=“UniqueError”+errorIndex+“!A1”,
Display=@event.LOG\u CORR\u KEY,
Reference=“A”+(errorIndex+1),
Id=“UniqueError\uux”+错误索引
};
超链接。追加子项(超链接);
sheetData.AppendChild(超链接);
}
返回数据;
}
我做错什么了吗?
我找到了一篇关于如何添加超链接的文章,但看起来太复杂了。这个问题有什么帮助吗

因此,在一段时间的讨论之后,我决定专注于我的OpenXML Excel调查,我成功了

我找到了一个如何将超链接插入excel文件的解决方案,更重要的是,现在我的程序可以创建多个工作表,这些工作表的数量取决于我的dataObject。 我很兴奋,我想和大家分享我的成就

首先,您需要创建SpreadSheetDocument,因为这个原因,我创建了一个方法CreatePackage,并将其作为参数filePath和我的DataObject传递

public void CreatePackage(string filePath, List<DataObject> data)
{
    using (SpreadsheetDocument document = SpreadsheetDocument.Create(filePath, SpreadsheetDocumentType.Workbook)
    )
    {
        CreateParts(document, data);
    }
 }
public void CreatePackage(字符串文件路径,列表数据)
{
使用(电子表格文档=电子表格文档.Create)(文件路径,电子表格文档类型.工作簿)
)
{
创建部件(文档、数据);
}
}
CreateParts方法,接受电子表格文档数据对象

private void CreateParts(SpreadsheetDocument document, List<DataObject> data)
    {
        ExtendedFilePropertiesPart extendedFilePropertiesPart = document.AddNewPart<ExtendedFilePropertiesPart>();
        extendedFilePropertiesPart.Properties = new Properties();

        WorkbookPart workbookPart = document.AddWorkbookPart();
        //Create new sheet for every Unique error
        GenerateWorkbookPart(workbookPart,data.Count);
        //generates new SheetPart for every sheet
        GenerateWorkSheetsParts(workbookPart,data);

    }
private void CreateParts(电子表格文档、列表数据)
{
ExtendedFilePropertiesPart ExtendedFilePropertiesPart=document.AddNewPart();
extendedFilePropertiesPart.Properties=新属性();
WorkbookPart WorkbookPart=document.AddWorkbookPart();
//为每个唯一错误创建新工作表
GenerateWorkbookPart(workbookPart,data.Count);
//为每个图纸生成新的SheetPart
生成工作表零件(工作簿零件、数据);
}
我无法找到ExtendedFilePropertiesPart为什么以及如何依赖于Excell中的超链接,但我确信,如果没有此超链接,即使生成的Excell文件也将损坏,否则超链接将无法工作

接下来,我们需要为工作簿部件创建一个工作簿,也为工作簿创建一个工作表,它将保存所有工作表。对于每个工作表,我们还需要创建工作表部分,但我稍后会回来。目前:

private void GenerateWorkbookPart(WorkbookPart workbookPart, int dataCount)
        {

            Workbook workbook = new Workbook();
            Sheets sheets = new Sheets();
            Sheet sheet = new Sheet();
            for (int i = 1; i < dataCount+2; i++)
            {
                var relId = "rId" + i;
                if (i == 1)
                {
                    sheet = new Sheet()
                    {
                        Name = "Main",
                        SheetId = (uint) i,
                        Id = relId
                    };
                }
                else
                {
                    sheet = new Sheet()
                    {
                        Name = "Unique" + (i-1),
                        SheetId = (uint)i,
                        Id = relId
                    };
                }

                sheets.AppendChild(sheet);
            }
            workbook.AppendChild(sheets);
            workbookPart.Workbook = workbook;
        }
private void GenerateWorkbookPart(WorkbookPart WorkbookPart,int dataCount)
{
工作簿=新工作簿();
板材=新板材();
板材=新板材();
对于(int i=1;i
为什么我要在总数上加+2?因为首先,由于某些原因,工作表的RelationshipId(Id)不能为0,所以我需要从1开始,第二,excel中的第一个页面是导航页面,所以我也跳过了它

为文档创建WorkBookPart后,我将开始为每个工作表创建工作表部分,并用数据填充它

private void GenerateWorkSheetsParts(WorkbookPart workbookPart, List<DataObject> data)
        {
            for (int i = 1; i < data.Count+2; i++)
            {
                var relId = "rId" + i;
                if (i == 1)
                {
                    WorksheetPart workSheetPart = workbookPart.AddNewPart<WorksheetPart>(relId);
                    GenerateWorkSheetPartContent(workSheetPart, i, data);
                }
                else
                {
                    WorksheetPart workSheetPart = workbookPart.AddNewPart<WorksheetPart>(relId);
                    GenerateWorkSheetPartContent(workSheetPart, i, data[i-2].NestedObject);
                }

            }
        }

 private void GenerateWorkSheetPartContent(WorksheetPart worksheetPart,int indexer, List<NestedObject> data)
        {

            Worksheet worksheet = new Worksheet();
            SheetData sheetData = new SheetData();
            Hyperlinks hyperlinks = new Hyperlinks();

            if (indexer == 1)
            {
                sheetData.AppendChild(ConstructHeader("Unique errors", "Count"));
                
                foreach (var @event in data)
                {
                    indexer++;
                    Row row = new Row();
                    row.Append(ConstructCell(@event.ErrorMessage, "A" + indexer, CellValues.String), ConstructCell(@event.ListOfErrorsObject.Count.ToString(), CellValues.Number));
                    sheetData.AppendChild(row);
                    Hyperlink hyperlink = new Hyperlink()
                    {
                        Reference = "A" + indexer,
                        Location = "Unique" + (indexer - 1)+"!A1",
                        Display = "Unique" + indexer
                    };
                    hyperlinks.AppendChild(hyperlink);
                }
                worksheet.Append(sheetData, hyperlinks);
                worksheetPart.Worksheet = worksheet;
            }
            else
            {
                worksheet.AppendChild(sheetData);
                worksheetPart.Worksheet = worksheet;
            }
        }
private void GenerateWorkSheetsParts(WorkbookPart WorkbookPart,列表数据)
{
对于(int i=1;i        private Row ConstructHeader(params string[] headers)
    {
        Row row = new Row();
        foreach (var header in headers)
        {
            row.AppendChild(ConstructCell(header, CellValues.String));
        }
        return row;
    }

    private Cell ConstructCell(string value, CellValues dataType)
    {
        return new Cell()
        {
            CellValue = new CellValue(value),
            DataType = new EnumValue<CellValues>(dataType),
        };
    }
    private Cell ConstructCell(string value, string cellReference, CellValues dataType)
    {
        return new Cell()
        {
            CellReference = cellReference,
            CellValue = new CellValue(value),
            DataType = dataType,
        };
    }
static void AddHyperlink()
    {

        var filePath = "test.xlsx";

        // C1 in Sheet1
        var sheetName1 = "Sheet1";
        var column = "C";
        var row = 1;

        // Link to A10 in Sheet2
        var pathToOtherFile = filePath;
        var sheetName2 = "Sheet2";
        var cellRef = "A10";

        using (var document = SpreadsheetDocument.Open(filePath, true))
        {
            WorkbookPart wbPart = document.WorkbookPart;



            var sheets = document.WorkbookPart.Workbook.Sheets.Cast<Sheet>().ToList();



            var sheet = sheets.Where(x => x.Name == sheetName1).FirstOrDefault();

            string relationshipId = sheets.First().Id.Value;
            //get the worksheetpart by Id
            WorksheetPart worksheetPart = (WorksheetPart)wbPart.GetPartById(relationshipId);
            var worksheet = worksheetPart.Worksheet;


            Cell cell = GetCell(worksheet, column, row);
            var s = cell.LastChild;

            var cell1 = cell;

            CellFormula cellFormula1 = new CellFormula() { Space = SpaceProcessingModeValues.Preserve };
            cellFormula1.Text = $"HYPERLINK(\"[{pathToOtherFile}]{sheetName2}!{cellRef}\", \"Radio Clash\")";
            cell1.CellFormula = cellFormula1;

        }

    }


    private static Cell GetCell(Worksheet worksheet, string columnName, int rowIndex)
    {
        Row row = GetRow(worksheet, rowIndex);

        if (row == null)
            return null;

        return row.Elements<Cell>().Where(c => string.Compare
               (c.CellReference.Value, columnName +
               rowIndex, true) == 0).First();
    }


    // Given a worksheet and a row index, return the row.
    private static Row GetRow(Worksheet worksheet, int rowIndex)
    {
        return worksheet.GetFirstChild<SheetData>().
          Elements<Row>().Where(r => r.RowIndex == rowIndex).First();
    }
    cellFormula1.Text = $"=HYPERLINK(\"[\" & MID(CELL(\"filename\"),SEARCH(\"[\",CELL(\"filename\"))+1, SEARCH(\"]\",CELL(\"filename\"))-SEARCH(\"[\",CELL(\"filename\"))-1) &\"]{sheetName2}!{cellRef}\", \"Radio Clash\")";
cellFormula1.Text = $"HYPERLINK(\"[{pathToOtherFile}]{sheetName2}!{cellRef}\", \"Radio Clash\")";