Neuigkeiten:

Wenn ihr euch für eine gute Antwort bedanken möchtet, im entsprechenden Posting einfach den Knopf "sag Danke" drücken!

Mobiles Hauptmenü

Datensatz nur bilden wenn noch nicht vorhanden

Begonnen von tismo, Oktober 25, 2025, 16:06:41

⏪ vorheriges - nächstes ⏩

tismo

Hallo,

durch klicken auf eine Schaltfäche wir in einem Unterformular ein neuer Datensatz gebildet.

    Me![Unterformular].SetFocus
    DoCmd.RunCommand acCmdRecordsGoToNew
    Me![Unterformular]!Textfeld1.SetFocus
    Me![Unterformular]!Textfeld1 = "Inhalt1"
    Me![Unterformular]!Textfeld2 = "Inhalt2"

Im Unterformular wird der Datensatz mit dem 'Inhalt1'  im 'Textfeld1' und 'Inhalt2' im 'Textfeld2' erzeugt
klappt soweit.

Wie lautet der code, wenn vorher überprüft werden soll, ob der der Datensatz 'Textfeld' mit dem 'Inhalt1' im 'Unterformular' schon vorhanden ist und wenn nicht dann neu bilden ansonsten nicht?

Kann mir jemand helfen?


Bitsqueezer

Hallo,

einen Datensatz schlägt man am besten nach, indem man DLookup verwendet. Dazu bitte die Doku lesen.

Es ist schlechte Praxis, einen Datensatz mit Daten zu füllen. Wenn der User das versehentlich gemacht hat, hast Du bereits halbfertige Daten und eine ID vergeben (sofern eine AutoID vorhanden ist), je nach Aufbau des Datensatzes wird er dann auch unfertig gespeichert.

Besser ist, die Eigenschaft DefaultValue zu verändern und dann zu einem neuen Datensatz zu springen. Die Daten stehen dann ebenfalls im Feld, aber wenn der User die Bearbeitung nicht beginnt, wird auch nichts gespeichert.

Du brauchst außerdem kein SetFocus, um Eigenschaften zu verändern, egal ob Value oder DefaultValue.

Gruß

Christian

tismo

Hallo,

das ist ja vielleicht alles richtig, aber warum sollte ich eine für meine Zwecke perfekt funktionierende vba ändern nur weil 'man' das so nicht macht?

Die Anwendung ist so geschrieben, dass es für die User sehr einfach gehalten ist und ihnen dadurch eine Menge Arbeit abgenommen wird. Um die Arbeit noch effektiver zu machen bräuchte ich eine Lösung für mein Problem: erkenne, ob der Datensatz schon existiert, wenn ja im Textfeld2 mit InhaltX ändern, sonst Datensatz erstellen und Textfeld 2 mit InhaltX füllen.

Es gibt sicherlich noch viele bessere Vba's, aber die vorhandene funtioniert für meine Zwecke am besten, da insgesamt auf einmal 70 Datebnsätze erzeugt werden müssen.

LG
Lars


andyfau

Hallo Lars,

warum sollte man im Forum fragen, wenn man Vorschläge, die in guter Absicht gegeben werden, erstmal garnicht ausprobiert und ablehnt.

Hier ein Vorschlag, der deinem "Quick and Dirty-Ansatz" vielleicht mehr entspricht:
Lege in der Tabelle einen Index auf Textfeld1 mit der Einstellung Doppelte Sätze erlaubt = nein an. Dann wirst Du es nicht schaffen einen zweiten Datensatz mit dem gleichen Inhalt in Textfeld1 anzulegen. Um es noch "dreckiger" zu machen kannst Du den dann auftretenden Laufzeitfehler einfach mit on error resume next übergehen und dem Anwender eine Meldung "Satz schon voranden" geben.



Beste Grüße
Andreas

Bitsqueezer

Hallo,

naja, offenbar funktioniert "die VBA" (?) ja so gut, daß Du sie verändern willst. Und wenn sie ja so perfekt ist und Du "sie" auf keinen Fall ändern willst, warum willst Du "sie" dann jetzt doch ändern?

Völlige Unlogik.

Und wenn man schon beim Verbessern ist, warum dann nicht gleich richtig machen? Aber da Du ja anscheinend Änderungsvorschläge gar nicht akzeptieren willst, spare ich mir weitere Kommentare.

Gruß

Christian

MzKlMu

Hallo,
Du musst vorab mit DlookUp prüfen (wie Christian schon schrieb) ob der Datensatz vorhanden ist.
Tippe DlookUp im VBA Editor ein, stelle den Cursor auf das Wort und drücke F1. Du erhältst dann zu DLookUp jede Menge Hilfe mit vielen Beispielen.

Abgesehen davon sehe ich das wie Christian. Und noch etwas fällt mir auf:

Zitatda insgesamt auf einmal 70 Datebnsätze erzeugt werden müssen.
Das ist auch erklärungsbedürftig.
Muss jeder einzelen Datensatz auf Existenz geprüft werden ?
Gruß Klaus

tismo

Hallo Christian

vielleicht war 'verändern' nicht der richtige Begriff, sondern sollte 'ergänzen' heißen.
Es tut mit Leid, wenn du dich falsch verstanden gefühlt hast.

Ich bin leider kein professioneller Access-Programmierer und bin daher auf Hilfe aus diesem Forum angewiesen.
Ich weiß, dass in meiner Anwendung viel Müll drin ist, aber die Anwendung läuft und wenn ein Problem auftritt, kann ich dieses in wenigen Minuten beheben. Wie heißt es? never change a winning team.
Von Zeit zu Zeit stehen leider Veränderungen zwangsläufig an. Diese versuche ich alleine zu bewältigen. Dies geht aber nicht immer. Deshalb frage ich hier im Forum.

Änderungsvorschläge nehme ich gern an, aber bei einer Größe der Anwendung von 0,5 GB und aufgeteilten Datenbänken von 1,7 GB wird es schwierig jeden Code zu überarbeiten.

Jedesmal wenn ich im Forum ein Frage stelle, hoffe ich, dass mein Problem von allen verstanden wird, auch wenn ich nicht die richtigen Begriffe verwende und mir ein schneller Lösungsvorschlag in Form eines Codes gegeben wird.

Wenn du dich von mit angegriffen gefüht hast tut mir das Leid. Leider kann ich mit deinen Antworten in dieser Form nicht viel anfangen.

LG
Lars



Normalo0815

#7
Hallo tismo,

  Me![Unterformular].SetFocus
    DoCmd.RunCommand acCmdRecordsGoToNew
    Me![Unterformular]!Textfeld1.SetFocus

    If Len("Inhalt1") > 0 then   ' <- und v .. Statt "Inhalt1" den Variablennamen einsetzen!
      DoCmd.FindRecord Replace(Replace(Replace(Replace(Replace("Inhalt1", "[", "[[]"), """", "[""]"), "?", "[?]"), "*", "[*]"), "#", "[#]"), acEntire, False, acSearchAll, False, acCurrent, True
      Me![Unterformular]!Textfeld1 = "Inhalt1"
      Me![Unterformular]!Textfeld2 = "Inhalt2"
    end if

Die Konstante "Inhalt1" muss noch überall durch den tatsächlichen Variablennamen ausgetauscht werden!

• Wenn ein Datensatz gefunden wird, dann wird dorthin navigiert, ansonsten bleibt der Fokus am neuen Datensatz. Die Zuweisung der Inhalte erfolgt dann dementsprechend.
• Leerer Text ("" oder NULL) werden übergangen.
• Groß-/Kleinschreibung wird beim Suchen ignoriert bzw. als gleich behandelt.
• Die zahlreichen Replaces sind nötig, um die Mustersuche mit Platzhalterzeichen zu verhindern.

Ein eindeutiger Index auf das Feld in der Tabelle wäre auch sinnvoll, um generell Duplikate auszuschließen.

Ungetestet! Kann sein, dass es nicht richtig funktioniert oder unerwartete Nebenwirkungen gibt  Das ist auch von den Formulareinstellungen (Eigenschaften) abhängig. :o

-----

Edit 13:30 Uhr: Die Reihenfolge der Replaces geringfügig abgeändert, da es sonst in manchen Situationen nicht richtig funktionierte!
Freundliche Grüße
Normalo0815   :)

tismo

Hallo Klaus,

ZitatDas ist auch erklärungsbedürftig.
Muss jeder einzelen Datensatz auf Existenz geprüft werden ?

Meine Anwender sind teilweise über 60 Jahre und haben mit Programmen/Anwendungen eigentlich nicht viel am Hut. Für die Personen habe ich meine Anwendung so gestaltet, dass beim klicken auf einen Button in einem Unterformular eine Organisationsliste mit 70 Datensätzen/Zeilen aufgelistet wird. Der Anwender muss nun diese Liste von oben nach unten kurz durcharbeiten und die entsprechenden Datensäzte aktivieren. Als nächstes drückt der Anwender auf einen weiteren Button um alle nicht aktivierten Datensätze wieder zu löschen. Er erhält nun eine Liste mit ca. 10-30 Datensätze, die er weiter bearbeiten kann. Wenn er die nun aktivierten Datensätze bearbeitet, wird die Hintergrundfarbe blau, wenn der Datensatz fertig bearbeitet ist wird die Hintergrundfarbe weiß und jeder andere Anwender sieht, dass dieser Datensatz erledigt ist.

Ich wollte meine Anwendung jetzt so verändern, dass ein bestimmter aktivierter Datensatz weiß (bearbeitet) wird, wenn ein bestimmtes Etikett ausgedruckt wird, sollte der erste Anwender vergessen haben den dafür zuständigen Datensatz zu aktivieren, sollte dieser in der Liste eingefügt werden und sofort als bearbeitet markiert werden.

Das war eigentlichg mein Problem.

Wie ich schon zuvor bemerkte, bin ich kein Informatiker und habe mir alles selber angeeignet.
Aber es läuft (!!!), und die Anwender sind froh, dass Ihre Vorschläge zur Verbesserung der Anwendung schnell umgesetzt werden.

Manchmal wünschte ich mir, wenn ein professioneller Informatiker mal über die Anwendung drüber schaut. Ich muss noch mit der Access Version 2010 arbeiten, da nur noch hier Replikationen möglich sind. Da die Anwender zu Beratungen mit Laptops zu den Kunden fahen und ich eine satbile Internetverbindung nicht garanieren kann ist die Synchronisierung der Datenbanken mittes Replikation meines Erachtens die beste Lösung.

LG
Lars

MzKlMu

Hallo,
ZitatJedesmal wenn ich im Forum ein Frage stelle, hoffe ich, dass mein Problem von allen verstanden wird,
Dein Problem ist verstanden worden und es gab auch Lösungsvorschläge dazu (DLookUp).

 
ZitatDer Anwender muss nun diese Liste von oben nach unten kurz durcharbeiten und die entsprechenden Datensäzte aktivieren.
Warum legst Du dnicht gleich nur so viele DS an wie nötig ? Woran erkannt der Anwender die zu aktivierenden DS ?

ZitatAls nächstes drückt der Anwender auf einen weiteren Button um alle nicht aktivierten Datensätze wieder zu löschen.
Du weist, dass diese Datensätze nicht wirklich physisch gelöscht werden, die werden nur intern zur Löschung vorgemerkt. Gelöscht (entgültig) werden diese DS erst nach dem das Access Dienstprogramm "Reparieren/Komprimieren" ausgeführt worden ist. Auch Entwürfe von Formularen und Berichten werden erst danach wirklich aus der DB entfernt.Das muss regelmäßig gemacht werden, sonst bläht sich die DB auf. "Reparieren/Komprimieren" muss daher auch auf jedem PC regelmäßig ausgeführt werden. Mit "Reparieren/Komprimieren" werden auch die Indizetabellen neu geschrieben. Was im Zusammenhang mit der Replikation zu Problemen führen kann.

Die Replikation wurde von MS auch wegen Unzuverlässigkeit aufgegeben. Das solltest Du bedenken und nach anderen Lösungen suchen. Für andere Lösungen ist Christian allerdings der bessere Ansprechpartner.
Gruß Klaus

tismo

Hallo Klaus,

danke für deine Antwort

ZitatWarum legst Du dnicht gleich nur so viele DS an wie nötig ? Woran erkannt der Anwender die zu aktivierenden DS ?

Die Liste die eingelesen wird ist eine Organisationsliste mit Vorschlägen. Nicht alle eingelesenen Datensätze sind jedesmal erforderlich und müssen vom Anwender/Berater mit dem Kunden besprochen werden und dementsprechend aktiviert werden. Einige Datensätze sind in bestimmten Fällen automatisch aktiviert, andere werden garnicht erst dem Anwender zur Aktivierung vorgeschlagen.

ZitatAls nächstes drückt der Anwender auf einen weiteren Button um alle nicht aktivierten Datensätze wieder zu löschen.

Ich weiß um das Problem mit der Replikation. Die Anwendung läuft mittlerweile auf 40 verschiedenen PC's oder Laptops und wird von 15 Anwendern bearbeitet. Ich habe bisher nur gute Erfahrungen mit der Replikation von Tabellen gemacht. Die Probleme und Fehler, die bisher angefallen sind konnten, in den letzten 20 Jahren alle relativ schnell von mir behoben werden.

Allerdings stehe ich mittlerweile mit der Version 2010 vor nicht lösbaren Problemen wie z.B. das Erstellen von Berichten im pdf/A-3 Format (Zugferd).
Anderseits hat die Replikation von Tabellen den Vorteil, dass bei einem Datenverlust auf dem Server oder Ausfall des Servers die Tabellen mit den Daten immernoch auf den Clients vorhanden sind und im Notfall zurückgespielt werden können.
Ich kann es mir nicht leisten beim Kunden auf eine bestehende Internetverbindung zu hoffen oder um das WLAN-Passwort zu fragen. Es gibt tatsächlich noch viele Orte wo ich kein Internet habe, vor allem im Ruhrgebiet.

Wenn du oder Christian mir eine mindestens genauso zuverlässige Methode vorschlagen könntet, wäre ich euch sehr dankbar. Ich war aber auch diesbezüglich schon mit mit Karl Donaubauer im Kontakt. Zuletzt überlegten wir eine Replikation für die neuesten Access-Versionen zu programmieren, was einen erheblichen Aufwand bedeutete.

LG
Lars

Normalo0815

Hallo tismo,
mir ist aufgefallen, dass in Beitrag #7 die Replaces ungünstig gereiht waren, und es deshalb in manchen Situationen nicht richtig funktionierte. Nachfolgend und auch in #7 nun korrigierter Code:
  Me![Unterformular].SetFocus
    DoCmd.RunCommand acCmdRecordsGoToNew
    Me![Unterformular]!Textfeld1.SetFocus

    If Len("Inhalt1") > 0 then  ' <- und v .. Statt "Inhalt1" den Variablennamen einsetzen!
      DoCmd.FindRecord Replace(Replace(Replace(Replace(Replace("Inhalt1", "[", "[[]"), """", "[""]"), "?", "[?]"), "*", "[*]"), "#", "[#]"), acEntire, False, acSearchAll, False, acCurrent, True
      Me![Unterformular]!Textfeld1 = "Inhalt1"
      Me![Unterformular]!Textfeld2 = "Inhalt2"
    end if
Die weiteren Hinweise siehe Beitrag #7.
Freundliche Grüße
Normalo0815   :)

tismo

Hallo Normalo0815,

    If Len("Inhalt1") > 0 then  ' <- und v .. Statt "Inhalt1" den Variablennamen einsetzen!
      DoCmd.FindRecord Replace(Replace(Replace(Replace(Replace("Inhalt1", "[", "[[]"), """", "[""]"), "?", "[?]"), "*", "[*]"), "#", "[#]"), acEntire, False, acSearchAll, False, acCurrent, True
      Me![Unterformular]!Textfeld1 = "Inhalt1

wenn ich das richtig lese wird der Inhalt verglichen aus Inhalt1, ob dieser schon vorhanden ist.

Vielleicht habe ich mich falsch oder zu ungenau ausgedrückt, aber es soll nachgesehen werden, ob das Textfeld mit dem Inhalt1 schon vorhanden ist um dann ggf erzeugt zu werden.

Kann ich im code Inhalt1 einfach mit Textfeld1 austauschen?

    If Len("Textfeld1") > 0 then  ' <- und v .. Statt "Inhalt1" den Variablennamen einsetzen!
      DoCmd.FindRecord Replace(Replace(Replace(Replace(Replace("Textfeld1", "[", "[[]"), """", "[""]"), "?", "[?]"), "*", "[*]"), "#", "[#]"), acEntire, False, acSearchAll, False, acCurrent, True
      Me![Unterformular]!Textfeld1 = "Inhalt1

VG
Lars

Normalo0815

Me![Unterformular]!Textfeld1 und 2 sehen für mich wie Steuerelemente im Formular aus, was noch keinen Inhalt hat (Zuweisung erst danach). Sind diese an Tabellenfelder gebunden oder nicht?

"Inhalt1" sieht aus wie eine Konstante im VBA-Code, was eigentlich keinen Sinn macht. Sollte eine Variable sein.

wie sieht der Original-VBA-Code aus?

Freundliche Grüße
Normalo0815   :)

tismo

Danke für die Antwort

bitte vergiss meinen vorherigen Post, war ein Denkfehler von mir.


LG
Lars