在 ExcelDNA UDF 中设置单元格公式

Set Cell Formula in ExcelDNA UDF

我正在为 Excel 用户开发一个 UDF(用户定义的函数),在 ExcelDNA 的帮助下,这项任务似乎很容易。但是,当我使用以下两个公式在 Excel 的单元格中对其进行测试时,两者都显示 #VALUE!。需要帮助来解决这个问题,谢谢。

=mySetCellFormula("Test", "")
=mySetCellFormula("Test", "A1")

Imports System.Net
Imports System.Drawing
Imports System.Windows.Forms
Imports Microsoft.Office.Core
Imports Excel = Microsoft.Office.Interop.Excel
Imports ExcelDna.Integration
Imports ExcelDna.Integration.XlCall

Public Module MyFunctions
    Public Function mySetCellFormula(ByVal sFormuaR1C1 As String, ByVal cellAddress As String) As String
        ' Get the correct application instance
        Dim xlApp As Excel.Application
        Dim xlSheet As Excel.Worksheet
        Dim xlCell As Excel.Range
        xlApp = CType(ExcelDnaUtil.Application, Excel.Application)
        xlSheet = CType(xlApp.ActiveSheet(), Excel.Worksheet)
        If cellAddress = "" Then
            xlCell = xlApp.ActiveCell()
        Else
            xlCell = xlSheet.Range(cellAddress)
        End If
        'xlCell.FormulaR1C1 = "=" & Chr(34) & sFormuaR1C1 & Chr(34)
        xlCell.FormulaR1C1 = "=" & sFormuaR1C1
        mySetCellFormula = ""
    End Function
End Module

感谢Govert对Excel计算模型概念的启发,最后我制定了如下解决方案:

Imports System.Net
Imports System.Drawing
Imports System.Windows.Forms
Imports Microsoft.Office.Core
Imports Excel = Microsoft.Office.Interop.Excel
Imports ExcelDna.Integration
Imports ExcelDna.Integration.XlCall

Public Module MyFunctions
    Public Function mySetCellFormula(ByVal sFormuaR1C1 As String, ByVal cellAddress As String) As String
        ' Get the correct application instance
        Dim xlApp As Excel.Application
        Dim xlSheet As Excel.Worksheet
        Dim xlCell As Excel.Range
        xlApp = CType(ExcelDnaUtil.Application, Excel.Application)
        xlSheet = CType(xlApp.ActiveSheet(), Excel.Worksheet)
        If cellAddress = "" Then
            xlCell = xlApp.ActiveCell()
        Else
            xlCell = xlSheet.Range(cellAddress)
        End If

        ExcelAsyncUtil.QueueAsMacro( _
            Sub()
                xlCell.FormulaR1C1 = "=" & sFormuaR1C1
            End Sub)

        mySetCellFormula = ""
    End Function
End Module

感谢 Govert 和 Wayne;我需要相同的实现,但在 C# 中: 我以以下对我有用的结尾:

public static void SetCellFormula(string cellAddress, string sFormua)
{
  try
  {
    Excel.Range xlCell;
    var xlApp = (Excel.Application)ExcelDnaUtil.Application;
    var activeSheet = xlApp.ActiveSheet;
    var xlSheet = (Excel.Worksheet)activeSheet;
    if ( string.IsNullOrEmpty(cellAddress))
    {
      xlCell = xlApp.ActiveCell;
    }
    else
    {
      xlCell = xlSheet.get_Range(cellAddress);
    }

    ExcelAsyncUtil.QueueAsMacro(
      () =>
        {
          xlCell.Formula = $"={sFormua}";
        });
  }
  catch (Exception ex)
  {
    Debug.WriteLine(ex);
  }
}

连同;

 public static void SetCellValue(string cellAddress, object cellValue)
{
  try
  {
    Excel.Range xlCell;
    var xlApp = (Excel.Application)ExcelDnaUtil.Application;
    var activeSheet = xlApp.ActiveSheet;
    var xlSheet = (Excel.Worksheet)activeSheet;
    if (string.IsNullOrEmpty(cellAddress))
    {
      xlCell = xlApp.ActiveCell;
    }
    else
    {
      xlCell = xlSheet.get_Range(cellAddress);
    }

    ExcelAsyncUtil.QueueAsMacro(
      () =>
        {
          xlCell.Value2 = cellValue;
        });
  }
  catch (Exception exc)
  {
    Debug.WriteLine(exc);
  }
}

可以通过以下方式验证:

  [ExcelFunction(Name = "TestFormula", Description = "Test Set Formula on Cell")]
public static string TestFormula()
{
  SetMyCellValue("A1", 1);

  SetMyCellValue("A2", 2);
  SetMyCellValue("A3", 4);
  SetMyCellValue("A4", 8);

  SetMyCellValue("B1", -1);
  SetMyCellValue("C1", 3);
  SetMyCellValue("D1", 5);

  SetCellFormula("B2", "$A*B-$A2");

  return "=TestFormula";
}