System.IO.FileNotFoundException with DocumentFormat.OpenXml v 2.16.0 - c#

Context of solution: Currently, I have an external application called kdsRibbon which creates and facilitates a ribbon in Revit called "KDS TOOLS". Within this ribbon, there are multiple panels and buttons. I use the .InvokeMember property to link each button with an external command that is in a separate solution. By using InvokeMember, the ribbon looks into a specified file location to find the .dll of the external command and runs the Execute class of the external command. This also allows for rapid iteration of the external commands without restarting Revit each time.
One of the external commands I have linked to my Ribbon is called ExportXLTM (button name is Export/Import Excel), where I want to export specified data into an excel sheet with a .xltm extension. The only issue is, to do this, I need to use the reference DocumentFormat.OpenXml for properties to allow exportation to excel. I install DocumentFormat.OpenXML through Nuget, and I am able to build my solution successfully, but whenever I debug I receive this error:
"System.IO.FileNotFoundException: 'Could not load file or assembly 'DocumentFormat.OpenXml, Version=2.16.0.0, Culture=neutral, PublicKeyToken=8fb06cb64d019a17' or one of its dependencies. The system cannot find the file specified.'"
So, to my understanding the flow is kdsRibbon --> Invoke External Command --> External Command runs --> Relies on DocumentFormat.OpenXml --> Error
I have looked up this error countless times and tried many things. I have changed copy local property to true, I have ensured that DocumentFormat.OpenXML and WindowsBase are both available to the solution, I have tried having both .dll files in Reference Assemblies folder, having them in the same folder location as the kdsRibbon.dll and the ExportXLTM.dll (these are in the same location folder), and I have put both .dll files in the bin of the ExportXLTM solution, and all of these return the same error. I ensured that System.IO is correctly referenced in both my Ribbon and External Command and I still receive the same error.
Is there something I am missing or can anyone help me towards a solution? Does it have to do with the Invoke Member property that causes visual studios to look in the wrong directory location for the .dll files? I have exhausted my possible solutions and I am stuck.
UPDATE: Since I am new I am not allowed to embed images so I have attached links
kdsRibbon with panels and buttons
Error Message in Debug mode within ExportXLTM external command
InvokeMember usage within kdsRibbon External Application, references external command, and also where error occurs within kdsRibbon (highlighted area)

You likely have another addin installed that uses a different version of DocumentFormat.OpenXml.

Related

Click Once Deployment - How to publish an application which has multiple VS projects?

I'm building a complex WPF application. I'm having multiple visual studio solutions. Each solution has a project. Due to code protection reason, I had to place projects in separate solutions.
ComponentMain Solution (WPF Application)
ComponentA Solution (Class Library)
ComponentB Solution (Class Library)
Component A & B referenses assembly of Main Solution. The main solution loads the assemblies of Component A & B using reflection during the runtime.
When I build each solution, an Xcopy post build event will be triggered and all the dll's are copied into a folder called GlobalOutput, where I can run the application by simply running the MainSolution.exe.
Now I want to publish the application using ClickOnce. As I mentioned earlier, there are multiple projects and Dll's are loaded using reflection.
As per to my knowledge I cannot use the click once publish wizard due to above reason. May be i'm wrong.
How can I publish my application using click once.?
As I haveing all the dll's in GlobalOutput directory, Is there any way to create clickkonce deployment directly from there?
You can try to specify which files are published by Click Once.
For you, it will be something like:
Pick one of those solutions/projects as the publishing project to configure Click Once. You need to mark the dlls from the other projects/solutions as prerequisites.
With a project selected in Solution Explorer, on the Project menu, click Properties.
Click the Publish tab.
Click the Application Files button to open the Application Files dialog box.
In the Application Files dialog box, select the application assembly (.dll file) that you wish to mark as a prerequisite. Note that your application must have a reference to the application assembly in order for it to appear in the list.
In the Publish Status field, select Prerequisite from the drop-down list.
To make the file from the other solutions/projects appear in the Application File Dialog box in step 3, you can either reference the output dlls, or add them as solution file and set the build action to content.
For more information: Specify Which Files Are Published by ClickOnce

Raster Data Loading from FilePath in Dotspatial

I have this simple line of code in DotSpatial
var raster = Raster.OpenFile("X://Data//4mr_project.tif");
Why raster just getting null value??
I also have .aux, .ovr, .tfw files in the same directory.
EDITED:
I found that the line below works fine:
var featureSet = FeatureSet.Open("X:\\Test Data\\shap\\edited.shp")
because Dotspatial have capability to load .shp file by default. But loading raster data .tif format, Dotspatial need GDAL extensions. Now the question is how to load GDAL extensions manually in Dotspatial using C#.
GDAL extensions can be supported in your own application through the use of the AppManager component. You can drag and drop this onto your form. This allows for support from the GDAL data extensions, and will also gives support to other plug-ins. Here is a basic walk through for adding the AppManager to a new project that just has a Map on the form.
1) From the Visual Studio Toolbox, right click and click on "Choose Items"
2) From the dialog, choose "Browse" and browse to the DotSpatial.Controls.dll library.
3) Click Ok as needed to close the dialogs and get back to the Toolbox.
4) Find the AppManager component you just added in the Toolbox.
5) Drag the AppManager component onto your form. (not on the map, but on the form). A new instance should appear below your form in the non-visual components list.
6) Select this component to view it's properties in the Properties Dialog.
7) Set the map for the appManager (or other components if you are using them).
8) The GDAL component does not even require the Map to be defined in order to work, it should just work. But you will need the GDAL extension. You can find the DotSpatial.Data.Rasters.GdalExtension in the "Windows Extensions" folder. Ensure that you have a similar folder in your output directory with the necessary GdalExtension. One method is just to ensure that this is in your final distribution folder manually.
9) (Optional) One trick you can use, to ensure you have the GDAL plugin in your release folders is to add the libraries as content. This way, regardless if you are working on a debug version or a release version, it will ensure that the GDAL data extension makes it to the output folders.
10) Ensure that the directory you are using (like "Windows Extensions") is listed in the Directories property of the AppManager. The image below shows the default folders which are "Application Extensions" and "Plugins". I think it originally was "Application Extensions" but got updated to "Windows Extensions" later. Unfortunately, I don't think they updated the default folder.
11) In the code somewhere (probably in the form constructor) you need to call appManager1.LoadExtensions(); If you don't call this, it will not actually load the GDAL extension even if you have the GDAL library as part of your project.
12) Add a SpatialDockManager, SpatialHeaderManager, SpatialStatusStrip to the project. Then assign these to the properties on the AppManager, the same way you did the map. For reasons that are beyond me and were implemented after I left, the previously open ended design structure has changed, and now it will throw message box errors if the program does not include these things but you try to use Extensions. The "ProgressHandler" property takes the SpatialStatusStrip.
After following all 12 of these steps (and running the project in x86 mode) the raster code you posted in the initial question works, and you can open geotifs. I also pushed the GDAL extension into the root "Application Extensions" directory while trying to get it to work, but I don't think you have to do that. It should work if it is in a subfolder.
Sorry to be that late (hopefully, it's never too late), but if you wish to use the plugin without using AppManager, because you may be composing something custom and do not want to depend on the main DotSpatial application framework (note that the AppManager utilizes some slightly advanced "magic" to make it all work together), you can do yourself the following few simple tasks:
1) Add a reference to the file
(DotSpatial Release Folder)\Windows
Extensions\DotSpatial.Data.Rasters.GdalExtension.dll
to your project (this is the main GdalExtension Plugin output file).
NOTE: To make sure this step is done correctly, make sure that building your library (the one that references the GdalExtension.dll) ends up copying to this project's output directory the additional files from the same folder (i.e. gdal_csharp.dll etc.).
2) This same folder also contains a gdal subfolder. Copy the folder itself, as-is, to your output path (usually ...\bin\Release\\ or ...\bin\Debug\\, depending on your configuration). Of course in your final project, you would probably like to use a post-build copy event to automate the process, or just include the folder as content in your application build output, as Ted also mentions in step 9 of his answer.
NOTE: By output folder, I am referring to the Application Output Path, not the library output path. If your application is using a library, which undertakes the task of loading rasters (through GdalExtension), the gdal folder does not need to be in the output folder of this library. It needs to end up in your final application's output folder. The reason is that the various dll files are loaded dynamically, so they have to be found in the executing application folder.
3) As early as possible in your codebase, create a new GdalRasterProvider, which should now be referenced by the dll file added in step 1. This means, add something like the following line to your project
var grp = new DotSpatial.Data.Rasters.GdalExtension.GdalRasterProvider();
Thereafter, the first line of code in your post should work as expected. So, technically, the answer to the original question is that the DefaultDataManager class did not find any suitable provider to perform the task of actually loading the Raster file. Therefore, you are left with a null variable.
Interestingly, you don't need to hold the reference anywhere (i.e. do anything with variable grp). If you check the source code, the constructor itself undertakes the task of adding itself to the DefaultDataProvider.PreferredProviders dictionary, which is eventually invoked behind the scenes in the call to Raster.Open(string) method. The only "tough-to-figure-out" part is simply to copy the gdal folder in your application output path, because the GDAL extension loads a number of references located therein upon instantiation of any provider, and the loading is based on a "gdal" subfolder located in whichever folder your application resides and is executed from.
(Note that the Plugin also contains two more providers (GdalImageProvider and OgrDataProvider). To make these two work, you need to instantiate them but also to manually add them to the PreferredProviders dictionary of the DefaultDataProvider, typically also up early in your application code)

Referencing dll files - my AutoCAD plugin only works on my computer

I have created an AutoCAD plugin, but encounter problems when using the plugin on certain machines. It works fine on my machine.
One thing that I have noticed is that if I change the output path of the build to a different directory I get problems stating that certain namespaces cannot be found.
The following shows the build output folder with the dll files in, the build is successful.
http://imgur.com/5va3ePj
However, if i build to an empty folder (even with dll files referenced) i get the following errors and warnings...
http://imgur.com/eM86l0u
This plugin needs to be able to be used by other users, i think im not referencing dll files properly or something as the program only runs successfully on my computer (and all computers that i have opened the solution in visual studio and built to the export folder). Copying all the files shown in the folder above to the same path on another users computer doesn't work, other users get an error stating 'Could not load fil or assembly "c:/info3d/info3dreloaded.dll" or one of its dependencies. Operation not supported. Exception from HRESULT: 0x80131515)'
Thanks in advance for any help!
Chris
For AutoCAD DLLs set the Copy Local to false. AutoCAD provides those via its runtime.
"Once a AutoCAD .NET API DLL is referenced, you must set the Copy Local property of the referenced DLL to False." from http://knowledge.autodesk.com/search-result/caas/CloudHelp/cloudhelp/2015/ENU/AutoCAD-NET/files/GUID-8657D153-0120-4881-A3C8-E00ED139E0D3-htm.html
Right click on the reference and click on properties and set the "copy local" property to true

How do I get the executable to run on other computers without creating a setup,

I have a program that graphs a text file with some data in it. It works in the debug/release modes of VS 2010 C#. I'm using the .Net and Aforge frameworks. In my references is AForge.Math and the System.Windows.Forms.Charting libraries.
When I run the executable in the ...bin/release folder it works completely, meaning that when I drag and drop my text file into my form a graph appears, as it should. However if I copy that release folder onto another computer the .exe runs but when I drag and drop the text file it doesn't plot. I just get a white blank form.
This is what the program should look like when it's working...
when it's not working it does something like this(so I've attempted to drag and drop a text file into the form) and I get something that looks like this....
I suspect that my problem comes from using the AForge framework. All the computers have the .Net so when the data is input the charting continues to work but the data that is being graphed comes from AForge which is not on the computer. Although I am not entirely sure.
You should copy all the DLLs that you find in your debug or release folder. But sometimes not all the DLLs appear there. If you are using a framework maybe is looking for these DLLs in the installation directory or the GAC.
In this case that AForge is an external dlls so you have two solutions:
Install AForge in all the pcs where you want to copy your program.
CopyLocal True: In the references, in each AForge DLL, get sure that CopyLocal is true. Check this link for help on setting up CopyLocal=true. Then these DLLs will appear in your debug/release directory so when you drag all the references will work. Get sure that you copy all the files inside of debug/release folder, specially .dll, .exe, .config. Once you have it working maybe you can avoid copying .pdb files.
Personally I would try the last one.
Try setting all your references to be copylocal = true, this should put a copy of the dll in the bin\release folder so you can copy them to the other computer.
Open your solution in Visual-Studio and expand the references from the solution-explorer. It should show you a reference list of all DLLs your project is referring to. It must also include your AForge framework if it is used.
Now all you have to do is to ensure that the same set of DLLs are present on the target system:
Either in the exe's own path (This will be applicable for your custom DLLs such as AForge FW)
or
In the GAC (Global Assembly Cache) (Applicable for libraries that are installed such as your System.** framework libraries and MSOffice DLLs).
If something is missing, just copy the additional DLLs to your .exe folder on the target machine.

Loading the application manifest in .NET

I have a ClickOnce application deployed to a virtual machine, Windows 7 32-bit. This application uses some COM components so to get the application working I have created manifests for both the COM assembly and the the application, i.e.
application1.exe and
application1.exe.manifest
comAssembly1.dll and
comAssembly1.x.manifest
Following information from here.
To ensure the application is working, I have run regsvr32 on the COM assembly and all is OK. I then un-registered the assembly and was hoping that all would continue to work. Sadly, it is not the case.
My first port of call was to check my manifests. These match the article referenced above as well as others I have read. So I wanted to check if the manifest was being loaded. I have Process Monitor running and have put a filter on to show only access of files named "application1.exe.manifest", and I don't see any. Having a bit of a google I don't seem to be able to find anywhere that says when then manifest is loaded or by which process.
Have any of you had this problem before? If so, did you discover the cause?
Or is there some magic switch I need in my ClickOnce manifests to tell it to use a manifest file?
And for my own information, when would you expect to see you applications manifest being accessed?
A separate .manifest file will only be used by Windows if the executable doesn't contain an embedded manifest. Problem is that any C# executable already has one. A simple one that's auto-generated by the compiler, it declares the program compatible with UAC.
Project + Add New Item, pick the Application Manifest File item template. It will open in the editor, showing those UAC entries. Move your reg-free COM manifest entries into this one and deploy your app without the .manifest files.

Categories