https://xn----1-bedvffifm4g.xn--p1ai/news/%D0%BE%D1%82%D0%BA%D0%B0%D0%B7-%D0%BE%D1%82-%D0%BC%D0%BE%D0%B4%D0%B0%D0%BB%D1%8C%D0%BD%D1%8B%D1%85-%D0%BE%D0%BA%D0%BE%D0%BD-%D0%B2-1%D1%81-8-3/
Geltungsbereich Der Artikel behandelt das asynchrone Modell zur Erstellung der Geschäftslogik, das der Plattform „1C:Unternehmen“ in der Ausgabe 8.3 hinzugefügt wurde. Die bereitgestellten Informationen sind für die aktuellen Releases der Plattform relevant. Verzicht auf die Verwendung von modalen Fenstern in der Plattform 1C:Unternehmen 8.3 Bei der Entwicklung der Konfiguration auf der Plattform 1C:Unternehmen 8 tritt gelegentlich die Notwendigkeit auf, die Programmausführung bis zu dem Moment anzuphalten, an dem der Benutzer eine Entscheidung trifft oder bestimmte Aktionen ausführt. Beispielsweise sollte beim Klicken auf die Schaltfläche zum Ausfüllen des tabellarischen Teils der Benutzer gefragt werden, ob der tabellarische Teil gelöscht werden soll, um den Verlust der zuvor eingegebenen Daten zu vermeiden. Ein solches Verhalten kann beispielsweise durch den folgenden Code gewährleistet werden: &AufDemClient Prozedur FuelleWaren(Befehl) Antwort = Frage(„Der tabellarische Teil wird gelöscht. Fortfahren?“, ModusDialogFrage.JaNein); Wenn Antwort = CodeRueckgabeDialog.Ja Dann //Algorithmus zum Ausfüllen EndeWenn; EndeProzedur Als Ergebnis der Arbeit dieses Codeausschnitts wird die Ausführung des Programmcodes angehalten, auf dem Bildschirm wird eine Frage angezeigt, die Benutzeroberfläche der Anwendung wird außer dem Dialog mit der Frage unzugänglich, das System wartet auf die Entscheidung des Benutzers, die Codeausführung wird erst nach Beantwortung der Frage fortgesetzt. Auch das Öffnen von modalen Fenstern über den Aufruf der Methode OeffneModal() führt zur Anhaltung der Codeausführung und zur Blockierung der Benutzeroberfläche. Bei der Arbeit mit der Konfiguration im Modus des Web-Clients über einen Browser wird in diesem Fall ein neues Fenster – ein Popup-Fenster – geöffnet, das nicht nur den aktuellen Tab, sondern die gesamte Benutzeroberfläche des Browsers blockiert, einschließlich der anderen geöffneten Fenster und Tabs. Popup-Fenster im Internet werden häufig zur böswilligen Verbreitung unerwünschter Werbung verwendet, daher enthalten Browser Funktionen zur Blockierung von Popup-Fenstern. In diesem Fall muss für die Arbeit mit 1C:Unternehmen 8-Konfigurationen über den Browser die Blockierung von Popup-Fenstern verboten werden. Probleme treten auch bei der Arbeit auf mobilen Geräten auf. So werden beispielsweise modale Fenster auf dem iPad nicht unterstützt. Um diese Probleme zu lösen, sollten anstelle von modalen Fenstern blockierende Fenster verwendet werden. Für den Benutzer sieht alles visuell gleich aus: Das Fenster blockiert die Benutzeroberfläche des Web-Clients. Das blockierende Fenster wird jedoch „über“ dem Hauptfenster gezeichnet, und nur der aktuelle Browser-Tab, in dem die Konfiguration geöffnet ist, wird blockiert, was das Umschalten auf andere Tabs ermöglicht, da dabei keine modalen Browserfenster verwendet werden. Somit werden keine Popup-Fenster im Browser geöffnet, und die Arbeit über den Web-Client auf mobilen Geräten wird gewährleistet. Für das Root-Element der Konfiguration gibt es die Eigenschaft „Modus der Verwendung von Modalität“, die bestimmt, ob in der Konfiguration modale Fenster geöffnet werden können. Wenn die Option „Verwenden“ ausgewählt ist, können modale Fenster geöffnet werden. Wenn die Option „Nicht verwenden“ ausgewählt ist, sind modale Fenster unzulässig. Beim Versuch, eine Methode aufzurufen, die ein modales Fenster öffnet, gibt das System eine Fehlermeldung aus: Bei diesem Wert der Eigenschaft „Modus der Verwendung von Modalität“ sind nur blockierende Fenster zulässig. Wenn die Option „Verwenden mit Warnungen“ ausgewählt ist, wird beim Öffnen von modalen Fenstern im Nachrichtenfenster der folgende Text angezeigt: Diese Arbeitsweise kann als Zwischenstufe bei der Überarbeitung der Konfiguration mit dem Ziel des Verzichts auf modale Fenster verwendet werden. Der Hauptunterschied zwischen blockierenden und modalen Fenstern besteht darin, dass das Öffnen eines blockierenden Fensters die Ausführung des Codes nicht anhält. Daher müssen Entwickler den Programmcode, der modale Fenster verwendet, unter Berücksichtigung dieser Besonderheit umschreiben. Der Code muss in zwei Teile unterteilt werden: Öffnen des blockierenden Fensters; Verarbeitung der Benutzerauswahl. Der am Anfang des Artikels angegebene Codeausschnitt muss wie folgt umgeschrieben werden: &AufDemClient Prozedur FuelleWaren(Befehl) Benachrichtigung = Neue BeschreibungBenachrichtigung(„FuehleWarenFrageAbschluss“, DiesesObjekt); Fragetext = „Der tabellarische Teil wird gelöscht. Fortfahren?“; ZeigeFrage(Benachrichtigung, Fragetext, ModusDialogFrage.JaNein); EndeProzedur &AufDemClient Prozedur FuehleWarenFrageAbschluss(Ergebnis, Zusatzparameter) Export Wenn Ergebnis = CodeRueckgabeDialog.Ja Dann //Algorithmus zum Ausfüllen EndeWenn; EndeProzedur Nach der Ausführung der Prozedur ZeigeFrage() hält das System nicht an, um auf die Antwort des Benutzers zu warten, die Codeausführung wird fortgesetzt. Der Benutzer kann erst nach dem Abschluss der gesamten Prozedur eine Auswahl treffen. Dabei wird die Export-Prozedur FuehleWarenFrageAbschluss() aufgerufen. Ihren Namen haben wir im Konstruktor des Objekts BeschreibungBenachrichtigung übergeben. Die Prozedur, die nach der Auswahl aufgerufen wird, kann im Formularmodul, im Befehlsmodul oder im allgemeinen nicht-globalen Modul liegen. Im betrachteten Beispiel befindet sich die aufgerufene Prozedur im Modul der gesteuerten Form, daher haben wir im Parameter DiesesObjekt übergeben. Betrachten wir den Aufruf einer Prozedur, die in einem allgemeinen Modul liegt. Dazu fügen wir ein neues allgemeines Modul BenachrichtigungVerarbeitung hinzu, setzen dafür das Flag „Client (gesteuerte Anwendung)“, und das Flag „Global“ wird nicht gesetzt. Wir platzieren die Prozedur FuehleWarenFrageAbschluss() in diesem Modul. Dann sieht der Befehls-Handler wie folgt aus: &AufDemClient Prozedur FuehleWaren(Befehl) Benachrichtigung = Neue BeschreibungBenachrichtigung(„FuehleWarenFrageAbschluss“, BenachrichtigungVerarbeitung); Fragetext = „Der tabellarische Teil wird gelöscht. Fortfahren?“; ZeigeFrage(Benachrichtigung, Fragetext, ModusDialogFrage.JaNein); EndeProzedur Nach dem Aufruf einer beliebigen Methode, die ein blockierendes Fenster öffnet, muss die Prozedur enden, und der folgende Code sollte in der Prozedur platziert werden, die nach dem Schließen des Fensters aufgerufen wird. Zur Übertragung des Kontexts (Hilfsdaten, bestimmter Parameter, Variablenwerte) aus der Prozedur, die ein modales Fenster öffnet, in die Prozedur, die beim Schließen aufgerufen wird, ist der dritte optionale Parameter des Konstruktors des Objekts BeschreibungBenachrichtigung vorgesehen – Zusatzparameter. Dieses Objekt (jeglichen Typs) wird als letzter Parameter an die in BeschreibungBenachrichtigung beschriebene Prozedur übergeben. Am Beispiel des oben betrachteten Codeausschnitts kann dies wie folgt erfolgen: &AufDemClient Prozedur FuehleWaren(Befehl) Parameter1 = 0; Parameter2 = 0; ParameterListe = Neue Struktur(„Parameter1, Parameter2“, Parameter1, Parameter2); Benachrichtigung = Neue BeschreibungBenachrichtigung(„FuehleWarenFrageAbschluss“, DiesesObjekt, ParameterListe); ZeigeFrage(Benachrichtigung, „Der tabellarische Teil wird gelöscht. Fortfahren?“, ModusDialogFrage.JaNein); EndeProzedur &AufDemClient Prozedur FuehleWarenFrageAbschluss(Ergebnis, Zusatzparameter) Export Wenn Ergebnis = CodeRueckgabeDialog.Ja Dann //Analysiere Zusatzparameter.Parameter1 //Analysiere Zusatzparameter.Parameter2 EndeWenn; EndeProzedur Wenn nur ein Wert übertragen werden soll, kann die Struktur weggelassen und dieser Wert dem Parameter Zusatzparameter des Konstruktors des Objekts BeschreibungBenachrichtigung zugewiesen werden. Betrachten wir einige Beispiele für die Arbeit mit blockierenden Fenstern. Aufgabe 1. Öffnen eines anderen Formulars Aus dem Dokumentformular soll beim Klicken auf die Schaltfläche „Parameter öffnen“ ein Formular geöffnet werden, auf dem zwei Kontrollkästchen Parameter1 und Parameter2 platziert sind, die der Benutzer aktivieren muss. Nach dem Schließen des Formulars sollen die Werte der Parameter in der Nachrichtenleiste ausgegeben werden. Wir erstellen ein allgemeines Formular „FormularParameter“, auf dem wir die Attribute Parameter1 und Parameter2 sowie den Befehl FormularSchliessen platzieren: Der Befehls-Handler sieht wie folgt aus: Der Befehls-Handler sieht wie folgt aus: &AufDemClient Prozedur FormularSchliessen(Befehl) ParameterListe = Neue Struktur(„Parameter1, Parameter2“, Parameter1, Parameter2); Schliessen(ParameterListe); EndeProzedur Für das Formular setzen wir die Eigenschaft OeffnungsmodusFenster auf „Gesamte Benutzeroberfläche blockieren“: Auf dem Dokumentformular platzieren wir den Befehl ParameterOeffnen, dessen Handler wir wie folgt beschreiben: &AufDemClient Prozedur ParameterOeffnen(Befehl) Benachrichtigung = Neue BeschreibungBenachrichtigung(„ParameterOeffnenAbschluss“, DiesesObjekt); OeffneFormular(„AllgemeinesFormular.FormularParameter“, , , , , , Benachrichtigung); EndeProzedur &AufDemClient Prozedur ParameterOeffnenAbschluss(Ergebnis, Zusatzparameter) Export Wenn TypWert(Ergebnis) = Typ(„Struktur“) Dann Für jeden SchlusselWert aus Ergebnis Schleife Nachricht = Neue BenutzerNachricht; Nachricht.Text = „Schlüssel: „”“ + SchlusselWert.Schlussel + „”“, Wert = „ + SchlusselWert.Wert; Nachricht.Mitteile(); EndeSchleife; EndeWenn; EndeProzedur Im Benutzermodus, bei der Ausführung der Konfiguration unter dem Web-Client, erhalten wir folgende Arbeitsergebnisse: Zum Vergrößern auf das Bild klicken. Der Fensteröffnungsmodus kann auch im letzten Parameter der Prozedur OeffneFormular angegeben werden. &AufDemClient Prozedur ParameterOeffnen(Befehl) Benachrichtigung = Neue BeschreibungBenachrichtigung(„ParameterOeffnenAbschluss“, DiesesObjekt); OeffneFormular(„AllgemeinesFormular.FormularParameter“, , , , , , Benachrichtigung, ModusOeffnenFensterFormular.GesamteBenutzeroberflächeBlockieren); EndeProzedur Aufgabe 2. Frage beim Schließen des Formulars Beim Schließen des Bearbeitungsfensters soll der Benutzer gefragt werden, ob er das Fenster wirklich schließen möchte. Diese Aufgabe kann mit dem folgenden Code gelöst werden, der im Formularmodul der Bearbeitung platziert ist: &AufDemClient Global BenoetigeSchliessenFormular; &AufDemClient Prozedur VorDemSchliessen(Verweigerung, Standardbehandlung) Wenn NOT BenoetigeSchliessenFormular = Wahr Dann Verweigerung = Wahr; Benachrichtigung = Neue BeschreibungBenachrichtigung(„VorDemSchliessenAbschluss“, DiesesObjekt); ZeigeFrage(Benachrichtigung, „Möchten Sie das Fenster wirklich schließen?“, ModusDialogFrage.JaNein); EndeWenn; EndeProzedur &AufDemClient Prozedur VorDemSchliessenAbschluss(Ergebnis, Zusatzparameter) Export Wenn Ergebnis = CodeRueckgabeDialog.Ja Dann BenoetigeSchliessenFormular = Wahr; Schliessen(); Anders BenoetigeSchliessenFormular = NichtDefiniert; EndeWenn; EndeProzedur In der Prozedur VorDemSchliessen des Formulars wird dem Benutzer eine Frage gestellt, das Flag Verweigerung wird auf Wahr gesetzt, das Schließen des Formulars wird abgebrochen. Nach einer bejahenden Antwort auf die Frage wird die Variable BenoetigeSchliessenFormular auf Wahr gesetzt, das Formular wird erneut geschlossen. Aufgabe 3. Eingabe eines numerischen Werts Beim Klicken auf eine Schaltfläche im Bearbeitungsfenster soll der Standarddialog zur Eingabe einer Zahl geöffnet werden. Dazu muss die Methode ZeigeEingabeZahl() anstelle von EingabeZahl() verwendet werden, die ein blockierendes Fenster anstelle eines modalen Fensters öffnet. &AufDemClient Prozedur EingabeZahl(Befehl) Benachrichtigung = Neue BeschreibungBenachrichtigung(„EingabeZahlAbschluss“, DiesesObjekt); ZeigeEingabeZahl(Benachrichtigung, 0, „Geben Sie die Menge ein“, 15, 3); EndeProzedur &AufDemClient Prozedur EingabeZahlAbschluss(Ergebnis, Zusatzparameter) Export Wenn NOT Ergebnis = NichtDefiniert Dann Nachricht = Neue BenutzerNachricht; Nachricht.Text = „Sie haben die Menge „ + Ergebnis + „ eingegeben.“; Nachricht.Mitteile(); EndeWenn; EndeProzedur Nach dem Schließen des Fensters zur Eingabe der Zahl wird die Prozedur aufgerufen, an deren ersten Parameter die eingegebene Zahl oder der Wert NichtDefiniert übergeben wird, wenn der Benutzer die Eingabe abgebrochen hat. Aufgabe 4. Farbauswahl Beim Klicken auf eine Schaltfläche im Bearbeitungsfenster soll der Benutzer über den Standarddialog zur Farbauswahl die erforderliche Farbe angeben. Diese Farbe soll für den Hintergrund der gedrückten Schaltfläche festgelegt werden. Wir fügen der Form den Befehl Farbauswahl mit dem folgenden Handler hinzu: &AufDemClient Prozedur Farbauswahl(Befehl) FarbauswahlDialog = Neuer FarbauswahlDialog; Benachrichtigung = Neue BeschreibungBenachrichtigung(„FarbauswahlAbschluss“, DiesesObjekt); FarbauswahlDialog.Zeige(Benachrichtigung); EndeProzedur &AufDemClient Prozedur FarbauswahlAbschluss(Ergebnis, Zusatzparameter) Export Wenn NOT Ergebnis = NichtDefiniert Dann Elemente.Farbauswahl.FarbeHintergrund = Ergebnis; EndeWenn; EndeProzedur Für die Objekte FarbauswahlDialog (sowie DialogBearbeitungStandardzeitraum, KonstruktorFormatzeichenkette, DialogZeitplanRegelauftrag, DialogSchriftartAuswahl) öffnet die Methode Zeige() ein blockierendes Fenster. Nach dem Schließen des Fensters wird die Prozedur aufgerufen, an deren ersten Parameter der ausgewählte Wert (Farbe, Schriftart usw.) oder der Wert NichtDefiniert übergeben wird, wenn der Benutzer die Auswahl abgebrochen hat. Es ist darauf hinzuweisen, dass das Objekt DateiauswahlDialog im Gegensatz zu den Dialogen zur Farbauswahl oder Schriftartauswahl keine Methode Zeige() hat, da die Implementierung dieser Dialoge erheblich unterschiedlich ist. Um den Dateiauswahl-Dialog im Web-Client zu verwenden, muss zuvor die Erweiterung zur Dateibearbeitung eingebunden werden. Dialoge, die über die Erweiterung zur Dateibearbeitung implementiert werden, verursachen keine solchen Arbeitsprobleme wie modale Browser-Fenster, daher wurde das Öffnen von blockierenden Fenstern für das Objekt DateiauswahlDialog nicht implementiert. Abschließend sei angemerkt, dass ab dem Release 8.3.10 die Unterstützung von modalen Fenstern im Web-Client eingestellt wurde. In diesem Fall wird bei einem Aufruf einer modalen Methode in der Konfiguration eine Ausnahme generiert. Auch die Unterstützung des Benutzeroberflächenmodus „In einzelnen Fenstern“ im Web-Client wurde eingestellt. Darüber hinaus können in der dünnen und der Web-Version keine Formulare mehr in einem separaten Fenster geöffnet werden (bei Arbeit im Modus „In Tabs“). Solche radikalen Schritte ermöglichten es, auf den Benutzeroberflächenmodus zu verzichten, der von modernen Browsern nicht mehr unterstützt wird. Welche praktische Schlussfolgerung kann aus diesen Informationen gezogen werden? Die Schlussfolgerung ist ziemlich einfach – wenn in Ihrer Konfiguration aus irgendeinem Grund weiterhin modale Aufrufe existieren, wird an diesen Stellen im Web-Client ein Fenster mit einer Fehlermeldung angezeigt. Es sei davor gewarnt, nach einer schnellen Lösung für dieses Problem im Internet zu suchen, da die meisten Ratschläge auf folgendes Rezept hinauslaufen: Im Konfigurator auf Konfigurationsebene die Eigenschaft „Modus der Verwendung von Modalität“ auf den Wert „Verwenden“ setzen. Natürlich wird dies derzeit nur deshalb nicht funktionieren, weil moderne Browser selbst keine modalen Aufrufe mehr unterstützen. Und Sie haben nur zwei Möglichkeiten, das oben beschriebene Problem zu lösen: Aktualisieren Sie die Plattform auf Release 8.3.10+ (8.3.11), setzen Sie die Konfigurationseigenschaft „Kompatibilitätsmodus“ auf „Nicht verwenden“ und schreiben Sie die Codeabschnitte, die modale Methoden verwenden, unter Verwendung des asynchronen Modells zur Erstellung der Geschäftslogik um. Empfehlen Sie Ihren Kunden, veraltete Browser zu verwenden, in denen modale Aufrufe noch unterstützt wurden (Mozilla Firefox Version 37 und niedriger, Chrome unter Version 37 usw.). Übrigens, ab Release 8.3.11 werden die Web-Browser Microsoft Internet Explorer Versionen 8 und 9 nicht mehr unterstützt. Mit Web-Browsern im Hinblick auf Modalität haben wir uns bereits befasst, nun ist es an der Zeit, die Situation mit den anderen Clients zu klären. Ab Version 8.3.5 wird die Eigenschaft „Modus der Verwendung von Modalität“ in der dünnen und der dicken Client-Version nur berücksichtigt, wenn der Befehlszeilenparameter /EnableCheckModal angegeben ist. Dieser Parameter wird automatisch nur beim Starten der Anwendung aus dem Konfigurator in die Befehlszeile eingefügt. Wenn dieser Parameter nicht angegeben ist, werden keine Ausnahmen generiert und keine entsprechenden Warnungen angezeigt. In der Praxis bedeutet dies, dass bei Verwendung der dicken und der dünnen Client-Version keine grundlegenden Änderungen im Arbeitsverhalten bei Verwendung des Modalitätsmodus beobachtet werden – modale Aufrufe werden wie zuvor funktionieren, ohne jegliche Warnungen auszugeben, wie im Web-Client. Um alle Punkte auf dem „i“ zu setzen, sei angemerkt, dass ab Ausgabe 8.3.9 im dicken Client die Konfigurationseigenschaft „Modus der Verwendung von synchronen Aufrufen von Plattformerweiterungen und externen Komponenten“ ignoriert wird, wobei die entsprechenden synchronen Methoden ohne Generierung von Ausnahmen und Anzeige von Warnungen funktionieren. Die ignorierte Eigenschaft wurde in Ausgabe 8.3.5 eingeführt, um die asynchrone Arbeit mit externen Komponenten, Kryptographie und Erweiterungen zur Dateibearbeitung im Web-Browser Google Chrome zu unterstützen. Es ist klar, dass dies keinen Bezug zum dicken Client hat, und daher hat das „stille“ Ignorieren dieser Eigenschaft einfach zusätzliche Prüfungen zur Verwendung synchroner Methoden bei der Verwendung der Konfiguration ausgeschlossen. Übrigens! Da die Plattform sicher in Richtung Web fortschreitet, haben die Entwickler ab Version 8.3.8 bestimmte Einschränkungen für den Programmcode eingeführt, der mit der Logik zum Schließen von Formularen oder Anwendungen verbunden ist, die im dicken und dünnen Client ausgeführt wird. Lesen Sie unbedingt unseren Artikel, der diesen Aspekt ausführlich beleuchtet. Darüber hinaus gibt es im Kurs „Professionelle Entwicklung von Benutzeroberflächen und Formularen in 1C:Unternehmen 8.3“ ein Kapitel, das dem Verzicht auf Modalität gewidmet ist, und Sie können dort eine Menge nützlicher und aktueller Informationen zu diesem Thema finden. Kollegen, es gibt zwei Dinge, die man endlos lesen kann: den Feed in VKontakte und die Änderungsliste im nächsten Release der Plattform, also fassen wir die endgültigen Ergebnisse zusammen ;) Im Prozess der Betrachtung von Beispielen, die den Übergang von Elementen des synchronen Modells zum asynchronen ermöglichen, sind Sie wahrscheinlich bereits bemerkt haben, dass im Allgemeinen der Umfang des Programmcodes zugenommen hat. Je mehr Code, desto höher wird die Komplexität seiner weiteren Wartung und Fehlersuche. Darüber hinaus wird die Menge des Codes noch weiter zunehmen, wenn wir im Entwicklungsprozess eine größere Anzahl von Dialogen verwenden. Daher muss man im Prozess der Entwicklung von anwendungsorientierten Lösungen, die auf die Arbeit im Web-Client ausgelegt sind, an die Arbeitsparadigmen denken, die derzeit in modernen Web-Anwendungen verwendet werden. Daher, wenn in Ihrer Konfiguration viele interaktive Dialoge mit dem Benutzer und ausgegebene Warnungen vorhanden sind, lohnt es sich, diese Funktionalität zugunsten anderer Ansätze zur Organisation der Interaktion mit dem Benutzer zu überdenken.
