Question

Je fais référence à une bibliothèque COM dans Visual Studio. Elle a donc automatiquement créé l'assembly Interop correspondant. Je voudrais faire un GetType () sur ces objets com, mais ils renvoient toujours System .__ ComObject . Les interroger pour une interface fonctionne cependant:

bool isOfType = someComeObject is ISomeComObject; //this works

Mais ce que je veux vraiment, c’est que je renvoie le type réel de l’objet com:

Type type = someComeObject.GetType(); //returns System.__ComObject :-(

Est-ce que quelqu'un sait comment faire ce que je veux faire?

Était-ce utile?

La solution

Ajoutez une référence à Microsoft.VisualBasic.dll , puis:

Microsoft.VisualBasic.Information.TypeName(someCOMObject)

Référence MSDN ici .

Autres conseils

La réponse acceptée par Darin nécessite une dépendance à Microsoft.VisualBasic.dll . Si vous ne le souhaitez pas, vous pouvez utiliser cette classe d’aide simple:

public static class TypeInformation
{
    public static string GetTypeName(object comObject)
    {
        var dispatch = comObject as IDispatch;

        if (dispatch == null)
        {
            return null;
        }

        var pTypeInfo = dispatch.GetTypeInfo(0, 1033);

        string pBstrName;
        string pBstrDocString;
        int pdwHelpContext;
        string pBstrHelpFile;
        pTypeInfo.GetDocumentation(
            -1, 
            out pBstrName, 
            out pBstrDocString, 
            out pdwHelpContext, 
            out pBstrHelpFile);

        string str = pBstrName;
        if (str[0] == 95)
        {
            // remove leading '_'
            str = str.Substring(1);
        }

        return str;
    }

    [ComImport]
    [InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
    [Guid("00020400-0000-0000-C000-000000000046")]
    private interface IDispatch
    {
        int GetTypeInfoCount();

        [return: MarshalAs(UnmanagedType.Interface)]
        ITypeInfo GetTypeInfo(
            [In, MarshalAs(UnmanagedType.U4)] int iTInfo,
            [In, MarshalAs(UnmanagedType.U4)] int lcid);

        void GetIDsOfNames(
            [In] ref Guid riid,
            [In, MarshalAs(UnmanagedType.LPArray)] string[] rgszNames,
            [In, MarshalAs(UnmanagedType.U4)] int cNames,
            [In, MarshalAs(UnmanagedType.U4)] int lcid,
            [Out, MarshalAs(UnmanagedType.LPArray)] int[] rgDispId);
    }
}

Vous avez essentiellement compris. GetType () sur un objet COM va vous donner System .__ ComObject, et vous devez essayer de le convertir en quelque chose d'autre pour voir ce qu'est réellement l'objet.

Je suis tombé par hasard sur cette question il y a quelques jours alors que je recherchais le nom de type complet d'un objet System .__ ComObject . J'ai fini par obtenir le nom du type en utilisant la solution de Darin, puis en parcourant toutes les classes de tous les assemblys pour tester la correspondance:

    typeName = Microsoft.VisualBasic.Information.TypeName(someCOMObject);
    foreach (System.Reflection.Assembly assembly in AppDomain.CurrentDomain.GetAssemblies())
    { 
        foreach (Type type in assembly.GetTypes())
        {
            if ((someCOMObject as type)!=null)
                fullTypeName = type.FullName;
        }
    }

Ce n’est pas la solution la plus rapide et la plus élégante, mais elle a fonctionné.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top