Find and Call function in dll
gitboy16 opened this issue · comments
Hi,
Thank you for the package.
I manage to assemblies from a dll following the example in the readme file. Would you be able to tell me how I can list the functions in that dll and call it?
Thank you
Best regards
You can get whatever you want through reflection API.
julia> asm = T"System.Reflection.Assembly".LoadFrom(raw"C:\Program Files\dotnet\shared\Microsoft.WindowsDesktop.App\3.1.18\System.Windows.Forms.dll")
System.Reflection.RuntimeAssembly("System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089")
julia> asm.ExportedTypes |> collect
1021-element Array{CLRObject,1}:
System.Drawing.Design.IPropertyValueUIService
System.Drawing.Design.PaintValueEventArgs
System.Drawing.Design.PropertyValueUIHandler
System.Drawing.Design.PropertyValueUIItem
System.Drawing.Design.PropertyValueUIItemInvokeHandler
System.Drawing.Design.UITypeEditor
System.Drawing.Design.UITypeEditorEditStyle
⋮
System.Windows.Forms.VisualStyles.VisualStyleElement+Window+SmallCaptionSizingTemplate
System.Windows.Forms.VisualStyles.VisualStyleElement+Window+FrameLeftSizingTemplate
System.Windows.Forms.VisualStyles.VisualStyleElement+Window+SmallFrameLeftSizingTemplate
System.Windows.Forms.VisualStyles.VisualStyleElement+Window+FrameRightSizingTemplate
System.Windows.Forms.VisualStyles.VisualStyleElement+Window+SmallFrameRightSizingTemplate
System.Windows.Forms.VisualStyles.VisualStyleElement+Window+FrameBottomSizingTemplate
System.Windows.Forms.VisualStyles.VisualStyleElement+Window+SmallFrameBottomSizingTemplate
julia> Form = T"System.Windows.Forms.Form, System.Windows.Forms"
System.Windows.Forms.Form
julia> Form.GetMembers() |> collect
720-element Array{CLRObject,1}:
System.Reflection.RuntimeMethodInfo("Void SetDesktopBounds(Int32, Int32, Int32, Int32)")
System.Reflection.RuntimeMethodInfo("Void SetDesktopLocation(Int32, Int32)")
System.Reflection.RuntimeMethodInfo("Void Show(System.Windows.Forms.IWin32Window)")
System.Reflection.RuntimeMethodInfo("System.Windows.Forms.DialogResult ShowDialog()")
System.Reflection.RuntimeMethodInfo("System.Windows.Forms.DialogResult ShowDialog(System.Windows.Forms.IWin32Window)")
System.Reflection.RuntimeMethodInfo("System.String ToString()")
System.Reflection.RuntimeMethodInfo("Boolean ValidateChildren()")
⋮
System.Reflection.RuntimeEventInfo("System.EventHandler SystemColorsChanged")
System.Reflection.RuntimeEventInfo("System.ComponentModel.CancelEventHandler Validating")
System.Reflection.RuntimeEventInfo("System.EventHandler Validated")
System.Reflection.RuntimeEventInfo("System.EventHandler ParentChanged")
System.Reflection.RuntimeEventInfo("System.EventHandler ImeModeChanged")
System.Reflection.RuntimeEventInfo("System.EventHandler Disposed")
System.Windows.Forms.Form+ControlCollection
See also: #11
Thank you. I manage to find the function I wanted. When I call it, it returns me the following:
System.Object[,,]("System.Object[,,]")
I am not sure what that is.
Is there a way to read the output in a Julia object ...like matrix, vector or anything else?
Also is there a way to create such an object from Julia and pass it to a function in the dll.
I am not sure what that is.
It is just a multidimensional array with a rank of 3. All array types are subtypes of System.Array
.
julia> isassignable(T"System.Array", T"System.Int32[,,]")
true
julia> isassignable(T"System.Int32[,,]", T"System.Array")
false
Is there a way to read the output in a Julia object ...like matrix, vector or anything else?
We have collect
function that converts .NET arrays to Julia arrays.
However, n-d arrays are not fully supported now, so they become 1-d arrays when you collect them. You can usereshape
function to recover dimension sizes.
public static int[,,] Get3DArray() {
return new int[2, 2, 2] {
{{1, 2}, {3, 4}},
{{5, 6}, {7, 8}}
};
}
julia> a = YourClass.Get3DArray()
System.Int32[,,]("System.Int32[,,]")
julia> collect(a)
8-element Array{Int32,1}:
1
2
3
4
5
6
7
8
julia> reshape(ans, 2, 2, 2)
2×2×2 Array{Int32,3}:
[:, :, 1] =
1 3
2 4
[:, :, 2] =
5 7
6 8
Other useful methods for .NET arrays:
julia> clrtypeof(a) # returns a CLR Type object
System.Int32[,,]
julia> clreltype(a) # returns the element type of a CLR array
System.Int32
julia> eltype(a) # returns the element type in Julia, if the array is collected
Int32
julia> a.GetValue(Int32[1,0,1]) # to access the n-d array without collecting
6
Also is there a way to create such an object from Julia and pass it to a function in the dll.
Yes, just pass the object to the function.
julia> b = reshape(1:8, 2, 2, 2)
2×2×2 reshape(::UnitRange{Int64}, 2, 2, 2) with eltype Int64:
[:, :, 1] =
1 3
2 4
[:, :, 2] =
5 7
6 8
julia> Console.WriteLine(b);
System.Int64[,,]
If you want an uninitialized array, there is a convenient function:
julia> DotNET.arrayof(T"System.Int32", (2, 2, 2))
System.Int32[,,]("System.Int32[,,]")
Thank you. The above is very useful.
Let's say I have the following:
julia> data = DotNET.arrayof(T"System.Object",(2,2,2))
System.Object[,,]("System.Object[,,]")
julia> data |> collect
8-element Vector{CLRObject}:
null
null
null
null
null
null
null
null
How do I actually add values in that vector?
(I want the array to be initilised with values)
Not sure if it can help but when I call some function in the dll I get something like that:
julia> Form.getIDs("")
System.Object[,,]("System.Object[,,]")
julia> Form.getIDs("") |> collect
4-element Vector{CLRObject}:
System.String("bi_id")
System.String("name")
System.String("internal")
System.String("external")
Thank you in advance.
arraystore
can do the job, which I forgot to mention.
julia> data = DotNET.arrayof(T"System.Object", (2, 2, 2))
System.Object[,,]("System.Object[,,]")
julia> DotNET.arraystore(data, (0, 0, 0), "bi_id")
null
julia> DotNET.arrayload(data, (0, 0, 0))
"bi_id"
julia> collect(data)
8-element Array{CLRObject,1}:
System.String("bi_id")
null
null
null
null
null
null
null
Note: In case you have a CLRObject
that represents a primitive type (aka "boxed"), you can call unbox
to retrieve the underlying data:
julia> collect(data)[1]
System.String("bi_id")
julia> DotNET.unbox(ans)
"bi_id"
Since Julia does not distinguish between boxed and unboxed types, values returned from .NET functions are automatically unboxed. So far, the collect
function is not recursive, and I wonder if this should be changed in the future...
You are a star. Thank you very much. I think it is worth saving the above in a manual or wiki as it can be useful to others. Feel free to close this "issue".
Hi, I hope you are well. I was wondering how hard would it be to support n-d arrays so it is possible know what is the real dimension of the arrays returned? Right now I have to guess it which is a bit of an issue. Thank you.
Supported in v0.2.0
, README updated.
You are the best. Thank you.