Feedback

ini Datei anlegen – mit Dictionary

// WICHTIG - zusätzlich diese Namespaces einbinden  - wenn noch noetig
// using System.Collections;
// using System.Collections.Generic;
// using System.IO;
// using System.Xml;
// using System.Xml.Linq;
// using System.Linq;
// using System.Text;
// using System.Runtime.InteropServices; 
// -------------------------------------------------



#region cIniFile - ini-datei lesen,schreiben...
    /// <summary> Domumentation der Klasse -            by A.Roters - Freeware - 2010
    /// 
    /// Diese Klasse kann eine sog. ini-Datei anlegen bzw. bearbeiten ( in ascii und xml-Format )
    ///
    /// Zwei Möglichkeiten stehen zur Verfügung: 
    /// 1. direktes schreiben in iniDatei  und/oder
    /// 2. über eine eigens geschriebene kleine Dictionary-Class !!!!!
    /// 
    /// 
    /// // ------------------------------------------------------------------------------------------------------
    /// Erklärung zum Dictionary   DIC-NAME:  myInifileInstanz.my_DIC.INI_Dictionary
    /// ------------------------
    /// Der sog. MASTERKey setzt sich im Dictionary aus  SECTIONNAME+subKEY zusammen.
    /// Value => (ist der Wert hinter dem  =-Zeichen des subKeys)
    /// Die Klasse splittet diese dann wieder auseinander       ( Key   ,  value  )
    /// Def.: Dictionary<string[2],string>( (s[0]="Section",s[1]="Key") , "value" )
    ///                                   (           MASTERKey         ,  value  )
    /// // -------------------------------------------------------------------------------------------------------
    /// 
    /// Dateiname: myDateiName.ini oder myDateiName.xml
    /// 
    /// Format Beispiel:
    /// ----------------
    /// ini-Datei (schreiben und lesen)
    /// ------------
    /// [mySektion1]         -> SECTION s[0]
    /// my_key1=value1       -> my_key1 s[1]  -> s[0]+s[1] diese beiden Werte sind im Dictionary der sog. MasterKEY     
    /// my_keyN=value2                           (hinter dem =-Zeichen steht dann value)                               
    /// [mySection2]
    /// my_key=value      
    /// 
    /// 
    /// und als xml-Datei (nur schreiben)
    /// -----------------
    /// <?xml version="1.0" encoding="utf-8" ?> 
    /// - <TESTINI_DATEN_ROOT_NAME>
    ///  - <mySektion1>
    ///    <my_key1>value1</my_key1> 
    ///    <my_keyN>value2</my_keN1> 
    ///  </mySektion1>
    ///  - <mySection2>
    ///    <my_key>value</my_key> 
    ///  </mySection2>
    /// </TESTINI_DATEN_ROOT_NAME>
    /// 
    /// 
    /// 
    /// WICHTIG - zusätzlich diese usings einbinden  - wenn noetig
    /// ----------------------------------------------------------
    /// using System.Collections;
    /// using System.Collections.Generic;
    /// using System.IO;
    /// using System.Xml;
    /// using System.Xml.Linq;
    /// using System.Linq;
    /// using System.Text;
    /// using System.Runtime.InteropServices;
    /// 
    /// -------------------------------------------------------------------------------------------------------------
    ///
    /// Alle Funktionen:
    /// ----------------
    /// - . instanzieren - IMMMER !!!!! 
    /// - cInifile myInifile = new cIniFile("c:meineIniDatei", OPEN_INI_MOD_.NEW);       // neuanlage iniDatei
    /// - cInifile myInifile = new cIniFile("c:meineIniDatei", OPEN_INI_MOD_.READWRITE); // neuanlage oder bearbeiten
    /// 
    /// - . iniDatei direkt beschreiben und Values lesen - diese zwei Funktionen schreiben/lesen direkt aus/in die iniDatei !!!!! 
    /// - myInifile.IniWriteValue("SECTION1" , "KEY1_1" , "value1a");     // den Eintrag direkt in iniDatei schreiben
    /// - string myValue = myInifile.IniReadValue("SECTION1" , "KEY1_1"); // Value direkt aus iniDatei lesen/holen 
    /// 
    /// - . Dictionary  - myInifile.myDIC. - einlesen aus iniDatei in Dic. und schreiben von Dic. in iniDatei  
    /// - myInifile.IniReadAll_fromFile_intoDictionary("" , cIniFile.INI_READ_MOD_.ALL_SECTIONS); // eine iniDatei in Dic. einlesen
    /// - myInifile.IniWriteAll_FromDictionary_IntoFile();   // das Dictionary in iniDatei schreiben; die iniDatei wird dabei neu erstellt
    /// 
    /// - . Dictionary - vier Funktionen zum Arbeiten - myInifile.myDIC.
    /// - myInifile.my_DIC.myAdd("SECTION_1" , "Key1" , "value"); // den Eintrag ins Dictionary schreiben; wenn nicht bereits vorhanden
    /// - myInifile.my_DIC.myRemove("SECTION_1" , "Key2");        // den Eintrag aus Dictionary loeschen; wenn vorhanden
    /// - string myValue=myInifile.my_DIC.myGetValue("SECTION_2" , "Key1"); // Value des Eintrags holen; wenn vorhanden
    /// - myInifile.my_DIC.mySetValue("SECTION_2" , "Key1","newValue");     // Value des Eintrags neu setzen; wenn Eintrag vorhanden  
    ///
    /// - 5. Zusatzfunktion - schreiben iniDatei in xmlDatei
    /// - myInifile.IniWriteAll__IntoXmlFile( @"TESTINI_DATEN_ROOT"); // schreiben in xmlDatei 
    /// - string[] liste=myInifile.IniReadAll(); // alles iniDatei_Zeilen lesen und als String-Array speichern
    /// 
    /// - 6. WICHTIG - zusätzlich diese Namespaces einbinden  - wenn noch noetig
    /// using System.Collections;
    /// using System.Collections.Generic;
    /// using System.IO;
    /// using System.Xml;
    /// using System.Xml.Linq;
    /// using System.Linq;
    /// using System.Text;
    /// using System.Runtime.InteropServices;
    /// 
    /// 
    /// - 7. zusätzlich diese VERWEISE einbinden - wenn noetig
    /// System.Xml;
    /// System.Xml.Linq;
    /// 
    /// // --------------------------------------------------------------------------------------------------------
    /// 
    /// Beispiele:
    /// ----------
    /// 
    /// //1. Möglichkeit - nur zwei eingeschränkte Funktionalität - Daten werden direkt in ini-Datei geschrieben oder ein value kann ausgelesen werden
    /// ---------------------
    /// // Instanz - IMMER ( natuerlich nur einmal pro iniDatei ) !!!!!
    /// cInifile myInifile = new cIniFile("c:meineIniDatei", OPEN_INI_MOD_.NEW);         // neue iniDatei anlegen; eine schon vorhandene iniDatei wird vorher geloescht
    /// //oder alternativ 
    /// //cInifile myInifile = new cIniFile("c:meineIniDatei", OPEN_INI_MOD_.READWRITE); // neue oder vorhandene iniDatei bearneiten; die vorhandene iniDatei wird weiter bearbeitet oder eine neue angelegt !!!
    /// 
    /// myInifile.IniWriteValue("SECTION1" , "KEY1_1" , "value1a"); // neuen Eintrag direkt in die iniDatei schreiben; wenn nicht schon vorhanden
    /// myInifile.IniWriteValue("SECTION1" , "KEY1_2" , "value1b"); // dito
    /// myInifile.IniWriteValue("SECTION2" , "KEY2_1" , "value1a"); // dito  usw...
    /// string myValueFromSectionKey=myInifile.IniReadValue("SECTION1" , "KEY1_2");  // Beispiel fuer einlesen eines Value direkt aus inidatei 
    /// 
    /// // Sonderfunktion - nur wenn eine iniDatei schon vorher angelegt wurden;  sprich vorhanden ist dann
    /// myInifile.IniReadAll_fromFile_intoDictionary("" , cIniFile.INI_READ_MOD_.ALL_SECTIONS); // aus einer iniDatei alles einlesen und in Dictionary schreiben !!!!!
    /// // oder alternativ  nur eine bestimmte Section komplett einlesen mit
    /// //myInifile.IniReadAll_fromFile_intoDictionary("SECTION1" , cIniFile.INI_READ_MOD_.ONLY_ONE_SECTION);
    /// 
    /// 
    /// // -------------------------------------------------------------------------------------------
    /// // ... jetzt kann z.B. mit 2.Möglichkeit das Dictionary bearbeitet werden und dieses dann zum 
    /// // Schluss wieder in einem Rutsch in die ini-Datei geschrieben werden !!!!! 
    /// // -------------------------------------------------------------------------------------------
    /// 
    /// 
    /// //2.Möglichkeit - viel umfangreicher -  mit Hilfe von Dictionary !!!
    /// //----------------------
    /// // Instanz - IMMER ( natuerlich nur einmal pro iniDatei ) !!!!!
    /// cInifile myInifile = new cIniFile("c:meineIniDatei", OPEN_INI_MOD_.NEW);         // neue iniDatei anlegen; die vorhandene iniDatei wird vorher geloescht
    /// //oder alternativ
    /// //cInifile myInifile = new cIniFile("c:meineIniDatei", OPEN_INI_MOD_.READWRITE); // neue oder vorhandene iniDatei bearneiten; die vorhandene iniDatei kann weiter bearbeitet werden oder eine neue iniDatei wird angelegt !!!
    ///
    /// // Sonderfunktion - nur wenn eine iniDatei schon vorher angelegt wurden;  sprich vorhanden ist dann
    /// myInifile.IniReadAll_fromFile_intoDictionary("" , cIniFile.INI_READ_MOD_.ALL_SECTIONS); // aus einer vorhandenen iniDatei alles lesen und in Dictionary schreiben !!!!!
    ///
    /// // jetzt weiter arbeiten... 
    /// myInifile.my_DIC.myAdd("SECTION_1" , "Key1" , "value"); // neuen Eintrag direkt ins Dictionatry schreiben ; Achtung es wird nicht direkt in die ini-Datei geschrieben !!!!!
    /// myInifile.my_DIC.myAdd("SECTION_1" , "Key2" , "value"); // dito
    /// myInifile.my_DIC.myAdd("SECTION_2" , "Key1" , "value"); // dito
    /// myInifile.my_DIC.myAdd("SECTION_2" , "Key2" , "value"); // dito 
    /// 
    /// myInifile.my_DIC.myRemove("SECTION_1" , "Key2");                  // Beispiel fuer loeschen  Section/Key  in Dic. 
    /// myInifile.my_DIC.mySetValue("SECTION_2" , "Key1","neyValue");     // Beispiel fuer aender Value eines Section/Keys in Dic.
    /// string myValue=myInifile.my_DIC.myGetValue("SECTION_2" , "Key1"); // Beispiel fuer lesen Value eines Section/Keys in Dic.
    /// 
    /// // WICHTIG - zum Schluss - jetzt erst das Dic. in ini-Datei schreiben !!!!!  WICHTIG !!!!!!
    /// myInifile.IniWriteAll_FromDictionary_IntoFile();                  // jetzt das komplette Dic. in ini-Datei schreiben
    ///
    /// // --------------------------------------------------------------------------------------------------------
    /// 
    /// Zusammenfassung:
    /// ----------------
    /// Man kann natürlich Möglichkeit1 und Möglichkeit2 miteinander wunderbar kombinieren.
    /// -  mit Möglichkeit1  -die Datei schnell aufbauen und dann mit
    /// -  Möglichkeit2      -diese bearbeiten/auslesen und wieder wegschreiben.
    /// 
    /// // ---------------------------------------------------------------------------------------------------------
    /// 
    /// Natürlich ist es auch nur mit dieser 2.Möglichkeit ohne weiteres machbar eine 
    /// iniDatei anzulegen/bearbeiten (ohne Möglichkeit 1)
    /// -----------------------------------------------------------------------------
    /// Beispiel:
    /// ---------
    /// // Instanz - IMMER ( natuerlich nur einmal pro iniDatei) !!!!!
    /// cInifile myInifile = new cIniFile("c:meineIniDatei", OPEN_INI_MOD_.READWRITE); // oder OPEN_INI_MOD_.NEW ;  oeffnen oder anlegen iniDatei
    /// // nur wenn iniDatei vorhanden ist, diese dann mit der folgenden Funktion komplett einlesen ....
    /// // myInifile.IniReadAll_fromFile_intoDictionary("" , cIniFile.INI_READ_MOD_.ALL_SECTIONS); // iniDatei in Dic. laden
    ///
    /// // .....und nun mit myADD/myGETValue/mySETValue/myRemove  aus  cDic-Klasse  die iniDatei bzw. Dic. bearbeiten 
    /// myInifile.my_DIC.myAdd("SECTION_1" , "Key1" , "value");
    /// myInifile.my_DIC.myAdd("SECTION_1" , "Key2" , "value");
    /// myInifile.my_DIC.myAdd("SECTION_2" , "Key1" , "value");
    /// 
    /// // usw.... siehe funktionsbeschreibung weiter oben 
    /// 
    /// // WICHTIG !!!! - und dann zum Schluss alles in die iniDatei zurückschreiben !!!!!! WICHTIG !!!!!
    /// myInifile.IniWriteAll_FromDictionary_IntoFile();  
    /// 
    ///  
    /// // ---------------------------------------------------------------------------------------------------------
    /// 
    /// So jetzt noch zwei Zusatz-Funktion:
    /// -----------------------------------
    /// - myInifile.IniWriteAll__IntoXmlFile( @"TESTINI_DATEN_ROOT_NAME"); // die iniDatei wird zusätzlich in eine xml-Datei geschrieben; nur in Verbindung mit gefuelltem Dictionary möglich !!!!!  
    /// - string[] liste=myInifile.IniReadAll(); // alles iniDatei_Zeilen lesen und als String-Array zu verfügung stellen
    /// 
    /// // ---------------------------------------------------------------------------------------------------------
    /// 
    /// 
    /// //und noch ein Show-Beispiel:  Dictionary komplett einlesen und anzeigen  ect.....
    ///       foreach( KeyValuePair<string[] , string>  d  in  myInifile.my_DIC.INI_Dictionary )
    ///        {
    ///            //                             MASTERKey                   -             Value
    ///            //              Sectionname       -          subKey        -             Value
    ///            MessageBox.Show( d.Key[0] +" -> "+"Key= ["+ d.Key[1] +"]   value= ["+ d.Value +"]");
    ///        }
    /// 
    /// 
    /// 
    /// nun viel Spass
    /// A.Roters
    /// 
    /// ohne Gewähr
    /// </summary>

    public class cIniFile
    {

        #region Eigenschaften

        // Filenamen fuer ini und xml-Datei
        private string _iniFileName;
        private string _xmlFileName;
        
        private string INI_FILE
        {
            get { return _iniFileName; }
            set { _iniFileName=value; }
        }

        private string XML_FILE
        {
            get { return _xmlFileName; }
            set { _xmlFileName=value; }
        }

        // eigenes Dictionary - siehe cDic-Klasse !!!
        private cDic _my_DIC=new cDic();
        public cDic my_DIC
        {
            get
            {
                return _my_DIC;
            }
            set
            {
                _my_DIC=value;
            }
        }

        // c - Write und Read-Funktion
        [DllImport("kernel32")]
        private static extern long WritePrivateProfileString( string section , string key , string val , string filePath );

        [DllImport("kernel32")]
        private static extern int GetPrivateProfileString( string section , string key , string def , StringBuilder retVal , int size , string filePath );
        
        #endregion
 
        // main
        #region Constructor -  Filename für ini- und xml-Datei festlegen
        /// <summary>
        /// Filename für ini- und xml-Datei festlegen
        /// </summary>
        /// 
        /// enum OPEN_INI_MOD_ -> NEW   neue ini-Datei anlegen; eine vorhandene Datei wird überschrieben !!!
        ///                    -> READ  eine vorhandene ini-Datei kann bearbeitet werden (über cDic - Dictionary)
        ///                    
        /// Aufrufbeispiel:
        /// cInifile myInifile = new cIniFile("c:meineIniDatei", OPEN_INI_MOD_.NEW)  -> neue iniDatei; die vorhandene iniDatei wird vorher geloescht
        /// cInifile myInifile = new cIniFile("c:meineIniDatei", OPEN_INI_MOD_.READ) -> eine breits vorher angelegte iniDatei bearbeiten !!! (per my_Dic. )
        /// 
        public enum OPEN_INI_MOD_ { NEW , READWRITE };
        public cIniFile( string filename ,OPEN_INI_MOD_ _MOD)
        {
            // hier werden die Filenamen festgelegt
            INI_FILE = filename+".ini";
            XML_FILE = filename+".xml";

            // wenn iniDatei vorhanden
            if(File.Exists(INI_FILE)==true)
            {
                if(_MOD==OPEN_INI_MOD_.NEW)
                {
                    DialogResult dr=MessageBox.Show("Die Datei "+INI_FILE+ " ist bereits vorhanden !!!nnDiese wird überschrieben !!!nnnEs wird aber eine Sicherungsdatei: "+INI_FILE+".orginal angelegt.nnDie ini-Datei neu schreiben ?" , "Warnung" , MessageBoxButtons.OKCancel);
                    if(dr==DialogResult.Cancel)
                    {
                        // wenn cancel...Abbruch
                        INI_FILE="";
                        MessageBox.Show("Abbruch");
                    }
                    else
                    {
                        // sonst, Sicherungs-ini-Datei anlegen FILENAME: Filename.original
                        if(File.Exists((INI_FILE+".orginal"))==true)
                            File.Delete(INI_FILE+".orginal");

                        File.Copy(INI_FILE , INI_FILE+".orginal");
                        File.Delete(INI_FILE);
                    }
                }
            }
        }
        #endregion


        #region ini-Datei komplett loeschen
        /// <summary>
        /// </summary>
        /// <returns>bool</returns>
        public bool IniFileDelete()
        {
            bool ret=false;

            if(File.Exists(INI_FILE)==true)
            {
                DialogResult dr=MessageBox.Show("Die Datei "+INI_FILE+ " wirklich loeschen ?" , "Warnung" , MessageBoxButtons.OKCancel);
                if(dr==DialogResult.Cancel)
                {
                    INI_FILE="";
                    MessageBox.Show("Abbruch");
                }
                else
                {
                    File.Delete(INI_FILE);
                    if(File.Exists(INI_FILE)==true)
                    {
                        //MessageBox.Show("error in DeleteIniFile: nnDie Datei "+INI_FILE+" konnte nicht geloescht werden");
                        throw new Exception("error in IniWriteValue: nnDie Datei konnte nicht geloescht werden");
                    }else
                        ret=true;
                }
            }
            return ret;
        }
        #endregion

        #region ini-datei: Eintrag in iniDatei schreiben
        /// <summary>
        /// Übergabe: Section , Key , Value
        /// 
        /// Formatbeispiel:
        /// ---------------
        /// [TEST_SECTION]
        /// my_key1=my_value     usw....
        /// </summary>
        /// <param name="Section"></param>
        /// <param name="Key"></param>
        /// <param name="Value"></param>
        /// <returns>bool</returns>
        public bool IniWriteValue( string Section , string Key , string Value )
        {
            bool ret=false;

            try
            {
                if(Section.Contains('[')!=true && Section.Contains(']')!=true)
                {
                    if(Key.Contains('[')==true)
                    {
                        //MessageBox.Show("error in IniWriteValue: nnUngültiges Zeichen im Keyname "["" "");