Want to protect your cyber security and still get fast solutions? Ask a secure question today.Go Premium

x
?
Solved

HOWTO: Marshal .Net Structure to VB

Posted on 2004-11-19
5
Medium Priority
?
356 Views
Last Modified: 2008-01-16
I am writing a C# class library that exposes a method that return a structure.  I am registering the assembly for COM interop and can reference the assembly in VB (Actually an Acces 2000 Code Module).  I can instantiate the object in VB but when I delcare the variable for the returning structure I get the following error.

         Variable uses and automation type not supported Visual Basic.

Also, if I declare the variable as an Object, the error occurs when I call the method.

Here is my code below...

-----------------------------------------------------------------------------------
C# Class
-----------------------------------------------------------------------------------

[GuidAttribute("B7D043BD-1003-4c6e-9050-0D0C4D93E213")]
      [ClassInterface(ClassInterfaceType.AutoDual)]
      public class VINDecoder
      {
      
            [GuidAttribute("201077FC-39A7-418e-A001-8AB69A3E52E4")]
            [StructLayout(LayoutKind.Sequential)]
            public struct VehicleInformation
            {      
                  [MarshalAs(UnmanagedType.LPWStr)]
                  public string Year;
                  [MarshalAs(UnmanagedType.LPWStr)]
                  public string Make;
                  [MarshalAs(UnmanagedType.LPWStr)]
                  public string Model;
                  [MarshalAs(UnmanagedType.LPWStr)]
                  public string MSRP;
            }

            public VINDecoder()
            {
                  //
                  // TODO: Add constructor logic here
                  //
            }

            public VehicleInformation Decode(string VIN)
            {
                  VehicleInformation vi = new VehicleInformation();
                  vi.Make = "Honda";
                  vi.Model = "Accord";
                  vi.Year = "2005";
                  vi.MSRP = "23000";
                  return vi;
            }

      }
}



---------------------------------------------------------------------------------------------------------
VB Code
---------------------------------------------------------------------------------------------------------

Public Function Test()

    Dim lVINDecoder As VINDecoder.VINDecoder
    Set lVINDecoder = New VINDecoder.VINDecoder
   
    Dim vi As VehicleInformation                                    '<--- Error occurs here
    Set vi = lVINDecoder.Decode("Test")

    Debug.Print vi.Make
End Function

Help code guru's!
0
Comment
Question by:mmurphy1005
  • 3
  • 2
5 Comments
 
LVL 6

Expert Comment

by:Chester_M_Ragel
ID: 12632192
VB Code,

 Public Function Test()

        Dim lVINDecoder As VINDecoder
        lVINDecoder = New VINDecoder

        Dim vi As VINDecoder.VehicleInformation                                    
        vi = lVINDecoder.Decode("Test")

        MessageBox.Show(vi.Make)
  End Function
0
 

Author Comment

by:mmurphy1005
ID: 12632280
This did not work...

First, the Dim line threw up with out the project name.  I got a "Expected User-Defined type, not project" error
The next line required the same thing to specify the object, plus it requires a "Set" statement to instantiate the object first.

Puting the project name in front of VehicleInformation did nothing to help.

Chester: Did this actually work for you?
0
 
LVL 6

Accepted Solution

by:
Chester_M_Ragel earned 900 total points
ID: 12632295
I always used to test the code efore posting. I made some changes to c# class as well. But I didn't post that. Sorry for that. The main point is that, when you refer a struct insite a class use the class name before the struct name.


using System;
using System.Runtime.InteropServices;

namespace VIN
{
      [GuidAttribute("B7D043BD-1003-4c6e-9050-0D0C4D93E213")]
      [ClassInterface(ClassInterfaceType.AutoDual)]
      public class VINDecoder
      {
     
            [GuidAttribute("201077FC-39A7-418e-A001-8AB69A3E52E4")]
                  [StructLayout(LayoutKind.Sequential)]
                  public struct VehicleInformation
            {    
                  [MarshalAs(UnmanagedType.LPWStr)]
                  public string Year;
                  [MarshalAs(UnmanagedType.LPWStr)]
                  public string Make;
                  [MarshalAs(UnmanagedType.LPWStr)]
                  public string Model;
                  [MarshalAs(UnmanagedType.LPWStr)]
                  public string MSRP;
            }

            public VINDecoder()
            {
                  //
                  // TODO: Add constructor logic here
                  //
            }

            public VehicleInformation Decode(string VIN)
            {
                  VehicleInformation vi = new VehicleInformation();
                  vi.Make = "Honda";
                  vi.Model = "Accord";
                  vi.Year = "2005";
                  vi.MSRP = "23000";
                  return vi;
            }

      }
}



--VB

Public Function Test()

        Dim lVINDecoder As VIN.VINDecoder
        lVINDecoder = New VIN.VINDecoder

        Dim vi As VIN.VINDecoder.VehicleInformation                                    '<--- Error occurs here
        vi = lVINDecoder.Decode("Test")

        Debug.Print vi.Make
End Function
0
 

Author Comment

by:mmurphy1005
ID: 12633995
Thanks so much for responding to this question but I still have the error "Variable uses and automation type not supported Visual Basic."

I had tried using the MarshalAs and GuidAttribute on the structure previously, but since it didn't fix the issue, I removed it.

I noticed in your VB code changes you are prefixing the the class and struct with the namespace "VIN".
If I try to include the namespace first, I  get a "User Defined Type not Defined".  In object broswer I can see the project "VINDecoder" and the class "VINDecoder" but no refernces to just "VIN".  I can see the method and structure information of the class too.  When I write the code I can navigate the class layout with intellisense.  With one notable exception, I can see the properties of the structure in object browser, but I can not get them to pop up with intellisense.  This may be a sign as to why I can not refernce the VehicleInformation structure in VB.

I also am still getting an error if I do not use "Set" when I instantiate the VINDecoder class.

I also wanted to make sure you know I am running the VB code in Access 2000 (VBA)  but that shouldn't make a difference I believe.  

I ran the code in VB and recveived the same error.  
Thanks again for all you efforts, can you try your solution on your end in Access or Excel to see if you get the same error?
0
 

Author Comment

by:mmurphy1005
ID: 12661137
Well I posted the question on dotnet.languages.csharp newsgroup.  Nicholas Paldino, a .Net/C# MVP came up with the solution.

He said to change the MarshalAs attribute to UnManagedType.Bstr.  By doing this the error was resolved and I can now use intellisnse to access the vi structure attributes.

Thanks Nicholas

You the Man!

Chsester, I am awarding you the points since Nicholas is not in ee.  I sure appreciate your comments as I did incorporate some of your suggestions.

Mike Murphy
0

Featured Post

Become an Android App Developer

Ready to kick start your career in 2018? Learn how to build an Android app in January’s Course of the Month and open the door to new opportunities.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Introduction This article series is supposed to shed some light on the use of IDisposable and objects that inherit from it. In essence, a more apt title for this article would be: using (IDisposable) {}. I’m just not sure how many people would ge…
Entity Framework is a powerful tool to help you interact with the DataBase but still doesn't help much when we have a Stored Procedure that returns more than one resultset. The solution takes some of out-of-the-box thinking; read on!
this video summaries big data hadoop online training demo (http://onlineitguru.com/big-data-hadoop-online-training-placement.html) , and covers basics in big data hadoop .
The Relationships Diagram is a good way to get an overall view of what a database is keeping track of. It is also where relationships are defined. A relationship specifies how two tables connect to each other. As you build tables in Microsoft Ac…

564 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question