Popular Post LarsJ Posted September 23, 2017 Popular Post Posted September 23, 2017 (edited) .NET Common Language Runtime (CLR) Framework was published five months ago. CLR.au3 which is the main UDF makes it possible to execute .NET code directly in an AutoIt script. .NET code in this context should be perceived in a very broad sense. As shown in the examples, there are virtually no limits to the possibilities that the UDF opens up for. .NET Common Language Runtime (CLR) Framework is the result of the work in Using .NET libary with AutoIt, possible? CLR.au3 is implemented in this thread. Most of the code in CLR.au3 is a translation of CLR.ahk from .NET Framework Interop (CLR, C#, VB) in the AutoHotkey forum. DotNet.au3 is a complete translation of CLR.ahk. This example is about DotNet.au3. It contains information about the functions in the UDF. Usage of the functions is demonstrated through small examples. And there is a description of a few .NET Framework concepts. The AutoHotkey project The AutoHotkey project started in .NET Framework Interop in autumn 2009. The latest update of CLR.ahk in .NET Framework Interop (CLR, C#, VB) was november 2011. The whole project seems to have been developed over this 3-year period. The project was developed by Lexikos in the AutoHotkey forum. He certainly looks very knowledgeable about the code in the .Net Framework and he has done a great job in implementing the AutoHotkey code in CLR.ahk. Lots of credit to Lexikos. If you want to test the AutoHotkey code, you can find a recipe here. DotNet.au3 Because a lot of COM support is included internally in AutoHotkey and especially because AutoHotkey natively supports safearrays, the code in CLR.ahk is short and compact. 150 code lines. In the zip-file below AutoIt safearray support is implemented in two separate UDFs: SafeArray.au3 and AccVarsUtilities.au3. Both of these UDFs were started in Accessing AutoIt Variables. That way, it has also been possible to keep the code in DotNet.au3 short and compact. 190 code lines. You should take a look at DotNet.au3. It's nice and easily readable code (maybe not so easy to understand, but easy to read). 7 functions DotNet.au3 contains 7 functions and 2 internal functions. The first 3 functions DotNet_Start(), DotNet_StartDomain() and DotNet_StopDomain() are only used to optimize the .NET Framework host (more about .NET concepts below). If you are satisfied with the default .NET Framework host, you can completely skip these functions. The next 3 functions DotNet_LoadAssembly(), DotNet_LoadCScode() and DotNet_LoadVBcode() are used to load .NET code into a domain. Before it's possible to execute .NET code it must be loaded into a domain. If DotNet_Start() and DotNet_StartDomain() have not been called, DotNet_Start() is called automatically by the 3 functions and the default domain is used to execute .NET code. DotNet_LoadAssembly() loads .NET code in a .NET assembly DLL-file into a domain. The other functions compiles C# and VB source code on the fly, creates a .NET assembly DLL-file in memory and loads the assembly file into a domain. All 3 functions returns a .NET code object which is a reference to the .NET code. The last function DotNet_CreateObject() takes a .NET code object and a class name as input parameters and creates an object as an instance of the class. The class must be defined in the .NET code. Because .NET code is object-oriented code, everything is performed through objects. Now the methods of the object can be called and this executes the functions in the .NET code. Below is a brief description of the 7 functions. $oRuntimeHost = DotNet_Start( $sVersion = "" ) DotNet_Start() Loads the .NET Framework code-execution environment known as the CLR into the AutoIt process and returns a .NET runtime host (a .NET Framework host). Default is to use the latest version of .NET Framework installed on the PC. Specify $sVersion eg. "v2.0.50727" to use an older version of .NET Framework. DotNet_Start() is automatically called by the other functions in DotNet.au3. You only need to call DotNet_Start() if you want to use an older version of .NET Framework. @error = 1 indicates that DotNet_Start() has failed. DotNet_StartDomain( ByRef $oAppDomain, $sFriendlyName = "", $sBaseDirectory = "" ) Creates and starts a user domain to run .NET code. Several user domains can be created and started at the same time. $oAppDomain is the returned domain object. $sFriendlyName is a name to identify the domain. $sBaseDirectory is the base directory where from .NET assemblies are loaded into the domain. The only purpose of $sFriendlyName is to be able to recognize the domain when the domains are listed with DotNet_ListDomains(). DotNet_ListDomains() is a utility function implemented in DotNetUtils.au3. The purpose of $sBaseDirectory is to be able to specify the directory where .NET assemblies are stored. The usage of $sBaseDirectory is demonstrated in examples. A default domain is automatically created by the other functions in DotNet.au3. You only need to call DotNet_StartDomain() if you want to specify a base directory for the domain. DotNet_StopDomain( ByRef $oAppDomain ) Unloads .NET assemblies loaded into the user domain and stops the domain. $oAppDomain is the domain object. The default domain cannot be stopped. $oNetCode = DotNet_LoadAssembly( $sAssemblyName, $oAppDomain = 0 ) DotNet_LoadAssembly() loads .NET code in a .NET assembly DLL-file into a domain and returns a .NET code object (a reference to the .NET code). $sAssemblyName is the name of the assembly DLL-file. $oAppDomain is the user domain. If no user domain is specified the assembly is loaded into the default domain. @error = 2 indicates that DotNet_LoadAssembly() has failed. $oNetCode = DotNet_LoadCScode( $sCode, $sReferences = "", $oAppDomain = 0, $sFileName = "", $sCompilerOptions = "" ) $oNetCode = DotNet_LoadVBcode( $sCode, $sReferences = "", $oAppDomain = 0, $sFileName = "", $sCompilerOptions = "" ) DotNet_LoadCScode() and DotNet_LoadVBcode() compiles C# and VB source code on the fly, creates a .NET assembly DLL-file in memory, loads the assembly file into a domain and returns a .NET code object. $sCode is the C# or VB source code. $sReferences is a pipe (|) delimited list of .NET DLL assemblies that the C#/VB code requires. Eg. "System.dll" or "System.Windows.Forms.dll". $oAppDomain is the user domain. If no user domain is specified the code is loaded into the default domain. The other parameters are related to the compilation process. If $sFileName is the name of a DLL-file the code is compiled into a .NET assembly DLL-file. Else the code is compiled in memory. $sCompilerOptions is rarely used. See Microsoft documentation for details. @error = 3/4 indicates that DotNet_LoadCScode() or DotNet_LoadVBcode() has failed. @error = 5 indicates a syntax error in the C# or VB source code. Such an error can be corrected by correcting the error in the source code. $oObject = DotNet_CreateObject( ByRef $oNetCode, $sClassName, $v3 = Default, ..., $v9 = Default ) DotNet_CreateObject() creates an object as an instance of a class. $oNetCode is a .NET code object as returned by one of the functions DotNet_LoadAssembly(), DotNet_LoadCScode() or DotNet_LoadVBcode(). $sClassName is the name of a class defined in the .NET code. The other parameters depends on the specific class. Summary Two functions must be called to execute .NET code directly in an AutoIt script. One of the functions DotNet_LoadAssembly(), DotNet_LoadCScode() or DotNet_LoadVBcode() to load the .NET code into a domain. And DotNet_CreateObject() to create an object from a class defined in the .NET code. Now the functions in the .NET code can be executed by calling the methods of the object. .NET concepts The .NET CLR In more or less the same way as AutoIt3.exe or AutoIt3_x64.exe is needed to run AutoIt code, the .NET CLR (Common Language Runtime) or the .NET Framework code-execution environment is needed to run .NET code. To be able to run .NET code inside an AutoIt script, the CLR or the .NET Framework code-execution environment must be loaded into the AutoIt process. This is the purpose of DotNet_Start(). The CLR can be loaded into a process through several of the functions in MSCorEE.dll. CorBindToRuntimeEx is one of these functions. DotNet_Start() executes CorBindToRuntimeEx in MSCorEE.dll and loads the CLR into the AutoIt process. A program or a part of a program which is able to start the CLR and execute .NET code is referred to as a .NET runtime host, a CLR host or simply a .NET Framework host. The code in DotNet.au3 implements an AutoIt .NET Framework host. Managed/unmanaged code .NET code which is executed (or managed) through the functions in the CLR is referred to as managed code. C# and VB code is managed code. Code which is not executed through the functions in the CLR is referred to as unmanaged code. AutoIt code is unmanaged code. You usually only distinguish between managed/unmanaged code in relation to .NET code and the .NET Framework. When you are executing .NET code there is often a part of both unmanaged and managed code involved. If you are executing .NET code through AutoIt, the AutoIt code is the unmanaged code and the .NET code is the managed code. The functions in MSCorEE.dll are some of the functions which belongs to the .NET Framework that can be executed from unmanaged code eg. AutoIt code. That's the reason why these functions are used to start the .NET Framework. The COM interfaces _AppDomain, _Assembly and _Type in Interfaces.au3 are some of the interfaces which belongs to the .NET Framework that can be used in unmanaged code. That's the reason why these interfaces are used to implement the functions in DotNet.au3. Managed code like C# cannot be translated into unmanaged code like AutoIt. There is no way to translate a command like "using System;" from C# to AutoIt. In many situations you can implement the same code in AutoIt as you can in C#. But that's generally not a simple translation of the C# code. It's a new implementation of the code. .NET domains With the functions in DotNet.au3 you can create an AutoIt .NET Framework host as shown in this picture: The blue box illustrates the unmanaged AutoIt code which is used to start the .NET Framework and load the CLR into the AutoIt process. The red box illustrates the default domain and several user domains where the managed .NET code is executed. Managed .NET code is always executed within a domain. The purpose of DotNet_StartDomain() and DotNet_StopDomain() is to create, start and stop user domains. If DotNet_StartDomain() isn't called the default domain is used. A domain in managed code is equivalent to a process in unmanaged code. The purpose of domains is to prevent that a crash in one part of the .NET code should lead to a crash in all of the .NET code. A crash of the code in a domain makes the domain inapplicable and a new domain must be created with DotNet_StartDomain(). This is very similar to the way that code is executed in separate processes in the operating system. The purpose of executing code in separate processes is (among other things) to prevent that a crash of the code in one process should lead to a crash of the code in several processes and finally to a crash of the entire operating system. A crash of the code in the default domain makes the entire CLR, that's loaded into the AutoIt process inapplicable. Because it's only possible to load the CLR into the same process once, the only way to reload the CLR is to restart the entire AutoIt process. That is to stop and start the AutoIt script. Usually it does not matter if the default domain or a user domain is used to execute .NET code. It's only strictly necessary to create a user domain if there is a need to specify a base directory for .NET assemblies. The only way to specify a base directory is through DotNet_StartDomain(). .NET assemblies Before it's possible to execute .NET code in a domain, the code must be loaded into the domain. Code is always loaded into a domain through a .NET assembly. This is also the case when .NET code is created on the fly by compiling C# or VB code in memory. Then the .NET code is stored in a .NET assembly which is created in memory and therefrom loaded into the domain. The purpose of DotNet_LoadAssembly() is to load .NET code in a .NET assembly DLL-file into a domain. Either the default domain or a user domain. The purpose of DotNet_LoadCScode() and DotNet_LoadVBcode() is to compile C# and VB code on the fly, create a .NET assembly in memory and load the .NET code into a domain. All 3 functions returns a .NET code object which can be used in DotNet_CreateObject() to create .NET objects. When a .NET assembly is stored as a file on disk it's usually stored with a DLL- or an EXE-extension. It contains information about classes, objects, methods, properties, events, datatypes etc. concerning the resources in the assembly. It's a binary file. A .NET assembly DLL-file should not be confused with a standard DLL-file eg. a DLL-file that belongs to the Windows operating system. A .NET assembly DLL-file contains managed code. A standard DLL-file contains unmanaged code. In the same way as there are tools to extract information about the code in a standard DLL-file, there are also tools to extract information about the code in a .NET assembly DLL-file. One of these tools is ILSpy. More about ILSpy in examples section below. .NET objects Because .NET code is object-oriented code, everything is performed through objects, properties and methods. When functions are executed in .NET code, they are executed as object methods. DotNet_CreateObject() takes a .NET code object as returned by DotNet_LoadAssembly(), DotNet_LoadCScode() or DotNet_LoadVBcode() and a class name as input parameters and creates a .NET object as an instance of the class. The class must be defined in the .NET code. Now the methods of the object can be called and this executes the functions in the .NET code. Examples The Examples folder contains scripts to demonstrate the usage of the functions in DotNet.au3. In scripts where .NET code is needed for the demonstration, the code is copied from original AutoHotkey examples: An example with a XPTable.dll .NET assembly (implemented in AutoIt in this post) and two simple C# and VB code examples. I don't want to review all examples. The examples are small examples like this: #include "..\..\Includes\DotNet.au3" Opt( "MustDeclareVars", 1 ) Example() Func Example() ; Start the latest version of .NET Framework ; DotNet_Start() is automatically called by the other functions in DotNet.au3 ; You only have to call DotNet_Start() if you need an older version of .NET Framework DotNet_Start() If @error Then Return ConsoleWrite( "DotNet_Start ERR" & @CRLF ) ConsoleWrite( "DotNet_Start OK" & @CRLF ) EndFunc The example simply starts the .NET Framework from an AutoIt script. Run the examples in SciTE by pressing F5 on the keyboard. A few examples with "(compile me)" in the file name must be compiled. Run these examples by double-clicking the exe-file. ILSpy .NET assembly browserILSpy is an open-source .NET assembly browser. Download ILSpy_Master_2.4.0.1963_Binaries.zip, unzip it and run ILSpy.exe. There is no installer. If you open \Examples\4) DotNet_LoadAssembly\XPTable.dll through the File | Open... menu you'll see this information in the right pane window: // ...\Examples\4) DotNet_LoadAssembly\XPTable.dll // XPTable, Version=1.1.0.27823, Culture=neutral, PublicKeyToken=24950705800d2198 // Global type: <Module> // Architecture: AnyCPU (64-bit preferred) // Runtime: .NET 1.1 using System; using System.Reflection; [assembly: AssemblyVersion("1.1.0.27823")] [assembly: CLSCompliant(true)] [assembly: AssemblyCompany("")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyCopyright("Copyright © 2005, Mathew Hall. All rights reserved.")] [assembly: AssemblyDelaySign(false)] [assembly: AssemblyDescription("A fully customisable ListView style control based on Java's JTable")] [assembly: AssemblyKeyFile("..\\..\\XPTable.snk")] [assembly: AssemblyKeyName("")] [assembly: AssemblyProduct("XPTable")] [assembly: AssemblyTitle("XPTable")] [assembly: AssemblyTrademark("")] Note the comments in the top. This line: // Architecture: AnyCPU (64-bit preferred) means that the DLL-file can be used as both a 32 and a 64 bit .NET assembly DLL-file. Using C# and VB Code in AutoItUsing C# and VB Code in AutoIt through .NET Framework is an example that uses DotNet.au3 UDF in order to be able to execute compiled C# and VB code in AutoIt scripts. Zip-file The zip-file contains two folders: Examples\ and Includes\. The project depends on eight include files of which DotNet.au3 is the actual UDF. To make it easier to use the UDF, all include files are collected in one large file: DotNetAll.au3. To use DotNet.au3 UDF in your own project just include DotNetAll.au3. You need AutoIt 3.3.10 or later. Tested on Windows 10, Windows 7 and Windows XP. Comments are welcome. Let me know if there are any issues. DotNet.7z Edited October 7, 2017 by LarsJ Last paragraph in Examples section ptrex, IndianSage, Gianni and 6 others 9 Controls, File Explorer, ROT objects, UI Automation, Windows Message MonitorCompiled code: Accessing AutoIt variables, DotNet.au3 UDF, Using C# and VB codeShell menus: The Context menu, The Favorites menu. Shell related: Control Panel, System Image ListsGraphics related: Rubik's Cube, OpenGL without external libraries, Navigating in an image, Non-rectangular selectionsListView controls: Colors and fonts, Multi-line header, Multi-line items, Checkboxes and icons, Incremental searchListView controls: Virtual ListViews, Editing cells, Data display functions
LarsJ Posted September 23, 2017 Author Posted September 23, 2017 Tomorrow I'll add some examples that shows how to use DotNet.au3 UDF. KaFu and Gianni 2 Controls, File Explorer, ROT objects, UI Automation, Windows Message MonitorCompiled code: Accessing AutoIt variables, DotNet.au3 UDF, Using C# and VB codeShell menus: The Context menu, The Favorites menu. Shell related: Control Panel, System Image ListsGraphics related: Rubik's Cube, OpenGL without external libraries, Navigating in an image, Non-rectangular selectionsListView controls: Colors and fonts, Multi-line header, Multi-line items, Checkboxes and icons, Incremental searchListView controls: Virtual ListViews, Editing cells, Data display functions
ptrex Posted September 25, 2017 Posted September 25, 2017 (edited) Hi Lars, Thanks for jumping on the .NET wagon, and delivering this nice UDF. !! In the theoretical background you provided, there's 1 crucial item missing to get to understand the full picture of the .NET CodeDOM Compiler Class ... The .NET CodeDom Class is just a wrapper around the CSC and VBC EXE. And has some limitations : https://stackoverflow.com/questions/7852926/microsoft-roslyn-vs-codedom CodeDom is a precursor to Roslyn, but is only marginally related. Essentially, CodeDom is a simple and (somewhat) language agnostic way to generate code that was added in .NET 1.0 to support designers (a la WinForms). Because CodeDom was an attempt at providing a unified model that can generate code in C#, VB, and other languages, it lacks high fidelity with any of the languages that it supports (that's why you can't create a switch statement with CodeDom). CSharpCodeProvider.CompileAssemblyFromSource is simply a wrapper around executing csc.exe ... One big difference I see: with CodeDom, each time you compile some C# or VB.NET, it happens out of process. CSC.exe or VBC.exe are the real workers behind the scene. So basically you can do the same with just a few lines of code. DotNet Compiler Wrapper Hopefully you keep us surprising with your expertise on this matter Rgds ptrex Edited September 25, 2017 by ptrex Contributions :Firewall Log Analyzer for XP - Creating COM objects without a need of DLL's - UPnP support in AU3Crystal Reports Viewer - PDFCreator in AutoIT - Duplicate File FinderSQLite3 Database functionality - USB Monitoring - Reading Excel using SQLRun Au3 as a Windows Service - File Monitor - Embedded Flash PlayerDynamic Functions - Control Panel Applets - Digital Signing Code - Excel Grid In AutoIT - Constants for Special Folders in WindowsRead data from Any Windows Edit Control - SOAP and Web Services in AutoIT - Barcode Printing Using PS - AU3 on LightTD WebserverMS LogParser SQL Engine in AutoIT - ImageMagick Image Processing - Converter @ Dec - Hex - Bin -Email Address Encoder - MSI Editor - SNMP - MIB ProtocolFinancial Functions UDF - Set ACL Permissions - Syntax HighLighter for AU3ADOR.RecordSet approach - Real OCR - HTTP Disk - PDF Reader Personal Worldclock - MS Indexing Engine - Printing ControlsGuiListView - Navigation (break the 4000 Limit barrier) - Registration Free COM DLL Distribution - Update - WinRM SMART Analysis - COM Object Browser - Excel PivotTable Object - VLC Media Player - Windows LogOnOff Gui -Extract Data from Outlook to Word & Excel - Analyze Event ID 4226 - DotNet Compiler Wrapper - Powershell_COM - New
LarsJ Posted September 25, 2017 Author Posted September 25, 2017 Hopefully, I do not offend anyone by saying that the code in CLR.au3 is a bit messy. DotNet.au3 is primarily a rewrite of CLR.au3 so the code appears a bit nicer. And at the same time it's a complete translation of CLR.ahk. DotNet.au3 (and CLR.ahk) can also be used on Windows XP. I'm not very excited about the .NET Framework or .NET code, so don't expect a lot of code from me. There are a few topics that I find interesting, which I also find interesting from an AutoIt point of view. One of these topics is the ability to execute compiled code in particular in relation to array manipulations. This is illustrated in the example with prime numbers. So this is the kind of examples with just a few code lines I have in mind. And for such small pieces of code, I don't think I need anything more advanced than this. All examples I've tested works fine. There are a few other topics I find interesting. Maybe I'll make a couple of examples for these topics. The section in first post about .NET concepts is just a simple overview. It certainly is not the full picture of anything. And I don't think you need the full picture to use the UDF or to add compiled C# or VB code to your AutoIt scripts. Controls, File Explorer, ROT objects, UI Automation, Windows Message MonitorCompiled code: Accessing AutoIt variables, DotNet.au3 UDF, Using C# and VB codeShell menus: The Context menu, The Favorites menu. Shell related: Control Panel, System Image ListsGraphics related: Rubik's Cube, OpenGL without external libraries, Navigating in an image, Non-rectangular selectionsListView controls: Colors and fonts, Multi-line header, Multi-line items, Checkboxes and icons, Incremental searchListView controls: Virtual ListViews, Editing cells, Data display functions
ptrex Posted September 25, 2017 Posted September 25, 2017 Not offended at all ... always happy to see a good UDF popping up. Just wanted to complete that background info, which dependencies CodeDom has (relying on CSC.exe and VBC.exe), for those who wants to take a shortcut.. (Please regard this as complementary info) At least it must have been a good "Brain Gym" for you doing the conversion from AHK to AU3 Rgds ptrex Contributions :Firewall Log Analyzer for XP - Creating COM objects without a need of DLL's - UPnP support in AU3Crystal Reports Viewer - PDFCreator in AutoIT - Duplicate File FinderSQLite3 Database functionality - USB Monitoring - Reading Excel using SQLRun Au3 as a Windows Service - File Monitor - Embedded Flash PlayerDynamic Functions - Control Panel Applets - Digital Signing Code - Excel Grid In AutoIT - Constants for Special Folders in WindowsRead data from Any Windows Edit Control - SOAP and Web Services in AutoIT - Barcode Printing Using PS - AU3 on LightTD WebserverMS LogParser SQL Engine in AutoIT - ImageMagick Image Processing - Converter @ Dec - Hex - Bin -Email Address Encoder - MSI Editor - SNMP - MIB ProtocolFinancial Functions UDF - Set ACL Permissions - Syntax HighLighter for AU3ADOR.RecordSet approach - Real OCR - HTTP Disk - PDF Reader Personal Worldclock - MS Indexing Engine - Printing ControlsGuiListView - Navigation (break the 4000 Limit barrier) - Registration Free COM DLL Distribution - Update - WinRM SMART Analysis - COM Object Browser - Excel PivotTable Object - VLC Media Player - Windows LogOnOff Gui -Extract Data from Outlook to Word & Excel - Analyze Event ID 4226 - DotNet Compiler Wrapper - Powershell_COM - New
junkew Posted September 25, 2017 Posted September 25, 2017 Would be nice to see example on generics. We struggle with the powershell automation namespace when we get a collection of psobjects back. Will check the clr and dotnet udfs to see if this udf gives better result. Endstate should be a broad native support for .net. FAQ 31 How to click some elements, FAQ 40 Test automation with AutoIt, Multithreading CLR .NET Powershell CMDLets
LarsJ Posted September 26, 2017 Author Posted September 26, 2017 ptrex, I was very curious to see if it was possible in a straightforward way to translate the AutoHotkey code into AutoIt code. And that was possible. My conclusion is that there is not much they can do in AutoHotkey code that we can't do in AutoIt code. junkew, I don't think there are many generic examples that are particular interesting from an AutoIt point of view. I have read most of the posts. I have to admit that I have not clicked all the links. I don't use PowerShell so I'll not be able to help in this area. Controls, File Explorer, ROT objects, UI Automation, Windows Message MonitorCompiled code: Accessing AutoIt variables, DotNet.au3 UDF, Using C# and VB codeShell menus: The Context menu, The Favorites menu. Shell related: Control Panel, System Image ListsGraphics related: Rubik's Cube, OpenGL without external libraries, Navigating in an image, Non-rectangular selectionsListView controls: Colors and fonts, Multi-line header, Multi-line items, Checkboxes and icons, Incremental searchListView controls: Virtual ListViews, Editing cells, Data display functions
junkew Posted September 26, 2017 Posted September 26, 2017 The general problem we face in clr.au3 but assume with dotnet.au3 will be similar (i will test coming week) is calling methods on generic collections. So also looking for another function in another namespace that return(s) a generic collection and manage it from AutoIt code (no issue in C#). Powershell collection is just an example Return Value Type: System.Collections.ObjectModel.Collection(Of PSObject) A Collection(Of T) collection of PSObject objects that contain the output of the pipeline. 2 . Exercise instead of compiling with the compilers of .net you can emit on the fly (much harder and did not see many examples on the internet) https://docs.microsoft.com/en-us/dotnet/framework/reflection-and-codedom/emitting-dynamic-methods-and-assemblies would be in the end similar to FASM solutions but then completely in AutoIt. FAQ 31 How to click some elements, FAQ 40 Test automation with AutoIt, Multithreading CLR .NET Powershell CMDLets
ptrex Posted September 26, 2017 Posted September 26, 2017 Larj, Thanks, ....Good to know we don't have to be shy working with AU3 rather than AHK It's a pitty you don't use PowerShell because it has a lot to offer ! As mentiioned before it can access all .NET classes and much more. But then again if you don't have a use case for it, it makes sense. Junkew, Yes I still hope someone can break this open how to access the PSOBJECT Members which is derived a .NET BASE Object. AutoIt returns these values from IsObj () COM Object Type: $objPsCollection = $pObjectPS.EndInvoke($objAsync) ConsoleWrite("$objPsCollection: " & IsObj($objPsCollection) & @TAB & "$objPsCollection: " & ObjName($objPsCollection) & " - " & ObjName($objPsCollection,6) & " - " & ObjName($objPsCollection,3) & @CRLF) Quote $objPsCollection: 1 $objPsCollection: Object - {81C5FE01-027C-3E1C-98D5-DA9C9862AA21} - System.Object Contributions :Firewall Log Analyzer for XP - Creating COM objects without a need of DLL's - UPnP support in AU3Crystal Reports Viewer - PDFCreator in AutoIT - Duplicate File FinderSQLite3 Database functionality - USB Monitoring - Reading Excel using SQLRun Au3 as a Windows Service - File Monitor - Embedded Flash PlayerDynamic Functions - Control Panel Applets - Digital Signing Code - Excel Grid In AutoIT - Constants for Special Folders in WindowsRead data from Any Windows Edit Control - SOAP and Web Services in AutoIT - Barcode Printing Using PS - AU3 on LightTD WebserverMS LogParser SQL Engine in AutoIT - ImageMagick Image Processing - Converter @ Dec - Hex - Bin -Email Address Encoder - MSI Editor - SNMP - MIB ProtocolFinancial Functions UDF - Set ACL Permissions - Syntax HighLighter for AU3ADOR.RecordSet approach - Real OCR - HTTP Disk - PDF Reader Personal Worldclock - MS Indexing Engine - Printing ControlsGuiListView - Navigation (break the 4000 Limit barrier) - Registration Free COM DLL Distribution - Update - WinRM SMART Analysis - COM Object Browser - Excel PivotTable Object - VLC Media Player - Windows LogOnOff Gui -Extract Data from Outlook to Word & Excel - Analyze Event ID 4226 - DotNet Compiler Wrapper - Powershell_COM - New
AppleB Posted July 6, 2018 Posted July 6, 2018 In the function DotNet_LoadCScode(), is there a way to reference more than one .dll file? So far I can only reference one and one of my C# programs uses some non-standard libraries and they need their .dlls referenced in order to work. Also, it doesn't recognize multiple System dlls. Is there a way to solve this? Thanks in advance!
Earthshine Posted July 6, 2018 Posted July 6, 2018 (edited) you do it like this, your's will have to reflect the libraries you use, this is an example that goes with the sample code I modified for learning purposes. I will attach the program so you can see what it does (multi threaded directory search) #include "..\..\Includes\DotNet.au3" Opt( "MustDeclareVars", 1 ) Example() Func Example() ; Compiles C# source code on the fly ; Creates a .NET assembly DLL-file in memory ; Loads the memory assembly file into the default domain ; Local $oCode = DotNet_LoadCScode( FileRead( "CodeCS.cs" ), "System.Windows.Forms.dll"); Local $oCode = DotNet_LoadCScode( FileRead( "Program.cs" ), "Microsoft.CSharp.dll | System.dll | System.Core.dll | System.Data.dll | System.Windows.Forms.dll | System.Data.DataSetExtensions.dll | System.Net.Http.dll | System.Xml.dll | System.Xml.Linq.dll" ) ; You must add the "System.Windows.Forms.dll" If @error Then Return ConsoleWrite( "DotNet_LoadCScode ERR" & @CRLF ) ; assembly because of line 1 in the C# code. ConsoleWrite( "DotNet_LoadCScode OK" & @CRLF ) Local $oFoo = DotNet_CreateObject( $oCode, "Foo" ) ; $oFoo is an object of the "Foo" class in the C# code Local $str[2] = ["d:\", "*.rul"] ; ConsoleWrite("Argument 1: " & $str[0] & @CRLF) ; ConsoleWrite("Argument 2: " & $str[1] & @CRLF) If IsObj( $oFoo ) Then $oFoo.Test("d:\", "*.dll") ; Test is a method (function) of the $oFoo object EndFunc if your target does not have those dlls, you will have to provide them. expandcollapse popupusing System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Windows; using System.Diagnostics; class Foo { public void Test(string dir, string filespec) { // if (argv.Length < 2) // { // Console.WriteLine(value: "ERROR: args = null please provide a path and a file specification to search for."); // Console.WriteLine(value: "Example: list c:\\ *.dll"); // } // else // { //DirectoryInfo testdr = new DirectoryInfo(path: argv[0]); //WalkDirectoryTree(testdr, searchname: argv[1]); DirectoryInfo testdr = new DirectoryInfo(path: dir); WalkDirectoryTree(testdr, searchname: filespec); // } } public static void WalkDirectoryTree(DirectoryInfo dr, string searchname) { System.IO.FileInfo[] files = null; DirectoryInfo[] subDirs = null; try { files = dr.GetFiles(searchname); } catch (Exception ex) { Console.WriteLine(ex.Message); } if (files != null) { foreach (FileInfo fi in files) { string dir = fi.DirectoryName; string file = fi.ToString(); if (dir.Length <= 3) { Console.WriteLine(value: dir + file); } else { Console.WriteLine(value: dir + '\\' + file); } } subDirs = dr.GetDirectories(); Parallel.ForEach(subDirs, dir => WalkDirectoryTree(dir, searchname)); } } public override bool Equals(object obj) { return base.Equals(obj); } public override int GetHashCode() { return base.GetHashCode(); } public override string ToString() { return base.ToString(); } } notice that I can't use a string array, in order to pass string arrays, Lars said I need to pass arrays of objects, but this is just a sample that works Edited July 6, 2018 by Earthshine My resources are limited. You must ask the right questions
AppleB Posted July 6, 2018 Posted July 6, 2018 It worked! Thank you so much. I really appreciate the quick response AND the solution. Hope you have a great day!
AppleB Posted July 6, 2018 Posted July 6, 2018 Actually, I spoke too soon. Now I am getting these errors and I do not know what they mean. There are more than are in this picture
Earthshine Posted July 6, 2018 Posted July 6, 2018 (edited) it looks like your cs code does not compile. does it compile in VSCode or whatever you are using? Where you are compiling, are those libraries installed? You can use NuGet in VSCode to get your libraries you need references to. Anyway, start a new thread Edited July 6, 2018 by Earthshine My resources are limited. You must ask the right questions
AppleB Posted July 6, 2018 Posted July 6, 2018 Well it is only a class library, so it doesnt really compile. But this wasnt a problem when I wasn't connecting to a database..
Earthshine Posted July 6, 2018 Posted July 6, 2018 (edited) class libs should still compile dude, can you make your dlls properly in your IDE? look at the bin output dir for all the necessary DLLS your app needs you should make a new thread and post sample code. Edited July 6, 2018 by Earthshine My resources are limited. You must ask the right questions
AppleB Posted July 6, 2018 Posted July 6, 2018 Ok well it compiles to a .dll that i reference in the autoit code. I meant that there was no executable. Im just not sure what it is asking me to do
Earthshine Posted July 6, 2018 Posted July 6, 2018 (edited) well, in your case, would you not rather be using the capability to run your compiled assembly from memory? you are using the LoadCS Code, no? do me a favor, make this a different support thread and give me the vcsproj files, Edited July 6, 2018 by Earthshine AppleB 1 My resources are limited. You must ask the right questions
LarsJ Posted July 6, 2018 Author Posted July 6, 2018 Passing variables and arrays Passing variables and arrays back and forth between AutoIt code and C#/VB.NET is demonstrated in examples in UsingCSandVB.7z as you can find in bottom of first post in this example. There are two set of examples: A set with C# code and a set with VB code. You can find the examples in these folders: Examples\1) Introductory C# and VB examples\ 3) Passing variables\ 1) From AutoIt to C# or VB\ 2) From C# or VB to AutoIt\ 4) Passing 1D arrays\ 1) From AutoIt to C# or VB\ 2) From C# or VB to AutoIt\ 5) Passing 2D arrays\ 1) From AutoIt to C# or VB\ 2) From C# or VB to AutoIt\ Controls, File Explorer, ROT objects, UI Automation, Windows Message MonitorCompiled code: Accessing AutoIt variables, DotNet.au3 UDF, Using C# and VB codeShell menus: The Context menu, The Favorites menu. Shell related: Control Panel, System Image ListsGraphics related: Rubik's Cube, OpenGL without external libraries, Navigating in an image, Non-rectangular selectionsListView controls: Colors and fonts, Multi-line header, Multi-line items, Checkboxes and icons, Incremental searchListView controls: Virtual ListViews, Editing cells, Data display functions
Network_Guy Posted February 18, 2019 Posted February 18, 2019 thanks for the great efforts , but is there any possible way to handle .Net code events via autoit ? i will give example :- here is C# code that contain MyMethod which return Timer object , using System; using System.Timers; public class Au3 { public System.Timers.Timer MyMethod() { System.Console.Write("CS Code is working \n"); System.Timers.Timer timer = new System.Timers.Timer(2000); return timer ; } } here is the autoit code which will start the timer and (what i wish to) handle the Elapsed event. #include<DotNetAll.au3> $oNetCode = DotNet_LoadCScode( FileRead( "CS_Code.cs" ), "System.dll" ) ; above C# code if not IsObj($oNetCode) then msgbox(0,"","CS code not loaded") $ClassObject=DotNet_CreateObject( $oNetCode, "AU3") if not IsObj($ClassObject) then msgbox(0,"","Class Object not Created") $Timer=$ClassObject.MyMethod() ; DotNet timer object if not IsObj($timer) then msgbox(0,"","Timer Object not Created") ObjEvent($Timer,"Test_") ; here is my event method $timer.Enabled=true sleep(4000) func Test_Elapsed($object,$event) ; here is event function msgbox(0,"","Timer Elapsed") endfunc but its not work , any idea ? Earthshine 1
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now