DPrometheus Posted March 30, 2009 Posted March 30, 2009 Hello there, The problem is the following: How can I pass a Word.Document object from vba code to vb.net? I have made a small program which wraps Word 2007 into a usercontrol (custom panel) but now I want to interact with the document I ran into some problems.. For some other customizations (extra buttons on the new Ribbon) I cannot call the function with correct parameters it seems. I cannot pass the Word.Document object from vba to vb.net for some reason I don't know. Can someone shine a light for me here? vb.net Public Class EcfToolForm Private _document As Word.Document Public Sub New() ' This call is required by the Windows Form Designer. InitializeComponent() ' Add any initialization after the InitializeComponent() call. End Sub ' This one doesn't work since vba can't use parameterized constructors Public Sub New(ByRef doc As Word.Document) InitializeComponent() _document = doc End Sub ' Extra function to replace above constructor. This now must be called after the constructor has been called. Public Sub LoadDoc(ByRef doc As Word.Document) _document = doc End Sub ... VBA Sub SpecialistButton_Click(control As IRibbonControl) On Error Resume Next Set toolbar = New Specialist07.EcfToolForm toolbar.LoadDoc (Word.ActiveDocument) toolbar.Show Err.Clear End Sub The library seems linked correctly (The form is shown (a toolbar, as you might have guessed ;) ) when the button is pressed, but as soon as the toolbar buttons are clicked it says object reference not set on the Word.Document object). Can someone explain me what I'm doing wrong? Kind regards, ~DP Quote My Development System Intel Core i7 920 @2.66Ghz 6 GB DDR3 SDRAM Windows 7 Ultimate x64 & Windows Vista Home Premium x64 dual boot GeForce GTX295 1.8 GB 3.5 TB HD
Mike_R Posted March 31, 2009 Posted March 31, 2009 I'm not a Word programmer, but your code looks ok to me. I think you'll have to trace this with debugging tools. Trace the actual assignment of '_document = doc' to make sure this is getting set right. (It must, but, well, trace it anyway...) Then put have a breakpoint within the method that gets called when you click a toolbar button. Then trace/step into that code as well to see what is going on. - Mike Quote Posting Guidelines Avatar by Lebb
DPrometheus Posted March 31, 2009 Author Posted March 31, 2009 thanks for helping me out, however.. this is my conclusion of debugging this project: on the VBA side on the line of toolbar.LoadDoc (Word.ActiveDocument) Word.ActiveDocument equals the actual document I can't see the full object but he recognizes it (it has the right name property, and at least it ain't Nothing (since VBE doesn't have such neat debugging tools as VS08) But on the other side things get a bit harder. Since I have to sign it each time and put the dll in the GAC I can't actually use breakpoints here (or don't know how, just a normal breakpoint won't do at least). But after some logging I can determine that the document is NOT passed through and doc in the LoadDoc function resides empty aka Nothing Public Sub LoadDoc(ByRef doc As Word.Document) _document = doc End Sub I already tried changing byref (maybe vba only supports byval) but without succes. Someone idea's? ~DP Quote My Development System Intel Core i7 920 @2.66Ghz 6 GB DDR3 SDRAM Windows 7 Ultimate x64 & Windows Vista Home Premium x64 dual boot GeForce GTX295 1.8 GB 3.5 TB HD
Mike_R Posted March 31, 2009 Posted March 31, 2009 True, you don't need 'ByRef' here, since you aren't changing the instance, so, yes, 'ByVal' makes more sense. But this isn't your problem (as you said). I have no clue, I'm afraid... Are you saying that the 'doc As Word.Document' parameter is coming through as 'Nothing' even though the argument passed in is non-null?? Can you show your code, including your logging calls for your LoadDoc method? Quote Posting Guidelines Avatar by Lebb
DPrometheus Posted April 6, 2009 Author Posted April 6, 2009 Sorry for the late response, but I haven't been at work for a few days due to sickness. Eventually I changed the form to contain several buttons on the outside of the panel which now interacts to the word document. This seems to solve this issue and since we already needed multiple 'outside buttons' we can hold these as well.. It would have been prettier if they nicely integrated into eachother but hey, it works now :) And it ain't that bad after all ;) Thanks for your time and suggestions! ~DP Quote My Development System Intel Core i7 920 @2.66Ghz 6 GB DDR3 SDRAM Windows 7 Ultimate x64 & Windows Vista Home Premium x64 dual boot GeForce GTX295 1.8 GB 3.5 TB HD
Cindy Meister Posted April 15, 2009 Posted April 15, 2009 Hi DPrometheus I know you've told Mike you've found a way to work around the problem, however, I thought you'd be interested in knowing how to pass a Word document object (or, indeed, any office object) from VBA to your .NET code. You have to declare the parameter in the .NET code as type object. Then you explicitly cast it (in VB.NET use CType()). For example: public void passWordDoc(object doc) { Microsoft.Office.Interop.Word.Document WordDoc = doc as Microsoft.Office.Interop.Word.Document; WordDoc.ActiveWindow.Caption = "Tested!"; } Since this is VB.NET, if you use Option Strict Off, you could also just continue with it being an object and use late-binding. Of course, then you wouldn't have any Intellisense. Quote
DPrometheus Posted April 15, 2009 Author Posted April 15, 2009 Hi Cindy, thanks for your response, since we're close to the deadline right now I will keep it in mind for a v2. ;) Though through curiosity I made a small test and it really works like a charm. :) Thank you ~DP Quote My Development System Intel Core i7 920 @2.66Ghz 6 GB DDR3 SDRAM Windows 7 Ultimate x64 & Windows Vista Home Premium x64 dual boot GeForce GTX295 1.8 GB 3.5 TB HD
Recommended Posts