You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: docs/guides-basic/accepting-range-parameters-in-udfs.md
+64-14
Original file line number
Diff line number
Diff line change
@@ -3,7 +3,50 @@ title: "Accepting Range Parameters in UDFs"
3
3
---
4
4
Parameters with the type of Excel's Range COM object are not directly supported by Excel-DNA. There is a list of allowed parameter types here: [Reference for data types in UDFs](../../../reference-data-type-marshalling)
5
5
6
-
If you want the function to also accept a sheet reference, your parameter should be of type 'object' and marked with an <ExcelArgument(AllowReference:=true)> attribute. In that case you'll get an object of type ExcelDna.Integration.ExcelReference if the function is called with a sheet reference.
6
+
You should prefer to get the values directly from the input parameter, without getting the Range COM object. It's also much more efficient doing it that way.
7
+
8
+
Your simple function that takes a single value or a range of values converted to an array, might then look like this:
9
+
10
+
```c#
11
+
publicstaticobjectConcat2(object[,] values)
12
+
{
13
+
stringresult="";
14
+
introws=values.GetLength(0);
15
+
intcols=values.GetLength(1);
16
+
for (inti=0; i<rows; i++)
17
+
{
18
+
for (intj=0; j<cols; j++)
19
+
{
20
+
objectvalue=values[i, j];
21
+
result+=value.ToString();
22
+
}
23
+
}
24
+
returnresult;
25
+
}
26
+
```
27
+
28
+
Typically you'd want to check the type of the value object, and do something different based on that. The `object[,]` array passed from Excel-DNA could have items of the following types:
29
+
30
+
```
31
+
double
32
+
string
33
+
bool
34
+
ExcelDna.Integration.ExcelError
35
+
ExcelDna.Integration.ExcelEmpty
36
+
ExcelDna.Integration.ExcelMissing (if the function is called with no parameter, as `=Concat2()`).
37
+
```
38
+
39
+
If you change the signature to have a single parameter of type `object` (instead of `object[,]`), like this:
40
+
```
41
+
public static object Concat2(object value)
42
+
```
43
+
then, depending on how the function is called, you might get one of the above types as the value or you might get an object[,] array as the value, so your type checks would look a bit different before you do the iteration.
44
+
45
+
46
+
If you really want information about the calling range, like the address, you need to
47
+
* Apply a `[ExcelArgument(AllowReference=true)]` attribute to the `object input` parameter (in VB `<ExcelArgument(AllowReference:=true)>` )
48
+
* Check whether the object you receive is of type `ExcelReference` (this is a thin wrapper over the C API reference information).
49
+
* Either use the C API calls to get information about the `ExcelReference` (like a sheet name), or create a `Range` COM object from the information in the `ExcelReference`. This `Range` object needs to be used with care when called from a function.
7
50
8
51
ExcelReference is not the same as the COM Range type, it is a small wrapper type for the Excel C API reference structure. From the ExcelReference it is possible to get a COM Range -
9
52
@@ -21,20 +64,27 @@ Private Function ReferenceToRange(ByVal xlRef As ExcelReference) As Object
21
64
EndFunction
22
65
```
23
66
67
+
or in C#:
24
68
25
-
The internal xlfReftext call in ReferenceToRange can only be made from functions that are registered as a macro-sheet functions. For this the exported function will need to be marked as IsMacroType:=True.
0 commit comments