Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Sonstige Fragen zu Delphi (https://www.delphipraxis.net/19-sonstige-fragen-zu-delphi/)
-   -   Delphi Zugriff auf MS Excel (https://www.delphipraxis.net/123829-zugriff-auf-ms-excel.html)

ThoPos 9. Nov 2008 21:01


Zugriff auf MS Excel
 
Hallo Zusammen,

ich stehe vor folgendem Problem:

Ich starte von Excel heraus mein Delphi-Programm und übergebe als Parameter den Namen der Excel-Arbeitsmappe und der Excel-Tabelle.
In meinem Programm greife ich dann mit GetActiveOLEObject('Excel.Application') auf Excel zu und lese die Tabelle aus. Dies funktioniert gut - solange nur eine Instanz von Excel läuft.

Aber wie kann mit ich die korrekte Instanz von Excel identifizieren und als Object einbinden?

Gruß aus Köln
Thomas

DeddyH 9. Nov 2008 21:05

Re: Zugriff auf MS Excel
 
Wie startest Du Excel denn? Per ShellExecute? Das gibt Dir doch IIRC das Instanzen-Handle zurück (oder eben einen Fehlercode).

mkinzler 9. Nov 2008 21:30

Re: Zugriff auf MS Excel
 
Du könntest die Datei auch per COM/OLe laden lassen

ThoPos 10. Nov 2008 03:45

Re: Zugriff auf MS Excel
 
Hallo Zusammen,

leider verstehe ich Eure Antworten nicht. :?:

Wie geschrieben läuft Excel schon und die Arbeitsmappe ist auch schon geladen. Ich starte von Excel heraus mit 'Shell "MeinProg.exe" "Mappe.xls" "Tabelle1", vbnormal' mein Delphi-Programm.

@DeddyH
Welche Rolle spielt es also, wie Excel vom Desktop oder Startmenü aus gestartet wurde?

@mkinzler
Wie soll ich die bereits geöffnete Datei mit COM/Ole laden?

Gruß aus Köln
Thomas

Chemiker 10. Nov 2008 07:02

Re: Zugriff auf MS Excel
 
Hallo ThoPos,

am besten wird es sein, wenn Du Dir eine neue Excel-Instanz erstellst.

Mit:

Delphi-Quellcode:
Excel:= CreateOleObject('Excel.Application’);
Und anschließend Deine XLS-Datei in Excel öffnen.


Bis bald Chemiker

teebee 10. Nov 2008 08:18

Re: Zugriff auf MS Excel
 
Es gibt bei MS einen Artikel, der anscheinend beschreibt, was Du brauchst:
Zitat:

Another way to get the IDispatch is by using the GetActiveObject() API to get the server's IDispatch from the ROT. However, this method requires that you must be able to obtain the CLSID or ProgID of the server. Furthermore, ambiguous situations can occur where you can't distinguish between multiple instances of the server.

This article uses another approach to obtain the IDispatch, which works for both Microsoft Excel and Microsoft Word, even when multiple instances are running.

ThoPos 3. Feb 2009 13:18

Re: Zugriff auf MS Excel
 
Hallo teebee,

das scheint das zu sein, was ich brauche. Auch wenn ich auf Grund anderer Probleme erst jetzt wieder dazu komme, mich diesem Problem anzunehmen.

Nur: kann mir das bitte jemand nach Delphi 2007 übersetzen?

Danke im Voraus!
Thomas

Chemiker 3. Feb 2009 13:43

Re: Zugriff auf MS Excel
 
Hallo ThoPos,

Zitat:

Zitat von ThoPos
Wie geschrieben läuft Excel schon und die Arbeitsmappe ist auch schon geladen. Ich starte von Excel heraus mit 'Shell "MeinProg.exe" "Mappe.xls" "Tabelle1", vbnormal' mein Delphi-Programm.

Warum startest Du Excel nicht mit Deinem Programm? Irgendwie werde ich da nicht schlau raus.

Du hast Excel mit einer Tabelle, dann startest Du Dein Programm aus Excel und willst dann wieder Bezug auf die Tabelle nehmen die in Excel steht aus dem Du Dein Programm startest.

Ist es nicht viel einfacher von Deinem Programm Excel zu starten?


Bis bald Chemiker

Sherlock 3. Feb 2009 13:56

Re: Zugriff auf MS Excel
 
Zitat:

Zitat von Chemiker
Du hast Excel mit einer Tabelle, dann startest Du Dein Programm aus Excel und willst dann wieder Bezug auf die Tabelle nehmen die in Excel steht aus dem Du Dein Programm startest.

Ist es nicht viel einfacher von Deinem Programm Excel zu starten?

Der geschilderte Zusammenhang legt eigentlich nahe ein Excel-Addin zu schreiben.
http://www.delphipraxis.net/internal...ht=excel+addin

Sherlock

ThoPos 3. Feb 2009 20:28

Re: Zugriff auf MS Excel
 
Hallo Zusammen,

ich versuche mal mein Problem näher zu beschreiben.

Von einem analytischen Meßgerät werden physikalische und chemische Daten gemessen. Die gemessenen Daten werden anschließend vom Analysengerät automatisch, zur weiteren Verrechnung, nach Excel geschrieben. Anschließend werden diese Daten vom Anwender mittels eines von mir erstellten AddIns aufbereitet und die endgültige Ergebnisse ermittelt.

Diese Ergebnisse sollen danach zum einen in eine Oracle-Datenbank geschrieben und zum anderen an den Auftraggeber übermittelt werden. Aus dem AddIn heraus sind diese beiden Schritte nicht praktikabel, weil
- die Datenbankanbindung mit ODAC einfacher, besser und schneller ist als ODBC bzw. ADO.
- mit Delphi FTP, SMTP und ähnliches unkomplizierter ist.

Aus diesem Grund starte ich, nach dem das Excel-AddIn mit seinen Aufgaben fertig ist, mein Delphi-Programm, welches die Tabelle ausliest und die Daten in eine Oracle-Datenbank schreibt. Anschließend erfolgt die Übermittelung der Daten an den Auftraggeber nach Kundenwunsch (FTP, Mail, Fax, Andruck, etc.).

Das ganze funktioniert einwandfrei - solange nur eine Instanz von Excel läuft. Wenn aber das Analysengerät eine neue Excel-Datei anlegt, während mein AddIn gerade eine Auswertung durchführt, so sind beim anchließend Start des Delphi-Programmes zwei Instanzen von Excel geöffnet. Und schon liefert das GetOLEObject, genauer gesagt der anschließende Zugriff auf die Arbeitsmappe, in fast allen Fällen eine Exception.

Ich hoffe, daß jetzt mein Problem verständlicher ist.

Gruß
Thomas

ThoPos 4. Feb 2009 05:54

Re: Zugriff auf MS Excel
 
Hallo Sherlock,

ich habe versucht mir das AddIn anzusehen.

Leider findet mein Delphi 2007 die TExcel...-Komponenten nicht. Und meine Versuche diese als Typenbibliotheken zu importieren scheiterten kläglich, da immer irgendwelche Sachen fehlen.

Gruß aus Köln
Thomas

nahpets 4. Feb 2009 09:25

Re: Zugriff auf MS Excel
 
Hallo,

bei Delphi 6 und 7 liegen sie unter delphi\ocx\Servers\. Eventuell wirst Du ja dort fündig.
Ansonsten suche mal im Delphiverzeichnis nach Excel*.pas.

Eventuell findest Du im BIN-Verzeichnis auch ein(ige) dclOffice*.bpl, dann musst Du nur dieses Package installieren.

p80286 4. Feb 2009 10:20

Re: Zugriff auf MS Excel
 
Hallo ThoPos,

zunächst einmal verstehe ich nicht was Du gegen ODBC hast, abgesehen von der lausigen Umsetzung in Excel (so wie ich es kenne!)
aber wie wäre es mit einem anderen Ansatz:
Dein Addinn schreibt die verarbeiteten Daten in eine Datei, die dann von Deinem Delphi-Programm weiter verarbeitet wird.
Je nachdem welches Format (CSV) Du in der Datei verwendest kommst Du ohne einen erneuten Aufruf von Excel aus.

Gruß K-H

ThoPos 4. Feb 2009 11:04

Re: Zugriff auf MS Excel
 
Hallo K-H,

meine Abneigung gegen ODBC ruht weniger auf die Technik als solche, sondern mehr auf
- die Umsetzung in VBA.
- das was unserere Netzwerk-Admins immer mit der Oracle-Konfiguration treiben.
Wenn ich ODAC verwende, ist mir absolut egal, was die lieben Admins machen - die DB-Anbindung steht!

Gegen Deinen Vorschlag des Datenaustausch per Datei steht - und das hatte vergessen zu schreiben - das ich auch Daten aus Oracle abhole und in die Tabelle schreibe, damit diese Informationen auch auf den Andrucken stehen. (QS und QM lassen grüßen.)

Und von der aktuellen Umsetzung sind alle Labormitarbeiter hellauf begeistert. Denn die Zusammenarbeit des Auftragssystemes (Oracle) und der Meßgeräte (Auswertung via Excel) funktioniert super.

Wäre da nicht das Problem, daß Excel ggf. mehrfach läuft.

Gruß aus Köln
Thomas

p80286 4. Feb 2009 11:20

Re: Zugriff auf MS Excel
 
Hallo ThoPos,

auf die Gefahr hin Dich vollkommen mißverstanden zu haben:
1) Daten werden durch Messungen erstellt
2) Daten werden durch Excel aufbereitet/verarbeitet
3) Daten werden in Datenbank geschrieben

Irgendwo dazwischen werden auch Daten aus einer DB abgeholt um wichtige Zusatzinformationen zu erhalten.
Jetzt einmal abgesehen vom Zeitpunkt wann Du was erledigen läßt, Du arbeitest grundsätzlich mit Excel und möchtest, daß ein Delphi-Programm eine Zusatzaufgabe erledigt, die am Ende der Verarbeitungsreihenfolge liegt.
Wenn Du über die von mir vorgeschlagene Datei gehst, dann kann Delphi seine "eigene" Excel Instanz eröffnen und es ist egal was sonst noch auf dem Rechner läuft. (vgl #5 von Chemiker)

Was allerdings nur dann sinnvoll ist, wenn die "Delphi-Verarbeitung" wirklich am Ende ist.

Gruß K-H

P.S.
Die normalen Mitarbeiter müssen ja nicht mitbekommen wer da wo arbeitet.

ThoPos 4. Feb 2009 21:51

Re: Zugriff auf MS Excel
 
Hallo K-H,

so vollkommen ist das Mißverständnis nicht.

Ich sortiere mal die Schritte:

A: Das Meßgerät: Messen einer Probenserie.
1. Das Meßgerät mißt kontinuierlich die Proben verschiedener Probenserien.
2. Am Ende jeder Messung schreibt die Steuersoftware des Meßgerät die Daten nach Excel. Bei diesem Schreibvorgang verwendet der Hersteller folgende Logik: Läuft eine Excel-Instanz ohne geöffnete Mappe, so wird die diese verwendet, ansonsten eine neue Instanz von Excel geöffnet. Excel-Instanzen mit geöffneten Mappen werden ignoriert. In der leeren oder neuen Excel-Instanz wird nun die Arbeitsmappe geöffnet - je Probenserie gibt es eine Mappe, bei der ersten Probe der Serie wird eine neue Mappe auf Basis einer Vorlage erstellt. In diesen Mappen werden für jede Probe der Serie eine Datenzeile geschrieben.
3. Die Mappe wird nach der Datenübertragung gespeichert und geschlossen.
4. Die Excel bleibt ohne geladene Mappe geöffnet.

B: Der Anwender in Excel: Nach dem alle Proben einer Serie gemessen wurden.
1. Öffnen der Arbeitsmappe in Excel.
2. Aufbereiten der Daten über diverse VBA-AddIns bzw. manuelle Berechnungen.

C: Mein Delphi-Programm (automatisch): Abgleich der Excel-Daten mit der DB.
1. Abholen von Auftraggeberdaten (z.B. Name, Adresse, Probenbezeichnung) aus der DB.
2. Abholen des Auftragumfanges aus der Oracle-DB, da das Meßgerät i.d.R. mehr Daten liefert, als der Auftraggeber verlangt.
3. Abholen der Daten aus Excel.
4. Markieren der gewünschten Daten in Excel und ggf. herausrechnen der nicht beauftragten Daten. (Ergebnisse nach Excel schreiben)
5. Ggf. verrechnen mit von anderen Meßgeräten in die DB geschriebenen Werten. (Ergebnisse nach Excel schreiben)
6. Gegenüberstellen der ermittelten Daten mit den gemäß DB verlangten Parametern für den Anwender.

D: Der Anwender in meinen Delphi-Programm: Logische Überprüfungen
1. Die automatischen Zuordnungen der Daten prüfen und ggf. korrigieren.
2. Evtl. Dimensionsumrechungen (z.B. g/L -> mg/L) durchführen lassen.
3. Prüfen, ob evtl. Grenzwertverletzungen real sind.
4. Freigabe der Ergebnisse

E: Mein Delphi-Programm (automatisch):
1. Die Daten werden in die DB geschrieben und auf dem in der DB hinterlegten Weg an den Auftraggeber übermittelt.
2. Die DB liefert für jede übermittelte Messung diverse Quittierungsdaten. Diese werden in die Excel-Mappe geschrieben.
3. Beenden meines Programmes.

F: Der Anwender: QS-Dokumentation.
1. Formatieren der Tabelle für den Andruck
2. Andruck der Excel-Tabellen mit allen Meß- und DB-Daten.
3. Unterschreiben und archiveren der Andrucke.


Bisher wir mein Programm über einen erstellten Menübefehl in Excel gestartet.

Bei der Überprüfung der Daten im Schritt D1 kann es vorkommen, das der Anwender mein Programm verläßt und ab Punkt B2 - mit den von der DB importierten Daten !!! - neu beginnt.

Gruß aus Köln
Thomas

Chemiker 4. Feb 2009 22:42

Re: Zugriff auf MS Excel
 
Hallo ThoPos,

Ich gehe jetzt mal davon aus das Du keine Chance hast die Messwerte die in Excel geschrieben werden in Delphi direkt umzuleiten. Aber nach Punkt A: 3. wird das Workbook geschlossen und abgespeichert.

Ab B: würde ich mit Delphi die Kontrolle übernehmen und mit OLE-Automation weiterarbeiten.
Damit wird erreicht:
1. Das Dein Programm die Kontrolle behält.
2. Weiter Messungen ohne Beeinflussung der Vorgänger Messung durchgeführt werden kann, weil so wie ich es jetzt verstanden habe die Steuersoftware ja autonom handelt.

Für mich stellt sich eigentlich das größte Problem mit der Umsetzung der diversen VBA-AddIns in Delphi. Wenn Du sie selbst geschrieben hast und die Logik kennst, sollte es nicht zu schwer sein.

Meine persönliche Meinung von QS und Excel ist, dass sich das gegenseitig ausschließt. Ich weis nicht wie man eine vernünftige Validierung mit Excel hinkriegen soll, aber das ist wie gesagt meine persönliche Meinung(gestützt durch entsprechende Ehrfahrung).

Bis bald Chemiker

globetrotter77 4. Feb 2009 23:17

Re: Zugriff auf MS Excel
 
Da kann ich dem Chemiker nur beipflichten!
Das Analyseprogramm Prog1 hat Daten über irgendeinen Input In1 (Messgeräte, Messfühler etc.) ermittelt und sie in eine Excel-Mappe übertragen, welche nun gespeichert und geschlossen ist. Das Format dürfte immer das gleiche sein, also ist eine automatisierte Weiterverarbeitung möglich.
Ok, wir haben also einen Output Out1 des Analyseprogramms, wie auch immer.
Der Name der Excel-Datei dürfte bekannt sein, und wenn das Analyseprogramm eine neue Datei erstellt, wird die auch einen neuen Namen bekommen, oder? (Ansonsten müsste man sie mit eindeutig gekennzeichnetem Namen einfach kopieren)
Der nächste Schritt ist, dass eben dieser Output Out1 zum Input In2 für das nächste Programm Prog2 wird, das wiederum einen neuen Output Out2 erzeugt. Aus QS-technischen Gründen empfiehlt es sich hier tatsächlich, eine neue Datei anzulegen, so dass die alte erhalten bleibt.
Das "nächste Programm" Prog2 ist jetzt ganz einfach dein Delphi-Programm, das dann auch alle anschließenden Arbeiten erledigen kann, und zwar am besten ohne Einflussnahme irgendwelcher Anwender.
Ich betone, alle Arbeiten!
Dazu gehören auch Schritte wie F1 und F2, also Formatieren und Ausdruck.
Wenn dann tatsächlich noch manuelle Eingriffe nötig sein sollten, muss man sich erst mal überlegen, wieso das so ist und ob es nicht möglich ist, in immer wieder gleicher Form darauf zu reagieren, sprich: zu programmieren.
Korrekturen während der eigentlich als automatisch konzipierten Bearbeitung sind mehr als kontraproduktiv, sondern dürften bestenfalls in einem weiteren Schritt in gut dokumentierter Form erfolgen.

So würde ich es machen, einfach Schritt für Schritt.
Auf keinen Fall so, dass sich die Programme gegenseitig aufrufen, da sind die Schwierigkeiten wirklich vorprogrammiert.

Weiß nicht, ob dir das weiterhilft, aber frag einfach nochmal nach, falls es nicht so sein sollte.

ThoPos 5. Feb 2009 05:44

Re: Zugriff auf MS Excel
 
Hallo Chemiker, hallo Globetrotter77,

im Grunde kann ich Euch nur beipflichten:

1. Excel und QS -> ein Widerspruch in sich ...
2. Alles sollte aus Delphi heraus gesteuert werden ...

Aber leider scheint dies nicht zu gehen bzw. der Aufwand wäre zu groß. Und schließlich muß das arme Labor meinen Aufwand bezahlen.

Der Gerätehersteller verfolgt leider die Philosophie, daß alles in Excel gemacht werden soll. Die Steuersoftware macht wirklich nichts anderes als Steuern und dee nackten Meßwerte zu liefern. Dabei kennt die Software zwei Exportformate: eine Textdatei für alle Proben oder je eine Excel-Datei pro Projekt (Probenserie). In der Textdatei steht leider nur die Probennummer, aber nicht das Projekt und die Struktur der Textdatei ist auch eigenartig: eine Zeile pro Probe, einzelne Meßwertblöcke (Bezeichnung, Wert, Einheit) mit Semikolon getrennt, die Daten eines Messwertblockes mit Komma getrennt, manche Ergebnisse in Hochkommas, andere widerrum nicht. Somit ist ein Einlesen der Textdatei sehr mystisch. Alle Excel-Dateien werden in einem fest eingestellten Verzeichnis abgelegt und der Dateiname ist der Name des Projektes, ggf. um nicht für Dateinamen verwendbare Zeichen bereinigt.

Sämtliche Berechnungen werden über die zahlreichen AddIns, ebenfalls vom Gerätehersteller, durchgeführt: z.B. Kalibrierung (liniar, quatratisch oder exponentiell), Umrechnen des Meßwertes in eine Gehaltsangabe (Massenanteil, Massenkonzentration, etc.), korrigieren der Daten um andere Angaben, die den Meßwert beeinflussen, etc.

Die AddIns sind alle geschützt. Somit kann ich nicht nachsehen, wie die AddIns arbeiten. Und das Lösen einer exponentiellen Gleichung aus 8 Wertepaaren (Meßwert - Gehalt) in Delphi möchte ich mir wirklich nicht antun. Es gibt tatsächlich ein Element, das exponentiell ausgewertet wird.

Somit finde ich, die einfachste Lösung ist, den Anwender alles in Excel machen zu lassen und nur bei den Schritten (Daten aus DB holen, Daten in DB schreiben, Ergebnisse übermitteln) zu unterstützen. Das funktioniert bisher super und auch fehlerfrei. Sogar ein Kundenaudit wurde erfolgreich bestanden. Wäre da nicht das Problem, daß die Gerätesoftware im Hintergrund arbeitet und immer wieder eine weitere Excel-Instanz öffnet.

Gruß aus Köln
Thomas

globetrotter77 5. Feb 2009 12:02

Re: Zugriff auf MS Excel
 
Zitat:

Die AddIns sind alle geschützt.
Das ist natürlich keine gute Voraussetzung, war aber zu erwarten.
In diesem Fall würde ich, auch wenn sich mir die Nackenhaare sträuben, entweder
a) Delphi außen vor lassen und alles in Excel erledigen. Man kann auch aus Excel heraus Daten aus der DB abfragen und wieder zurückschreiben.
oder
b) Delphi die Daten ermitteln lassen und die Kommunikation über eine/mehrere Zusatzdateien steuern, aber auf keinen Fall aus Delphi wieder Excel aufrufen ... das ist vergleichbar damit, sich am eigenen Schopf aus dem Sumpf zu ziehen.

ThoPos 5. Feb 2009 18:58

Re: Zugriff auf MS Excel
 
Zitat:

Zitat von globetrotter77
b) ..., aber auf keinen Fall aus Delphi wieder Excel aufrufen ... das ist vergleichbar damit, sich am eigenen Schopf aus dem Sumpf zu ziehen.

Hallo Globetrotter,

das verstehe ich nicht. Wenn ich aus Excel heraus mein Programm starte und per GetOLEObjekt die Steuerung von Excel übernehme und anschließend Excel wieder freigebe, so ist doch alles in Ordnung? Ich kann doch auch, wenn ich mit dem Auto unterwegs bin, einen ortskundigen Passanten für mich durch die Stadt fahren lassen, und anschließend wieder selber weiterfahren; nur das anschließend der Passant an einem anderen Ort ist. So wie meine Excel-Mappe geändert ist.

Gruß
Thomas

Chemiker 5. Feb 2009 19:16

Re: Zugriff auf MS Excel
 
Hallo ThoPos,

Zitat:

Zitat von ThoPos
Ich kann doch auch, wenn ich mit dem Auto unterwegs bin, einen ortskundigen Passanten für mich durch die Stadt fahren lassen, und anschließend wieder selber weiterfahren; nur das anschließend der Passant an einem anderen Ort ist. So wie meine Excel-Mappe geändert ist.

Klar geht alles, aber was machst Du, wenn der Passant einfach nach Hause fährt. Excel wird geschlossen.


Bis bald Chemiker

ThoPos 6. Feb 2009 03:54

Re: Zugriff auf MS Excel
 
Na ja ...

solche und ähnliche Risiken bleiben immer.

Beim dem von euch immer wieder angesprochenen Datenaustausch per Datei kann es auch vorkommen, daß das eine Programm noch am schreiben ist, während das andere schon mit dem einlesen beginnt. Hier muß man sich - wie ich leider aus meiner Praxis schon erfahren mußte - einen Mechanismus ausdenken, der sicherstellt, daß die Datei auch wirklich zuende geschrieben wurde, bevor das zweite Programm anfängt zu lesen. Und Windows täuscht, insbesondere beim Speichern auf Netzwerklaufwerken, ein "fertig gespeichert" vor, obwohl ein Teil der Datei noch im Schreibpuffer von Windows ruht.

Genauso muß ich mir bei OLE eine entsprechende Sicherheit programmieren.

Aber zurück zu meiner ursprünglichen Frage: Kann mir einer das Beispiel von MS in C ein Beispiel in Delphi übersetzen oder einen anderen Weg nennen, wie ich an die richtige Instanz von Excel komme?

Gruß aus Köln
Thomas

Yheeky 6. Feb 2009 09:40

Re: Zugriff auf MS Excel
 
Weiss jetzt nicht, ob ich dein Problem genau verstanden habe:
Du liest Daten mit deiner Steuersoftware ein (d.h. die Daten sind in deinem Programm). Dann willst du diese Daten in eine Exceldatei packen, welche danach noch mit Formeln angepasst werden müssen. Und die Ergebnisse kommen dann in eine Datenbank...?

Richtig so?
Also ich kann dir nur raten: WENN du einen Export nach Excel umsetzen willst, dann beschäftige dich mit dem Format an sich. Ich würde mich nicht auf irgendwelche Schnittstellen verlassen, das ist immer unsicher. Gehe mal von einem Windows-/Office Update aus, was irgendwas an der Schnittstelle ändert und schon funktioniert dein Programm nicht mehr.

Hoffe ich hab dich richtig verstanden.

ThoPos 6. Feb 2009 10:31

Re: Zugriff auf MS Excel
 
Hallo Christian,

du hast mich leider nicht richtig verstanden. Die Steuersoftware ist vom Gerätehersteller und exportiert von sich aus per OLE nach Excel. Daran läßt sich nichts ändern. Die anschließenden Berechnungen in Excel erfolgen entweder mit AddIns des Gerätehersteller oder manuell. Ich will nur weitere Daten aus einer Oracle-DB abholen und in die Tabelle schreiben bzw. die endgültigen Daten aus Excel nach Oracle schreiben und ggf. Daten an den Auftraggeber senden.

Gruß
Thomas

p80286 6. Feb 2009 13:43

Re: Zugriff auf MS Excel
 
Hallo Thopos,

ein paar Tage keine Zeit gehabt und schon ist der Teufel los.
Bei Deiner Beschreibung des Text-Datenformates fiel mir ASCII-Delimited, auf Microsoftisch CSV ein.
Und das ist von Excel recht einfach zu bearbeiten (lesen).

Allerdings sehe ich keinen Grund von meinem Vorschlag abzurücken.
1) alle Addins werden in den Schritten a und b genutzt. -> kein Bedarf etwas über sie zu wissen.
2) Das Delphiprogramm bekommt die von 1) erstellten Daten (in welchem Format auch immer), die Schritte c,d,e ausführt.
3) der Qualitätsteil läuft ab.
Zitat:

F: Der Anwender: QS-Dokumentation.
1. Formatieren der Tabelle für den Andruck
2. Andruck der Excel-Tabellen mit allen Meß- und DB-Daten.
3. Unterschreiben und archiveren der Andrucke.
1. Formatieren der Tabelle für den Andruck Was auch immer das heißt(allein damit kann man für ein Leben Aufträge generieren)
2. Andruck der Excel-Tabellen mit allen Meß- und DB-Daten. Also irgendwo gibt es eine (Excel-)Datei mit allen Daten
3. Unterschreiben und archiveren der Andrucke. "das fertige Produkt"

Bei diesen Schritten sehe ich nirgendwo die Notwendigkeit von excel, abgesehen von der Erstellung der "Entproduktdatei", für die ich nebenbei bemerkt ein Text-Format (CSV) zwecks späterer Lesbarkeit, bevorzugen würde.

So wie Du es dargestellt hast, werden diese Arbeitsschritte z.Zt. vom Anwender durchgeführt (Bentzer an der Tastatur). Könnte man diesen vllt. davon überzeugen ein komfortableres und schnelleres und ..... Programm zu nutzen?
Vielleicht noch eine Fehlerprüfung / Vollständigkeitsprüfung als Gimmik obendrauf?

Ansonsten kann ich mich nur allen Ausführungen von globetrotter77 und chemiker anschließen.

Gruß K-H

globetrotter77 6. Feb 2009 19:28

Re: Zugriff auf MS Excel
 
Zitat:

Zitat von ThoPos
Zitat:

Zitat von globetrotter77
b) ..., aber auf keinen Fall aus Delphi wieder Excel aufrufen ... das ist vergleichbar damit, sich am eigenen Schopf aus dem Sumpf zu ziehen.

Hallo Globetrotter,

das verstehe ich nicht. Wenn ich aus Excel heraus mein Programm starte und per GetOLEObjekt die Steuerung von Excel übernehme und anschließend Excel wieder freigebe, so ist doch alles in Ordnung? Ich kann doch auch, wenn ich mit dem Auto unterwegs bin, einen ortskundigen Passanten für mich durch die Stadt fahren lassen, und anschließend wieder selber weiterfahren; nur das anschließend der Passant an einem anderen Ort ist. So wie meine Excel-Mappe geändert ist.

Gruß
Thomas

Das sagt sich so leicht, und es kann auch gut sein, dass ich selber einfach ein paar Sachen falsch mache damit, aber irgendwie hatte ich mit solchen Konstrukten bisher IMMER meine Schwierigkeiten.
Sogar dann, wenn ich in einer etwas längeren Schleife neue Excel-Dateien erstellen wollte, konnte es (musste aber nicht!?) passieren, dass beim Aufruf einer neuen Instanz von Excel (durch einen anderen Benutzer ... meist den ungeduldigen Anwender) irgendjemand oder irgendetwas durcheinander kam. Meistens waren das die üblichen Verdächtigen aus Redmond, die sich ausnahmsweise selber aufhängten.

Die schöne neue Welt, in der jeder mit jedem Auto rumgurken kann, erweist sich meiner Meinung nach nur allzu oft als ne einzige Schlittenfahrt auf ner riesigen Eisfläche.

In deinem Fall würde ich vermutlich eher die Methode des Staffellaufs bevorzugen, wenn es sich nicht ohnehin als sinnvoll erweist, alles in Excel abzuhandeln. (nun ja ... sinnvoll ist vielleicht der falsche Ausdruck bei Excel)
Also Kommando an Delphi komplett übergeben, sobald alle Add-Ins abgearbeitet sind,
und die restlichen Formatierungsarbeiten sowie Ausdruck etc. von Delphi erledigen lassen. Dann beißen sie sich zumindest nicht gegenseitig.

sputnic 12. Feb 2009 15:07

Re: Zugriff auf MS Excel
 
Hallo ThoPos,

ich möchte mal auf deine Ausgangsfrage:

Zitat:

Aber wie kann ich die korrekte Instanz von Excel identifizieren und als Object einbinden?
Excel speichert die offenen Instanzen in der RunningObjectTable, diese kannst Du abfragen. Ich habe dazu folgenden Code gefunden:

Delphi-Quellcode:
uses ComObj, ActiveX, Excel2000
var
  ROT: IRunningObjectTable;
  Enum: IEnumMoniker;
  Fetched: integer;
  RunningObj: IMoniker;
  Name: PWideChar;
  BindCtx: IBindCtx;
begin
  OleCheck(CreateBindCtx(0, BindCtx));
  OleCheck(GetRunningObjectTable(0, ROT));
  if ROT.EnumRunning(Enum) = S_OK then
  begin
    Enum.Next(1, RunningObj, @Fetched);
    while RunningObj <> nil do
    begin
      RunningObj.GetDisplayName(BindCtx, nil, Name);
      Memo1.Lines.Append(Name);
      Enum.Next(1, RunningObj, @Fetched);
    end;
  end;
Damit erhälst Du schon mal die Namen der offenen Arbeitsmappen. Über den Namen kannst du dann auf die Instanz zugreifen. Was Du erhälst ist dann ein Workbook Interface. Das könnte dann ungefähr so aussehen:

Delphi-Quellcode:
var
    WB: _WorkBook;
begin
    ....
      if Name = 'Mappe2' then
      begin
        ROT.GetObject(RunningObj, App);
        App.QueryInterface(_WorkBook, WB);
        if assigned(WB) then
        begin
          ShowMessage('Done');
          WB.Application.Quit;
        end;
      end;
    ....
end;
Ich hoffe, Du kannst was damit anfangen.

Grüße
Volker

ThoPos 12. Feb 2009 17:49

Re: Zugriff auf MS Excel
 
Hallo Volker,

vielen Dank schon mal für den Tipp.

Die obere Routine funktioniert prima und ich sehe auch die gewünschte Mappe.

In der unteren Routine habe ich aber das Problem mit der Variablen App. Was für ein Typ ist diese?
Denn ich erhalte immer eine Exception.

Gruß aus Köln
Thomas

mkinzler 12. Feb 2009 17:51

Re: Zugriff auf MS Excel
 
Müsste TExcelApplication sein

stoxx 12. Feb 2009 18:20

Re: Zugriff auf MS Excel
 
Zitat:

Leider findet mein Delphi 2007 die TExcel...-Komponenten nicht. Und meine Versuche diese als Typenbibliotheken zu importieren scheiterten kläglich, da immer irgendwelche Sachen fehlen.
da ich das heute auch hatte, kann ich Dir sagen, dass alle fehlenden Sachen da sind, nachdem Du zusätzlich zu der Excel_TLB, auch die Office_TLB erstellt hast.
Wenn die Pfade stimmen, sollte auch alles gehen.
(Ansonsten mal schnell die TLB's in Dein Projektverzeichnis kopieren)

ich hoffe, Du programmierst nicht völlig blind ohne IDE unterstützung mit den komischen OLEVariants :shock:

ThoPos 12. Feb 2009 18:50

Re: Zugriff auf MS Excel
 
Hallo Allerseits,

der Tipp von Sputnic hat mir den Weg zur Lösung freigeräumt :dancer: :

Delphi-Quellcode:
Uses
  ComObj, ActiveX, UrlMon;

procedure TForm1.Button1Click(Sender: TObject);
var
  BindCtx    : IBindCtx;
  Mk         : IMoniker;
  chEaten    : ULONG;
  DmyObj     : IUnknown;
  wb         : OleVariant;
  xl         : OleVariant;
  ws         : OLEVariant;
begin
  OleCheck(CreateBindCtx(0, BindCtx));
  OleCheck(MkParseDisplayNameEx(BindCtx, PWideChar(WideString(_Mappe)), chEaten, Mk));
  OleCheck(Mk.BindToObject(BindCtx, nil, IUnknown, DmyObj));
  wb := DmyObj as IDispatch;
  xl := wb.Application;
  ws := xl.workbooks[_Mappe].WorkSheets[_Tabelle];
  ws.range[_Zelle] := _Inhalt;
  ws := unassigned;
  wb := unassigned;
  xl := unassigned;
end;
Die vier Variablen haben folgenden Inhalt:
_Mappe -> FullName der Arbeitsmappe, z.B. 'D:\Temp\Mappe1.xls'
_Tabelle -> Name der Tabelle in der Arbeitsmappe, z.B. 'Tabelle1'
_Zelle -> Name oder Koordinaten der Zelle, z.B. 'A1' oder 'MeineZelle'
_Inhalt -> der in die Zelle zu schreibende Text

Gruß aus Köln
Thomas

stoxx 13. Feb 2009 14:58

Re: Zugriff auf MS Excel
 
also ich hab da mal gebastelt. Schick, Schick !
Die Lösung gefällt mir besser, als GetActiveOLEObject :-)

Delphi-Quellcode:
unit

  ComObj,
  ActiveX,

  ExcelXP;

  // oder nach Belieben

  // Excel2000;
  // Excel_TLB;

procedure TForm1.Button1Click(Sender : TObject);
var

    eApp : ExcelApplication;

begin

  eapp := SearchExcelAppFromWorkBook('Mappe1');
  eApp.Quit; // Mappe beenden
  eApp := nil; // Excel Instanz beenden


  eapp := SearchExcelAppFromWorkBook(FFileName);
  if not assigned(eapp) then
    eApp := CoExcelApplication.Create;
 


end;

Delphi-Quellcode:
//==============================================================================
// sucht zu einem Workbook (FileName) die passende Excel Application, wenn mehrere
// Instanzen von Excel offen sind
//==============================================================================

function SearchExcelAppFromWorkBook(const aWorkBookName : string) : ExcelApplication;
var
  ROT: IRunningObjectTable;
  Enum: IEnumMoniker;
  Fetched: integer;
  RunningObj: IMoniker;
  Name: PWideChar;
  BindCtx: IBindCtx;
  App : IInterface;

  wb : _WorkBook;

begin
  result := nil;

  try
      OleCheck(CreateBindCtx(0, BindCtx));
      OleCheck(GetRunningObjectTable(0, ROT));
      if ROT.EnumRunning(Enum) = S_OK then
      begin
        Enum.Next(1, RunningObj, @Fetched);
        while RunningObj <> nil do
        begin
          RunningObj.GetDisplayName(BindCtx, nil, Name);

          // ShowMessage('RunningObj.GetDisplayName: ' + Name);

          if Name = aWorkBookName then begin
              ROT.GetObject(RunningObj, app );
              App.QueryInterface(_WorkBook, WB);
              if assigned(WB) then begin
                  // ShowMessage('Gefunden: ' + aWorkBookName);
                  wb.Application.QueryInterface(_Application, result);
                  exit;
               end;
          end;

          Enum.Next(1, RunningObj, @Fetched);
        end;
      end;
  except
      result := nil;
  end;

end; //  SearchExcelAppFromWorkBook

stoxx 13. Feb 2009 16:29

Re: Zugriff auf MS Excel
 
könnte man eigentlich in die Codelib stellen :-)

ThoPos 14. Feb 2009 05:52

Re: Zugriff auf MS Excel und MS Word
 
Hallo,

nach dem ich es endlich geschaft habe, wollte ich die Routine so abändern, daß ich alle geöffneten Word-Dokumente finde. Problematisch sind dabei neue Dokumente auf Basis einer Vorlage, welche noch nicht gespeichert sind. Hier steht in der ROT nur der FullName der Vorlage, aber nicht der von Word vergebene Name, z.B. "MeineVorlage1".

Also dachte ich mir, ich gehe die Word-Instanzen in einer Schleife als OLEVariant in der Variable "App" durch und lese dann die Documents[..] aus :

Delphi-Quellcode:
function LeseWordDokumente(App: OLEVariant): TStringList;
var
  i    : Integer;
  Datei : OLEVariant;
begin
  Result := TStringList.Create;
  if UpperCase(App.Name) = 'MICROSOFT WORD' then
  begin
  for j := 1 to App.Documents.Count; do
  begin
    Datei := App.Documents[j];  // <-- hier tritt der Fehler auf !!!!
    SL.Add(Datei.FullName);
  end;
end;
Aber, warum kann ich die Dokumente nicht, analog VBA, mit App.Documents[j] ansprechen? Ich erhalte immer eine Exception.
Bei Excel funktioniert App.Workbooks[j] einwandfrei.

Gruß aus Köln
Thomas

ThoPos 14. Feb 2009 10:21

Re: Zugriff auf MS Excel und MS Word
 
Hallo,

hab's gefunden:

Delphi-Quellcode:
function LeseWordDokumente(App: OLEVariant): TStringList;
var
  i    : Integer;
  Datei : OLEVariant;
begin
  Result := TStringList.Create;
  if UpperCase(App.Name) = 'MICROSOFT WORD' then
  begin
  for j := 1 to App.Documents.Count; do
  begin
    Datei := App.Documents.Item(j); // Wichtig: Runde Klammern!!!
    SL.Add(Datei.FullName);
  end;
end;
Gruß aus Köln
Thomas

stoxx 14. Feb 2009 11:34

Re: Zugriff auf MS Excel und MS Word
 
nimm doch endlich mal die Interface Klassen und Deklarationen .. aus ExcelXP .. Excel2000 oder der importierten Excel_TLB
Dasselbe für Word.
da lässt es sich gar nicht erst compilieren, und Deine Fehler treten gar nicht auf :-)
frühe Bindung bevorzugen anstatt der späten Bindung ..

ThoPos 14. Feb 2009 18:52

Re: Zugriff auf MS Excel
 
Funktionieren die Interface-Klassen denn auch 100%ig mit allen Versionen von Office 97 bis Office 2007. Von Delphi 6 habe ich noch genau in Erinnerung, daß es Probleme mit den Komponenten gab. Die mit den Komponenten erstellten Programme waren an bestimmte Office-Versionen gebunden. Deshalb bin ich damals auf OLE umgestiegen und war die Versionsprobleme quitt. Und in dem "Gemischtwarenhandel" an Steuerrechner auf der Arbeit habe ich es leider mit allen Versionen seit Office 97 zu tun. Immer die aktuelle Office-Version auf allen Rechner zu haben, ist nicht gerade preiswert ...

stoxx 14. Feb 2009 19:09

Re: Zugriff auf MS Excel
 
also ich meinte nicht die Komponenten mit dem " T " davor. sondern die reinen Interfacedeklarationen.
bei der TLB werden die ja auch automatisch generiert.
(geht ja bei jedem OLE Interface)

und das ist zu Deinem Vorgehen genau dasselbe, einmal greifst Du auf die Interfaces mit OLEVariant zu, oder eben mit "typisierten" Interfaces .. wie z.b. _Workbook;


Wenn Du neue Features von Office2007 aufrufst ( wie z.b. ExportAsFixedFormat)
Und nur ein Office 97 installiert ist, passiert es Dir in beiden Varianten, dass das Interface eine Exception wirft.
(denke ich mir mal :-)


Der Unterschied ist nur, dass bei Deiner Variante aufwändig zur Laufzeit anhand des Quelltextes alle Interfacefunktionen erst in der Registry gesucht werden, bevor sie aufgerufen werden können.

Bei der frühen Bindung fällt das weg, und man sagt, es wäre schneller :-)

... wenn ich richtig informiert bin :-)

außerdem macht das Programmieren in Deiner Variante keinen Spaß :-)
Wenn Du also mit einer Office97_TLB arbeitest, dann funktionieren die auch noch auf Office2007 ....
natürlich nicht mit allen Funktionen ...


Alle Zeitangaben in WEZ +1. Es ist jetzt 11:16 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz