COM / OLE /ATL - Schnittstelle für Visual Basic ?



  • Hallo,
    ich habe eine DLL in C++ erstellt, die eine C-API wrappt. Nun will ich basierend auf dieser DLL eine weitere DLL oder TLB oder wie auch immer erstellen, die diese Funktionen für Visual Basic zur Verfügung stellt (ja, ich weiß, daß ich mit "DECLARE FUNCTION" in VB DLLs einbinden kann, aber das ist zu umständlich für die VB-User).
    Leider finde ich relativ wenig Doku zu diesem Problem. Mir ist noch nicht einmal klar, welches die beste Technik wäre - ActiveX, OLE, COM oder ATL - und vermutlich gibt es noch mehr Möglichkeiten 😞
    Hat jemand einen Tip, wo ich da Dokus, Howtos oder Samples finde (am besten online...)? Ich finde da nix gescheites.....



  • Gibts im reinen C++ nicht.

    Welchen Compiler verwendest Du denn ?



  • sorry, ich bin neu hier; die Frage hätte vielleicht besser ins MFC-Forum gepaßt?!
    Normalerweise benutze ich MSVC 6.0 Enterprise, aber ich habe auch MSVC 7.0 und BCB. Die DLL (oder was auch immer) soll unter VB 6.0 benutzt werden.
    Ich habe schon Versuche mit ATL und COM gemacht, aber wenn unter VB eine Collection mit "for each x in y" aufgerufen wird, funktioniert das im 1. Durchlauf prima, doch im 2. Durchlauf kommt nur Müll raus, obwohl auf der C++-Seite (jedensfalls soweit ich es debuggt habe) alles ok ist. Dummerweise gibt MSDN bezüglich der VB-Schnittstelle zu COM und ATL fast gar nichts her 😞



  • Mir ist noch nicht einmal klar, welches die beste Technik wäre - ActiveX, OLE, COM oder ATL - und vermutlich gibt es noch mehr Möglichkeiten 😞

    Das zeigt mir, dass Du Dich noch nicht mit diesen ganzen Abkürzungen beschäftigt hast, denn alle basieren auf einem grundlegenden, nämlich COM.
    ATL ist nur eine Klassenbibliothek, die das COM-Handling vereinfacht und schon Grundlagen für die Fenstererstellung zur Verfügung stellt.
    OLE ist die Schnittstelle zum Linken und Einfügen programmfremder Objekte in einen Container und ActiveX basiert auf OLE/COM und stellt eine grafische Benutzeroberfläche zur Verfügung.

    Fazit ist also, dass Du grundlegend COM benutzt und dort automatisierungkompatibel bleiben musst.
    Leider hab ich mit VB so gut wie nichts gemacht, so dass mir im Moment der Bezug von "for each x in y" zu einem COM-Objekt fehlt.



  • Das zeigt mir, dass Du Dich noch nicht mit diesen ganzen Abkürzungen beschäftigt hast,

    ganz genau, deshalb suche ich ja nach Dokus 😉



  • Hi Codewalker

    Also so einfach ist das nicht sämtliche Funktionen einfach in ein COM Objekt zu verpacken und dann mit VB zu verwenden. Die COM Technologie ist alles andere als einfach.
    Wenn du wirklich mit dem COM Coden anfangen willst, dann kann ich dir das Buch GoTo COM von Peter Loos von Addison Wesley empfehlen. Das ist aber wirklich harte Arbeit das durchzuackern. (oder schau einfach mal auf meine Website zu dem COM Tutorial (www.christiankonrad.de))

    Grüße
    Christian



  • hallo xris,
    ich habe mir dein COM-Tutorial angesehen. Prima gemacht, nur leider hört es da auf, wo meine Probleme anfangen...
    Irgendwo muß doch mal dokumentiert sein, wie VBasic auf COM zugreift? Mein spezielles Problem ist halt, daß VB über "for..each..next" auf eine Collection zugreifen soll. Dafür gibt es eine spezielle Schnittstellen-ID ("_NEWENUM"). Das habe ich nach langem suchen im MSDN gefunden. Leider ist sogar der Beispiel-Code dort falsch (for..each funktionert dort nur einmal, weil der Postionszähler nie zurückgesetzt wird). Nachdemm ich diesen Fehler korrigiert habe, kann ich die "for..each"-Schleife zwar mehrfach ausführen, aber die zurückgegebenen Werte sind falsch. Auf der C++-Seite scheint aber alles ok zu sein, jedenfalls soweit ich das in Debugger vefolgen kann. Und an dieser Stelle komme ich nicht weiter, solange ich nicht weiß, wie die Schnittstelle VB<=>COM auszusehen hat...



  • Wenn es sich um ein Enumerationsobjekt handelt, muss es nach der Schleife 'for each' wieder mit Reset zurückgesetzt werden.
    Wie geht denn der VB-Code weiter und wie sieht die C++-Seite aus?



  • mal ein Beispiel in Basic: *uiuiui....* *g*

    Dim RS as new URecordset
    Dim F as UField
    Dim i as integer

    Sub main
    debug.print "LOOP 1"
    i=0
    for each F in RS.UFields
    i=i+1
    F.Value="Test " & i
    debug.print "=> " & F.Value
    next
    debug.print "LOOP 2"
    i=0
    for each F in RS.UFields
    i=i+1
    F.Value="Test " & i
    debug.print "=> " & F.Value
    next
    debug.print "LOOP 2"
    for each F in RS.UFields
    debug.print "=> " & i
    next
    debug.print "ready"
    end sub

    Mal angenommen, mein RS.UFields hat 3 Elemente, dann kommt als Ausgabe:

    LOOP 1
    => Test 1
    => Test 2
    => Test 3
    LOOP 2
    => Test 1
    => Test 2
    => Test 3
    LOOP 3
    => Test3
    =>
    =>
    ready

    Wie ich beim Debuggen feststellen kann, wird die "Reset"-Methode des Enumerationobjects gar nicht aufgerufen. Fragt sich nur, warum nicht? Da liegt wohl auch der Hase im Pfeffer, denn wenn reset aufgerufen würde, dann würde der Beispielcode aus MSDN auch funktionieren...



  • Ein Beispiel, was ich bei XML-Enumerationobjekten gefunden habe:

    Dim xmlDoc As New Msxml2.DOMDocument
    Dim objNodeList As IXMLDOMNodeList
    Dim objNode As IXMLDOMNode
    xmlDoc.async = False
    xmlDoc.Load ("books.xml")
    Set objNodeList = xmlDoc.getElementsByTagName("author")
    For i = 0 To (objNodeList.length - 1)
      Set objNode = objNodeList.nextNode
      MsgBox objNode.Text
    Next
    objNodeList.Reset  // <-- muss natürlich auch in den VB-Code rein
    For i = 0 To (objNodeList.length - 1)
    ...
    


  • hmmmm... folgendes funktioniert aber:

    Sub Main()
    a = Array(1, 2, 3, 4)
    For Each x In a
    Debug.Print x
    Next
    For Each x In a
    Debug.Print x
    Next
    Next
    End Sub

    Auf der C++-Seite ist wohl auch alles ok, wenn ich debugge, wird der korrekte Wert an die Dispatch-Schnittstelle übergeben. Den Reset mache ich ja in C++, wenn letzte Element übergeben wird. Nur im @#/&%$*grummel* Basic kommt es nicht richtig an. Da fehlt halt ne gescheite Doku, wie die .ODL aussehen muß... Vielleicht versuche ich es besser mal in einem Basic-Forum 😉


Anmelden zum Antworten