Laden...

Forenbeiträge von Kostas Ingesamt 597 Beiträge

02.07.2012 - 13:31 Uhr

Sorry hat sich erledigt.

Ich habe das Projekt auf einem anderen PC kompilieren lassen und es hat
einwandfrei funktioniert. Danach wieder zurück auf der anderen Maschine,
die Referenz auf die DLL gelöscht und neu angelegt und jetzt funktioniert
auch auf dieser Maschine.
War wiedermal mein Fehler. Was ich falsch gemacht habe, habe ich leider nicht
bemerkt.
Sorry nochmals.
Gruß Kostas

02.07.2012 - 13:17 Uhr

Hallo Lennart,

genau das verwundert mich. Als Referenz habe ich die DLL für FW2.0
wie zum Geier kommt er auf die Idee FW3.5 zu verwenden.

Ich werde das Projekt auf einer anderen Maschine compilieren auf dem
Firebird 2.5 nicht installiert ist.

Danke für die Info. Der Treiben für Firebird 2.5 hatte ich noch nicht installiert.
Gruß Kostas

02.07.2012 - 12:44 Uhr

lHallo Zusammen,
ich habe ein Projekt schon länger nicht mehr anfassen müssen, und eigentlich
auch keine Änderungen eingebaut die das FW 3.5 benötigen würden.
In den Projekteigenschaften ist das Ziel FW auch 2.0 eingetragen.
Dennoch bekomme ich von VS2010 die Fehlermeldung:

Fehlermeldung:
Warnung 1 Der Primärverweis "FirebirdSql.Data.FirebirdClient, Version=2.1.0.0, Culture=neutral, PublicKeyToken=3750abcc3150b00c, processorArchitecture=MSIL" konnte nicht aufgelöst werden, da er eine indirekte Abhängigkeit von der Frameworkassembly "System.Data.Entity, Version=3.5.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" aufweist, die im derzeit als Ziel angegebenen Framework nicht aufgelöst werden konnte. ".NETFramework,Version=v2.0". Zur Beseitigung des Problems muss entweder der Verweis "FirebirdSql.Data.FirebirdClient, Version=2.1.0.0, Culture=neutral, PublicKeyToken=3750abcc3150b00c, processorArchitecture=MSIL" entfernt oder die Anwendung erneut als Ziel für eine Frameworkversion verwendet werden, die "System.Data.Entity, Version=3.5.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" enthält. FuhrparkServer

Hat jemand eine Idee wie ich das Problem beheben kann?

Drüber installiert habe ich übrigens die Zugriffskomponenten
FirebirdClient-2.0.1.exe und FirebirdClient-2.1.0.msi.

Das einzige was ich mir vorstellen kann ist, ich habe auf der gleichen Maschine
auch Firebird 2.5 installiert. Es ist also FB 1.5 und FB 2.5 auf der gleichen Maschine installiert und laufen unter einem unterschiedlichen Port und Instanzname einwandfrei parallel.

Gruß Kostas

09.09.2011 - 22:04 Uhr

Hallo Florian,

Der OR-Mapper von Telerik ist der von ehemals Vanatec aus München.
Ich weiß das dieser Lazy loading ungeschützt. Ob er jedoch das neue Lazy<T>
unterstützt weiß ich nicht. Da ich bis jetzt noch 0,nix Erfahrung mit OR-Mappern
und dessen Vorgehensweise habe, mögen meine Fragen für Euch sich anhören
wie aus einem anderen Stern. Dafür bitte ich um Vergebung.

Gruß Kostas

09.09.2011 - 12:43 Uhr

Ah, jetzt kommen wir der Sache schon näher.
Wenn Joins über PKs keine performance Probleme bereiten
ist das natürlich eine komplett andere Geschichte.
Ich habe nie performance tests durchgeführt. Ich bin immer schon davon
ausgegangen dass das so ist.

Wegen den Adressen, ich habe eine Tabelle Adressen in dieser alles
Adresstypen verwaltet werden. Unterschieden werden sie durch ein
Typenfeld 1=Kunde, 2=Lieferant u.s.w. Wenn z.B.: ein Kunde n Lieferadressen hat, wird
die Auflistung in einer separaten Tabelle geführt.

Gruß Kostas

09.09.2011 - 11:47 Uhr

Hallo FZelle,

der Grund warum ich das so aufteile würde ist, ich möchte aus der DB nur die
Informationen anfordern die ich gerade benötige. Wenn ich also nur die Adresse
benötige soll auch nur die Adresse von der DB angefordert werden und nicht
das komplette Kundentabelle. Das wäre von meiner Sicht her unnötiger trafic
und Belastung des DB-Servers.
Oder ist es so gemeint, die Adressklasse ist eine 1:1 Version der Tabelle. Auf der
Form binde ich nur die Adressfelder und fordere eine Adresse an. Was würde passieren,
werden alle Felder aus der Adresstabelle angefordert oder nur die die tatsächlich mit der
aktuellen Form gebunden sind? Wenn dem so ist, würde es bedeuten das so ein OR-Mapper
zur Laufzeit analysiert welche Daten benötigt werden und würde ein optimiertes Select statement
an die DB senden.

[Edit]
Da ich dieses Verhalten von einem OR-Mapper eher nicht erwarte,
würde das bedeuten dass mein DB-Model anders aussehen muss.
Man müsste die Tabelle Kunden in mehrere Tabellen aufteilen.
Wenn ich als Beispiel nur ein Bild pro Kunde hätte, müsste ich die Bilder
in einer neuen weiteren Tabelle KundenBilder ablegen damit sie nicht automatisch
mitgeladen werden. Das wiederum bedeutet mehr Joinings was eine
gewisse Leistungsbremse bedeutet.

Sorry das ich so anstrengend bin. :-|

Gruß kostas

08.09.2011 - 23:42 Uhr

Hallo FZelle,

danke für die Antwort.
Ich glaube ich habe das noch nicht richtig verstanden wie das gemeint ist.
Kannst du mir bitte anhand meines Beispiels mit einer Tabelle den Kunden kurz beschreiben wie man das richtig macht? Wie viele Klassen gibt es dafür
und welche ist für den User zum bearbeiten und welche Klasse für das persistieren zuständig.

[Edit]
Ich glaube ich bin jetzt dahintergekommen was du meinen könntest.
Es gibt ein File DBSchema.cs in diesem File sind 1:1 alle Tabellen
in Klassen abgebildet. Diese Klassen habe nur den Sinn das Schema
zu kontrollieren sonst nix.
Bezogen auf mein Beispiel habe ich eine oder gar zwei Klassen die auf
die gleiche Tabelle zugreifen und auch das persistieren, jede Klasse für
sich, übernehmen.
Diese Klassen kümmern sich überhaupt nicht um das Schema. Hauptsache
die Tabelle beinhaltet mindestens die Felder die in der Klasse angesprochen werden.

Ist das in etwa so?

Gruß Kostas

08.09.2011 - 23:22 Uhr

verwendetes Datenbanksystem: <SQL-Server>

Hallo Zusammen,

ich arbeite bis jetzt noch nicht mit OR-Mappern sondern direkt über ADO.NET.
Ich habe ein Set von Methoden die mir eine Liste<T> liefern und Methoden die die Daten
in die DB zurückschreiben. Alles kein Problem wenn es wenige Tabellen sind.
Für ein neues Projekt würde ich mich mit den OR-Mapper von ehemals Vanatec heute Telerik beschäftigen. Dabei drängt sich für mich eine Grundsatzfrage auf.

Ein OR-Mapper wie der OpenAccess ORM verwaltet die Struktur der Datenbank.
Das würde bedeuten dass ein 1:1 Abbild der Metadaten im Server auch in
den DAL Objekten herrscht, damit der OR-Mapper die Struktur anpassen kann.
Ich frage mich gerade wie kann ich dennoch zwei unterschiedliche editierbare result Objekte vorhalten?

Ein denkbares Scenario währe ein Verkäufer darf neue Kunden anlegen mit
der Minimalanforderung z.B.: die Adresse und Kommunikationsdaten.
Er darf jedoch nicht dem Kunden eine Preisliste vergeben und auch keine
Rabatte einräumen. Das dürfen nur autorisierte Bürokräfte.

Aktuell mache ich das so dass ich eine Form habe für die Verwaltung welche
über eine eigene Query sich die Daten aus der Kundentabelle zieht und bearbeitet.
Eine weitere Form für den Verkäufer die ebenfalls die Daten aus einer separaten
Query bekommt. Auch die ist problemlos editier bar.

Wenn ich das mit einem OR-Mapper versuchen würde, würde vermutlich
die Klasse mit den wenigeren Feldern zur Folge haben dass die nicht enthaltenen Felder aus der Tabelle entfernt werden. Das wird höchstwahrscheinlich nicht der Fall sein, was wiederum bedeuten würde dass
mit den DAL-Objekten nicht gearbeitet wird. Konkret also würde meine Kundenklasse nicht "einfach" um die Persistenz Technik des OR-Mappers erweitert, sondern es gibt eine weitere Kunden-Klasse mit exakt den gleichen
Feldern die auch in der Datenbank sind. Ist das in etwa so?

Gruß Kostas

05.09.2011 - 14:45 Uhr

Hallo Zusammen,

ich habe es jetzt üben die Klasse BackgroundWorker gemacht.
Der Timer stoppt sich selbst und startet danach den WorkerThread
per RunWorkerAsync();
Wenn der event RunWorkerCompleted gefeuert wird, wird der
der Timer wieder gestartet.

Die Implementierung war für mich am einfachsten und es scheint soweit
zu funktionieren. Zumindest habe ich beim Testen es nicht geschafft die
Implementierung ins schwanken zu bringen.

Dankeschön für die Hilfestellung.

Gruß Kostas

05.09.2011 - 11:44 Uhr

Hallo Zusammen,

ich habe auf der Form einen Timer welcher periodisch
diesen Thread erzeugt. Normalerweise ist der Thread fertig bevor
der Timer erneu zuschlägt. Theoretisch ist es jedoch möglich dass der Thread
immer noch läuft. Deshalb würde ich gerne abfragen
ob der Thread immer noch läuft. Wenn ja, soll der Timer
einfach eine Periode auslassen.

 Thread newThread =
            new Thread(new ThreadStart(CheckEmails));
            newThread.Start();

Hat jemand eine Idee?

Gruß Kostas

14.04.2011 - 16:07 Uhr

Hallo Zusammen,

kennt jemand eine Möglichkeit hauszufinden wie vielle Farben die Grafigkarte darstellen kann?

Gruß Kostas

04.11.2010 - 17:34 Uhr

Kann sehr gut sein dass in Ansi geschrieben wird. Falls es ansi
währe, wie bekomme ich das umconvertiert?

04.11.2010 - 16:13 Uhr

@Kostas:
Bitte hör mit dem Stringgefrickel auf, das gilt auch für SQLite.
>

Und wenn SqliteAdmin die Daten richtig lesen kann, stehen sie eigentlich nicht im richtigen Format drin.
Wie speicherst du denn die Daten da hinein.

Hallo FZelle,

die Daten werden über eine Delphi Windows Anwendung mit den Komponenten Zeos in die DB geschrieben.

[Edit]
Bezüglich Parameter, wenn du den Parameter in WHERE meinst, hast du recht
und das mache ich auch in der Regen auch. In diesem Fall habe ich etwas geschlampert.

Was mir garnicht gefällt ist eher das dr[1].ToString().
Gibt es dafür eine Elegantere Lösung?

Gruß Kostas

04.11.2010 - 16:09 Uhr

In der Tabelle Adressen sind Umlaute
In den Feldern Firmenname, Strasse und Ort

Wenn ich direkt beim auslesen der Daten das Feld dr[2].ToString()
abfrage, sehe ich den Firmenname. Wenn der Firmenname Umlaute enthält
werden für die Umlaute ander Zeichen angezeigt.

04.11.2010 - 14:16 Uhr

verwendetes Datenbanksystem: <SQLite V3>

Hallo Zusammen,

mein ConnectionString sieht so aus:

private static string connStrSql = @"Data Source=" + dbPath + @"\CRM.s3db; Version=3; UseUTF16Encoding=true";

und so lese ich die Daten aus der DB raus.
Leider werdne die Umlaute nicht richtig encoded obwohl UseUTF16Encoding
im connection String enthalten ist.
Wenn ich mit die Datenbank mit dem Tool sqliteadmin.exe ansehe,
sind die Umlaute enthalten.
Hat jemand eine Idee?


        public static BindingList<Adresse> GetFirmen(string suche)
        {
            Cursor.Current = Cursors.WaitCursor;
            try
            {
                //erzeuge eine neune Connection zu Datenbank
                using (SQLiteConnection connObj = new SQLiteConnection(ConnStrSql))
                {
                    try
                    {
                        //beliebiges SQL content 
                        string cmdText = @"SELECT AdressNr, Firmenname, Strasse, Ort, Telefon, Fax, Bezeichnung1, Bezeichnung2
                                         FROM Adressen";
                        if (suche != "")
                            cmdText += String.Format(" WHERE Firmenname like \"%{0}%\"", suche);

                        cmdText += " ORDER BY Firmenname";

                        //packe das SQL content in ein Command-Object
                        SQLiteCommand cmd = new SQLiteCommand(cmdText, connObj);

                        //DataReader zu auslesen von Daten erzeugen
                        SQLiteDataReader dr;

                        //Tabelle öffnen
                        connObj.Open();
                        dr = cmd.ExecuteReader(CommandBehavior.Default);

                        //neues temporäres Listen objekt orbereiten
                        BindingList<Adresse> listOfAdressen;

                        //das Listen objekt erzeugen
                        listOfAdressen = new BindingList<Adresse>();
                        //Das Listen-Objekt hat eigenschaften. Die Benutzer dürfen die Daten User-Objekte nicht verändern
                        listOfAdressen.AllowEdit = false;
                        listOfAdressen.AllowNew = false;
                        listOfAdressen.AllowRemove = false;
                        listOfAdressen.RaiseListChangedEvents = false;

                        //in einer Schleife alle Adressen aus der DB lesen
                        while (dr.Read())
                        {
                            //neues Adress Objekt anlegen und dem Konstruktor gleiche die Daten aus der DB übergeben.
                            //Als Ergebnis bekommt man ein "gefülltes" Adress Objekt welches wiederum per Add
                            //der Liste hinzugefügt wird.
                            utf8_encode

                            listOfAdressen.Add(new Adresse(int.Parse(dr[0].ToString()),
                                dr[1].ToString(),
                                dr[2].ToString(),
                                dr[3].ToString(),
                                dr[4].ToString(),
                                dr[5].ToString(),
                                dr[6].ToString(),
                                dr[7].ToString()));

                        }

                        dr.Close();

                        return (listOfAdressen);

                    }
                    catch (SQLiteException ex)
                    {
                        TriggerOnStatusEvent(ex.Message);
                        return null;
                    }
                }

            }
            finally
            {
                Cursor.Current = Cursors.Default;

            }
        }

10.09.2010 - 10:15 Uhr

Wie erzeugt man denn eine C-DLL für Windows CE mit einer X86 CPU (Cortex)
Geht das mit VS2008 oder benötigt man dafür andere Werkzeuge?

10.09.2010 - 09:50 Uhr

Ich habe natürlich die DLL selbst in das Programmverzeichnis kopiert,
auch beim DLL-Namen den Pfad mit angegeben. Die Meldung ist die gleiche.
Wenn ich die Dll lösche, kommt auch die gleiche Fehlermeldung.

Vermutlich passt etwas nicht mit der C-DLL.
Ist dir bekannt ob eine C-DLL für Windows CE anders kompiliert werden muss,
ich vermute das genau dass das Problem ist?

09.09.2010 - 20:51 Uhr

Hallo Zusammen,

aus einem Stück C-Code bestehend aus zwei kleinen Methoden wurde
mit VS2010 eine DLL erzeugt.
Die Dll kann nun von einem C# Projekt per DLLImport einwandfrei
auf dem PC! aufgerufen werden.

Die gleiche C-DLL läst sich unter Win CE nicht aufrufen. Es kommt die Fehlermeldung: Can't find PInvoke DLL "Backlight.dll"

[DllImport("Backlight.dll", EntryPoint = "BackLightOFF")]
public extern static void BackLightOFF(); 

Kann es sein dass ein VS Projekt für eine C-DLL anders aufgebaut sein
muss wenn es für ein Windows CE Device gedacht ist?

Gruß Kostas

07.09.2010 - 14:36 Uhr

Hallo Zusammen,

ich habe ein Win CE Device, dessen BackLight sich über die zwei Methoden Ein-/Ausschalten lässt. Leider gibt es dafür keine DLL die ich einfach in C#
einbinden kann. Ich habe von C++ leider überhaupt keine Ahnung. Ich es möglich
mit Vs2008 daraus eine DLL zu erzeugen die ich unter C# ausführen kann?

#include "stdafx.h"

unsigned char inportb(short addr)
{
  unsigned char cValue;
  _asm
  {
    mov dx, addr
    in  ax, dx
    mov cValue, al
  }

  return cValue;
}

void outpourtb(int addr, unsigned char val)
{
  __asm
  {
    push edx
    mov  edx, DWORD PTR addr
    mov  al,  BYTE PTR val
    out  dx,  al
    pop edx
  }
}

void BackLightON()
{
  // Set register 4AH bit1 to 0 to enable GPIOB
  outportb(0x3d4, 0x4a);
  unsigned c = inport(0x3d5) & 0xfd;
  outportb(0x3d4, 0x4a);
  outportb(0x3d5, c);
  // Set register 48H bit1
  outportb(0x3d4, 0x48);
  c = inport(0x3d5) | 0x02;
  outportb(0x3d4, 0x48);
  outportb(0x3d5, c);  
}

void BackLightOFF()
{
  // Set register 4AH bit1 to 0 to enable GPIOB
  outportb(0x3d4, 0x4a);
  unsigned c = inport(0x3d5) & 0xfd;
  outportb(0x3d4, 0x4a);
  outportb(0x3d5, c);
  // Clear register 48H bit1
  outportb(0x3d4, 0x48);
  c = inport(0x3d5) & 0xfd;
  outportb(0x3d4, 0x48);
  outportb(0x3d5, c);  
}

Gruß Kostas

05.09.2010 - 17:34 Uhr

naja, blockierend arbeitet dein Code nicht, sondern mit Polling. Kann man machen, aber mit SyncQueue hat das dann nichts mehr zu tun.

In meinem Fall, gibt es nur genau einen Producer und einen Consumer Thread.
Ist es dan in Ordung es so zu machen?
Was mit garnich gefällt ist Thread.Sleep(500);

Gruß Kostas

05.09.2010 - 16:00 Uhr

Hallo Zusammen,

ich habe es mal so versucht, indem ich
Dequeue und DoWorkAsync wie folgt abgeändert habe.
In meinem Fall, gibt es nur genau einen Producer und einen Consumer Thread.

Kann ich das so lassen?
Gruß Kostas

        public T Dequeue()
        {
            lock (this)
            {
//                while (_q.Count == 0)
                {
                    Debug.WriteLine(Thread.CurrentThread.Name + " Wait");
                    //Monitor.Wait(this);
                }
                Debug.WriteLine(String.Format("{0} Dequeue ==> {1}", Thread.CurrentThread.Name, (_q.Count - 1)));
                return _q.Dequeue();
            }
        }
        public void DoWorkAsync()
        {
            _exit = false;
            // Ab .net 4.0 besser Task.Factory.StartNew verwenden.
            ThreadPool.QueueUserWorkItem(_ =>
            {
                while (!_exit)
                {
                    try
                    {
                        if (ThreadHelper._queue.Count() > 0)
                        {
                            string aLine = ThreadHelper._queue.Dequeue();

                                    this.Progress.Fire(this, new ProgressEventArgs(aLine));
                            }
                        }
                        else Thread.Sleep(500);

                    }
                    catch (Exception ex)
                    {

                        this.Error.Fire(this, new ErrorEventArgs(ex.Message);
                    }


                }

                this.Finished.Fire(this);
            });

        }
05.09.2010 - 09:55 Uhr

Hallo herbivore,

ich würde gerne die SyncQueue<T> verwenden.
Doch leider gibt es Monitor.Pulse und Monitor.Wait nicht im CF.

Hast du eine Idee?

05.09.2010 - 09:42 Uhr

Hallo herbivore,

natürlich hast du recht. In OnClosing wird ja StopWorking bereits ausgeführt.
Das ist mir komplett entfallen.

Ich sehe du liest immer noch mit. 😃 Ich werde als nächstes die "Verarbeitungsklasse" in ein Thread nach dem gleichen Prinzip einkapseln.
Vermutlich werde ich Schwierigkeiten haben mit dem einbinden von Deiner
SyncQueue <T> um die Daten von einem Thread in den anderen zu übertragen.
Schöne Grüße.
Kostas

05.09.2010 - 00:15 Uhr

Hallo,

ich habe alles eingebaut. Solange keine Serielle Daten fliesen, funktioniert das beenden der App einwandfrei. Anders, wenn Daten empfangen werden und
die Close Methode ausgeführt wird, bekomme ich eine Exception ObjectDisposedException.

Ich vermute das noch nicht alle _readWorker.Progress Events abgearbeitet wurden, da aus dem ComPort ja relativ viele Daten empfangen werden, die über
die Progress auf die Form gesendet werden.
Das sind übrigens GPS Daten 57600,N,8,1. Ich hoffe das ich schon mal erwähnt hätte dass es sich um eine Win CE 1GHz X86 Proz Hardware handelt. Die Verarbeitung schafft das Gerät spielend.

Hast du eine Idee?

        private void ibClose_Click(object sender, EventArgs e)
        {
            _readWorker.StopWorking();
            this.Close();
        }
...
 _readWorker.Finished += (s, e) =>
            {
                Action action = () =>
                {
                    this._isReadWorkerFinished = true;
                    this.Close();
                };

                this.Invoke(action); <<ObjectDisposedException wurde nicht behandelt
            };
...
03.09.2010 - 23:38 Uhr

Hallo,

jetzt drängt sich noch eine Frage auf.
Auf dem Form hab ich eine Textbox in dieser jetzt alle Seriellen Daten geloggt werden. Es gibt noch eine zweite Klasse innerhalb der Anwendung die die Daten benötigt. Diese Klasse filtert nur bestimmte Datenpakete und verarbeitet sie.

Die Frage nun, sollte die zweite Klasse einen weiteren Anonymen Delegaten
(_worker.Progress) registrieren um an die Daten ran zu kommen,
oder sollte ich lieber von der MainForm innerhalb des _worker.Progress
eine Methode der zweiten Klasse aufrufen und das Datenpaket übergeben?

Ich vermute eher einen weitere Delegaten registrieren.
Dann müsste ich den _worker; umbauen als Public Property.

 _worker.Progress += (s, e) =>
            {
                Action action = () => this.Text = e.Progress.ToString();
                this.BeginInvoke(action);
            };

Gruß Kostas

03.09.2010 - 22:48 Uhr

Ich meinte eigentlich ein Bereich mit code snippet mit dem Titel Threading Muster.

03.09.2010 - 22:30 Uhr

Hallo,

ja das ist natürlich eine völlig andere Liga. Da bin ich leider Lichtjahre
davon entfern. Ich habe es in mein Projekt einbauen können und es
funktioniert einwandfrei.

Tausend Danke dafür. Ich habe bis jetzt um Threads einen großen Bogen gemacht.
Dieses Muster werde ich nun auch in anderen Projekten einsetzen. Du hast dich bei mir
somit verewigt. 😃

Gruß Kostas
P.S. dieses Muster sollte man im Forum irgend wie zugänglich machen. Ich bin sicher, es gibt noch mehr die das nicht wissen oder gut einsetzen können.

03.09.2010 - 18:18 Uhr

Hi,

ich habe jetzt ThreadLeseschleife public gemacht und CloseComPort()
so abgeändert. Es ist so das Join nicht fertig wird.

Hast du noch ein Hinweis?

        
        private void CloseComPort()
        {
            _serialCom.ThreadAbbrechen = true;
            _serialCom.ThreadLeseschleife.Abort();
            //this.SerPort.Close();
            _serialCom.ThreadLeseschleife.Join();


            //this.SerPort.Close();
            _serialCom.LineReaded -= _serialCom_LineReaded;
            _serialCom.Error -= _serialCom_Error;
        }

        private void Leseschleife()
        {
            while (!ThreadAbbrechen)
            {
                try
                {
                    // Zeile einlesen (blockiert den Thread, wenn keine Zeichen empfangen werden)
                    string aLine = _comPort.ReadLine();
                    OnLineReaded(aLine + Environment.NewLine);
                }
                catch (Exception ex)
                {
                    // Bei Problemen mit der seriellen Schnittstelle erneut versuchen
                    OnError("Leseschleife " + ex.Message);
                }
            }
        }


03.09.2010 - 16:01 Uhr

Hi,

vermutlich hast du recht.

Wenn ich ibClose_Click aufrufe, knalts.
Wenn ich jedoch CloseComPort() auf ein andern button
lege und vor dem CloseButton betätige, funkt alles einwandfrei.

Ich müsste eigentlich warten bis die Methode CloseComPort()
komplett fertig ist.
Weiter unten hab ich auch meine Leseschleife angehängt und wie der Thread
erzeugt wird.

Hast du eine Idee?

        private void ibClose_Click(object sender, EventArgs e)
        {
            CloseComPort();

            this.Close();
        }



        private void CloseComPort()
        {
            this.SerPort.Close();
            _serialCom.ThreadAbbrechen = true;
            _serialCom.LineReaded -= _serialCom_LineReaded;
            _serialCom.Error -= _serialCom_Error;
        }

        private void Leseschleife()
        {
            try
            {
                while (!_threadAbbrechen)
                {
                    try
                    {
                        // Zeile einlesen (blockiert den Thread, wenn keine Zeichen empfangen werden)
                        string aLine = _comPort.ReadLine();
                        OnLineReaded(aLine + Environment.NewLine);
                    }
                    catch (Exception ex)
                    {
                        // Bei Problemen mit der seriellen Schnittstelle erneut versuchen
                        OnError("Leseschleife " + ex.Message);
                    }
                }
            }
            finally
            {
                _threadLeseschleife.Join();
                _comPort.Close();
            }


        }


...
             //Thread aufbau.
            _threadLeseschleife = new Thread(new ThreadStart(Leseschleife));
            _threadLeseschleife.IsBackground = true;
            _threadLeseschleife.Name = "Leseschleife";
            _threadLeseschleife.Start();

...


03.09.2010 - 15:15 Uhr

Hallo Zusammen,

in einer Anwendung habe ich ein Thread welcher Daten aus der RS232 einliest
per ReadLine und danach ein Event feuert um den String in eine TextBox
darzustellen.
Da der Zugriff auf die TextBox über eini weiteren Thread nicht möglich ist,
wird im Eventheandler die Methode AddStringToTextBox aufgerufen.
Die String werden einwandfrei angezeigt.

Wenn ich nun die App per Close() beenden möchte, bekomme ich eine ObjectDisposeException. Wie kann ich das bitte umgehen?
Ich müsste also innerhalb der Methode abfragen ob die Form in Dispose Mode ist.

        private static void AddStringToTextBox(string data, TextBox tb)
        {
            if (tb.InvokeRequired)
            {

                tb.Invoke((EventHandler)delegate  <<< hier der Fehler
                {
                    if (tb.Text.Length > 2000)
                    {
                        tb.Text = data + Environment.NewLine;
                    }
                    else
                    {
                        tb.Text = data + Environment.NewLine + tb.Text;
                    }
                });
            }
            else
            {
                if (tb.Text.Length > 2000)
                {
                    tb.Text = data + Environment.NewLine;
                }
                else
                {
                    tb.Text = data + Environment.NewLine + tb.Text;
                }
            }
        }

Gruß Kostas

02.09.2010 - 17:28 Uhr
  
  
Aber enn du doch typisiert Arbeiten willst, warum dann DataTable/DataSet?  
Das jetzt ständig hin und her zu verfrachten macht nicht wirklich Sinn.  
  
Mit einem der vielen ORMapper bräuchtest du da fast nix machen.  
  
In meinem Projekt habe ich genau zwei Tabellen und in jeder Tabelle 0 bis maximal 10 Datensätze die nur Angezeigt und nicht editiert werden.  
  
Das was ich jetzt habe reicht schon völlig aus. DataRowView funkt auch beste sahne.  
  
Aktuell habe ich mit Umlauten und double zu kämpfen. Vermutlich muss ich nur eine Culture irgend wie dem XML übergeben. Die Felder werde flasch convertiert.
02.09.2010 - 14:21 Uhr

Hallo FZelle,

bitte noch eine kleine Frage.

das Objekt antworten repräsentiert die Datenmenge und ist gebunden
mit einem Grid. Der Datensatzzeiger zeigt also immer auf den aktuelle
Datensatz. Ich muss nun relativ Häufig auf antwort.Platz zugreifen.
Aktuell hole ich mir per GetAntwort das Antwort-Objekt. Funktionieren tut es schon,
ist jedoch nicht optimal. Ich könnte sicherlich den Wert in einer Variable zwischenspeichern. Am besten würde mit gefallen wenn ich direkt auf
BindingSource antworten zugreifen könnten um danach auf den Feldinhalt zuzugreifen.

Ist dir eine Möglichkeit bekannt?

 antworten = new BindingSource(dal.MyDS, "Antworten");
        public Antwort GetAntwort(int index)
        {
            if (index < 0) return null;
            DataTable tbl = myDS.Tables["Antworten"];
            DataRow row = tbl.Rows[index];
            Antwort antwort = new Antwort();

            antwort.Platz = int.Parse(row["Platz"].ToString());
            antwort.Antworttext = row["Antwort"].ToString();

            return antwort;
        }
01.09.2010 - 15:22 Uhr

Beim schreiben kannst du doch angeben, das Du das Schema mit schreiben willst.

ist ja wie Weihnachten, hatte den Parameter komplett übersehen.
Funkt beste Sahne.
Ein herzliches Dankeschön FZelle.

01.09.2010 - 13:10 Uhr

Super Danke,

wenn ich in einer Tabelle Columns hinzufüge jedoch kein Rows wird im XML
File die Tabelle nicht angelegt, erst mit der ersten Row sehe ich das im XML.
Das gleiche ist auch wenn ich nachtäglich alle Rows einer Tabelle lösche,
wird die Tabelle mit gelöscht. Das ist schade da ich bei jedem Insert immer
zuerst prüfen muss ob die Tabelle vorhanden ist.

Gibt es keine andere Möglichkeit das die Struktur komplett erhalten bleibt?

Gruß Kostas

01.09.2010 - 12:03 Uhr

Hallo FZelle,

nur rein Informativ, ich benötige es nicht für mein Projekt.
Kann ich in dem DataSet per SQL zugreifen, also Insert, Delete, Update und Select?

Aktuell füge ich so neue Datensätze in der Tabelle.

   public void InsertAntwort(Antwort antwort)
        {
            DataTable tbl = myDS.Tables["Antworten"];
            int maxID=0;

            foreach (DataRow row1 in tbl.Rows)
            {
                
                maxID = System.Math.Max(maxID,int.Parse(row1["ID"].ToString()));
            }

            DataRow row = tbl.NewRow();
            row["ID"] = maxID;
            row["Platz"] = antwort.Platz;
            row["Antwort"] = antwort.Antworttext;
            tbl.Rows.Add(row);
        }

Gruß Kostas

30.08.2010 - 11:24 Uhr

Bitte vergiss den BindingContext, den hat man in FW 1.1 benutzt.

BindingSource ist seit 2.0 vorhanden und viel besser zu benutzen.

  
BindingSource binder = new BindingSource(data.MyDS,"antworten");  
binder.AllowRemove = true; << ist Schreibgeschützt  
binder.AllowEdit = true;  
binder.AllowNew = true;  
binder.Sort = "Platz";  
  
dataGridView1.DataSource = binder;  
  

Hallo FZelle,
Ich kann dem binder Objekt nicht zuweisen, es ist Schreibgeschützt.
Hast du eine Idee?

30.08.2010 - 10:31 Uhr

Super das du auch mich aufpasst.

Werde ich gleich umsetzen.
Dankeschön.

29.08.2010 - 21:10 Uhr

ja ganau.

Zum testen habe ich auch gleich zwei Datensätze eingefügt.
Die sehe ich auch im XML-File. Im Grid sehe ich sie allerdings nicht.
Das Grid habe eich so gebunden. (Habe ich auch der Hilfe)
Kannst du erkennen was fehl und die Datensätze anzuzeigen?
Die Colums sehe ich übrigens.

antwortenView.Table = data.MyDS.Tables["antworten"];
            antwortenView.AllowDelete = true;
            antwortenView.AllowEdit = true;
            antwortenView.AllowNew = true;
            //antwortenView.RowFilter = "";
            antwortenView.RowStateFilter = DataViewRowState.ModifiedCurrent;
            antwortenView.Sort = "Platz";

            dataGridView1.DataSource = antwortenView;

[Edit]
habs gefunden. Ich muss noch ein CurrenyManger verwenden.
So gehts:

cm = (CurrencyManager)this.BindingContext[data.MyDS, "Antworten"];
            antwortenView = (DataView)cm.List;

            // Simple-bind to a TextBox control
            //textBox1.DataBindings.Add("Text", antwortenView, "ID");

            dataGridView1.DataSource = antwortenView;

Gruß Kostas

29.08.2010 - 20:29 Uhr

(:-) gerade wollte ich genau das fragen.){gray}

29.08.2010 - 20:03 Uhr

verwendetes Datenbanksystem: XML

ich möchte per code ein Dataset mit genau zwei Tabelle erzeugen.
Die Datensätze wärden zu einem Späteren Zeitpunkt hinzugefügt.
Aktuell habe ich das Problem wenn ich ein Column vom Typ Integer hinzufügen möchte, bekomme ich zur Laufzeit einen Fehler not null exception.

Hat jemand eine Idee wie ich das umgehen kann?

public static void CreateDatenbank(string dbName)
    {
        using (DataSet ds = new DataSet("Datenbank"))
        {
            
            using (DataTable dt = ds.Tables.Add("Antworten"))
            {
                dt.Columns.Add("ID", System.Type.GetType("System.Integer")); <<<hier kommt die exception darf nicht null sein.
                dt.Columns.Add("Platz", System.Type.GetType("System.Integer"));
                dt.Columns.Add("Antwort", System.Type.GetType("System.String"));
            }

            ds.WriteXml(dbName);

        }

    }

Gruß Kostas

06.08.2010 - 13:23 Uhr

Hallo,

ich glaube ich hat das was nicht ganz verstanden.
Über den Designer habe ich ein DataSet "antworten.xsd"
mit genau einer Tabelle "antworten" und zwei Felder
antwortID und antwort angelegt. Beim WriteXml hätte ich
erwartet dass im XML File die Feldstruktur enthalten ist.
Dem ist nicht so. Ich muss also per Code die Felder einfügen.
Wen dem so ist, wazu kann ich überhaupt die Tabnellen und Felder im
Designer anlegen?


            string path = System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().GetName().CodeBase);

            antwortenTable = new DataTable("antworten");

            antwortenTable.ReadXmlSchema(path + "\\antworten.xsd");
            antwortenTable.WriteXml(path + "\\antworten.xml");
//            antwortenTable.ReadXml(path + "\\antworten.xml");


            antwortenView = new DataView(antwortenTable, "", "antwortID", DataViewRowState.CurrentRows);

Gruß Kostas

06.08.2010 - 09:59 Uhr

verwendetes Datenbanksystem: XML

Hallo Zusammen,

ich benötige ein DataSet mit zwei Tabellen welches sehr wenig Datensätze
verwalten. Bis jetzt habe ich SQLite verwendet, ist für ein CF-Projekt.

Über den XSD Designer habe ich das Schema erzeugt. Nun suche ich nach
einer Möglichkeit daraus ein XML zu erzeugen. Ich finde immer nur den
umgekehrten Weg aus einer XML-Datei mittels XSD.exe ein XSD zu erzeugen.
Es geht doch sicherlich auch anders herum oder muss ich das XML File
immer selbst erzeugen?

Im Designer ist es möglich ein TableAdapter anzulegen. Doch leider habe ich hier nur die Auswahl einer SQL-Datenbank und nicht ein XML-File.
Wie wird bitte die Verbindung zum XML-File hergestellt?

Ist euch ein Tutorial dafür bekannt?

Gruß Kostas

03.08.2010 - 21:58 Uhr

Hallo FZelle, schon sehr lange nicht voneinander gehört. Ich hoffe es geht dir soweit gut.

Oh je, das wollte ich jetzt nun wirklich nicht hören "lesen". 😦
Mal sehen was ich mir noch für Ärger eingehandelt habe mit dem Misst Device.

Schöne Grüße aus Griechenland. 😃

Gruß Kostas

03.08.2010 - 20:29 Uhr

Hallo,

Bein herstellen der Verbindung bekomme ich die Fehlermeldung: Can´t find PInvoke DLL "SQLite.Interop.DLL"

Die Dll mit diesem Namen gibt es nicht unter CompactFramework
Ich weiß nicht wies bei früheren Releases war, aber im aktuellen befindet sich sehr wohl ne Interop Dll im CompactFramework Verzeichnis.

Ich habe in dem Verzeichnis die Files:
C:\Program Files (x86)\SQLite.NET\bin\CompactFramework
SQLite.Interop.066.DLL
SQLite.Interop.066.lib
System.Data.SQLite.dll
testce.exe

und unter
C:\Program Files (x86)\SQLite.NET\bin
System.Data.SQLite.dll
System.Data.SQLite.lib
System.Data.SQLite.Linq.dll
System.Data.SQLite.XML
test.exe
Test.db3
test.exe.config

Die Anwendung testce funktioniert auf dem Device nicht, ebenso
nicht die Anwendung Test. Die Test.exe auf dem PC funktioniert jedoch
einwandfrei.

Gruß Kostas

03.08.2010 - 19:51 Uhr

Pack die DLL mal in den gleichen Ordner wie die EXE selber ?

Ja das habe ich schon so gemacht.
Zunächst einmal würde mich eine zuverlässige Aussage interessieren
ob die aktuelle SQLite Version auf ein Win CE X86 Platform funktioniert.
Wie gesagt, auf ein PDA mit Win Mobile 6.5 auf einer ARM Platform kein
Problem.

Ich verwende übrigens den SQLite Data Provider

ADO.NET 2.0/3.5 SQLite Data Provider
Version 1.0.66.0 April 18, 2010
Using SQLite 3.6.23.1
http://sqlite.phxsoftware.com

Gruß Kostas

03.08.2010 - 18:53 Uhr

Hi,

ich glaube das ist nicht das gleiche. Das Betriebssystem ist WinCE 6.0
und nicht Xp Embedded oder so. Bein herstellen der Verbindung bekomme ich die Fehlermeldung: Can´t find PInvoke DLL "SQLite.Interop.DLL"

Die Dll mit diesem Namen gibt es nicht unter CompactFramework

Ich habe zuerst die Dlls vom Verzeichnis:
C:\Program Files (x86)\SQLite.NET\bin\CompactFramework
auf das Device kopiert.
Danach auch die DLLs von C:\Program Files (x86)\SQLite.NET\bin

es funktioniert einfach nicht.

Gruß Kostas

03.08.2010 - 18:08 Uhr

Hallo Zusamme,

ich habe eine Anwendung geschrieben die SQLite verwendet.
Auf ein PDA mit Mobile 6 und mit ARM Plattform funktioniert SQLite
einwandfrei. Die gleiche Anwendung auf ein Win Ce 6.0 mit Vortex86DX CPU scheint nicht zu funktionieren. Kann es sein dass SQLite die x86 Platform nicht unterstützt?

Auf der Website kann ich nicht erkennen welche Plattformen unterstützt werden.

Gruß Kostas

06.10.2009 - 10:35 Uhr

Hallo Zusammen,

ich möchte den Event OnPropertyChanged feuern. Dazu benötige ich dne Namen
des Propertys als Argument. Aktuell übergebe ich dne Namen als Text.
Gibt es eine Möglichkeit den Namen abzufragen und ihn zu übergeben?

    public string KurzText
        {
            get { return (this._KurzText != null) ? this._KurzText.Trim() : string.Empty; }
            set
            {
                if (value != this._KurzText)
                {
                    if (this.OnPropertyChanged("KurzText", value, this._KurzText))
                        this._KurzText = value;
                }
            }
        } // end public string KurzText

Gruß Kostas

03.09.2009 - 17:52 Uhr

Hi Ron,

ja ich über lege ob ich das machen soll.
Es sind insgesamt 113 Klasse.

Mal sehen was geht.

Dankeschön,

Gruß Kostas