Esempio n. 1
0
        /// <summary>
        /// [A very dirty-feeling function]
        /// Given a description, and a type, attempts to find an entry in the database for the given type that has a certain description.
        ///
        /// For example, `getFromDescription<language>("C++")` would look for a language (in the language table) with the description of `C++` and then returns it.
        /// </summary>
        /// <typeparam name="T">The type to look for. This must be a database type.</typeparam>
        /// <param name="db">The database connection.</param>
        /// <param name="description">The description to look for.</param>
        /// <returns>Either null, if the value wasn't found, or the value that was found.</returns>
        public static T getFromDescription <T>(this DatabaseCon db, string description) where T : class
        {
            if (db == null)
            {
                throw new ArgumentNullException("db");
            }

            if (description == null)
            {
                throw new ArgumentNullException("description");
            }

            // Get the right set that represetns `T`
            var set = db._getSetFromT <T>();

            // Then look through all of the values in the DbSet for it.
            foreach (var value in set)
            {
                // This is dirty...
                dynamic dyValue = value;
                if (dyValue.description == description)
                {
                    return(value);
                }
            }

            return(null);
        }
Esempio n. 2
0
        /// <summary>
        /// Throws an exception if the given name/description (the field is called 'description' but is used more as a name) is already being used.
        ///
        /// NOTE: The type `T` must contain a field called 'description'.
        /// </summary>
        /// <typeparam name="T">The type to check with. (this determines which table is used)</typeparam>
        /// <param name="db">The database connection.</param>
        /// <param name="name_description">The name/description to check for.</param>
        public static void enforceNameIsUnique <T>(this DatabaseCon db, string name_description) where T : class
        {
            var set = db._getSetFromT <T>();

            foreach (var record in set)
            {
                dynamic dyRecord = record;
                if (dyRecord.description == name_description)
                {
                    throw new Exception($"The name/description '{name_description}' is already being used by another {typeof(T).Name}");
                }
            }
        }
Esempio n. 3
0
        /// <summary>
        /// Throws an exception if the given bit index is already being used.
        ///
        /// NOTE: The type `T` must contain fields called `bit_index` and `description`.
        /// </summary>
        /// <typeparam name="T">The type to check with. (this determines which table is used)</typeparam>
        /// <param name="db">The database connection</param>
        /// <param name="index">The index to check</param>
        public static void enforceBitIndexIsUnique <T>(this DatabaseCon db, byte index) where T : class
        {
            var set = db._getSetFromT <T>();

            foreach (var record in set)
            {
                dynamic dyRecord = record;
                if (dyRecord.bit_index == index)
                {
                    throw new Exception($"The bit index {index} is being used by the {typeof(T).Name} '{dyRecord.description}'");
                }
            }
        }
Esempio n. 4
0
        // The reason this function is in ViewHelper, instead of DataHelper, is because of the user-interaction is requires, as well as the requirement of the MainWindow, making it specialised for use in views.
        /// <summary>
        /// Deletes a `T` from the database that has a description matching the given description.
        /// (note: in a lot of cases the description is just a name, hence 'name_description')
        ///
        /// This function will first prompt the user with a message box, asking them to confirm the deletion of the object.
        ///
        /// It is a requirement that `T` has a field called `description`.
        /// </summary>
        /// <typeparam name="T">The database type to remove (and also determines the database table that's used)</typeparam>
        /// <param name="window">The main window, so it's status can be updated</param>
        /// <param name="name_description">The name/description of the object to remove</param>
        /// <returns>True if something was delete.</returns>
        public static bool deleteTByDescription <T>(MainWindow window, string name_description) where T : class
        {
            if (window == null)
            {
                throw new ArgumentNullException("window");
            }

            if (name_description == null)
            {
                throw new ArgumentNullException("name_description");
            }

            var TName  = typeof(T).Name;
            var result = System.Windows.Forms.MessageBox.Show($"Are you sure you want to remove the {TName} '{name_description}'?",
                                                              "Confirmation", MessageBoxButtons.YesNo, MessageBoxIcon.Question);

            if (result == DialogResult.No)
            {
                window.updateStatus($"Not going through with removal of the {TName}");
                return(false);
            }

            using (var db = new DatabaseCon())
            {
                var set   = db._getSetFromT <T>();
                T   value = null;

                // I need to use dynamic, so can't use SingleOrDefault since it doesn't like lambdas apparently
                foreach (var val in set)
                {
                    dynamic dyVal = val;
                    if (dyVal.description == name_description)
                    {
                        value = val;
                        break;
                    }
                }

                if (value == null)
                {
                    window.updateStatus($"Can't delete a(n) {TName} that doesn't exist");
                    return(false);
                }

                window.updateStatus($"Removing {TName} '{name_description}' from the database");
                set.Remove(value);
                db.SaveChanges();
            }

            return(true);
        }
Esempio n. 5
0
        /// <summary>
        /// Given a bitmask, returns a list of all objects of `T` from the database that the bitmask contains.
        ///
        /// For example, say `T` was `device_type`, and in the database we only had two devices:
        ///     1: 'Arduino' with a bit_index of 0
        ///     2: 'PC' with a bit_index of 1
        ///
        /// Now, imagine the bitmask of '00000001', the 0th bit is set to 1, so a list only containing 'Arduino' is returned.
        /// Take '00000011', both the 0th and 1st bits are set, so a list containing both 'Arduino' and 'PC' is returned.
        /// </summary>
        /// <typeparam name="T">The database type to use.</typeparam>
        /// <param name="db">The database connection.</param>
        /// <param name="bitmask">The bitmask to use.</param>
        /// <returns>See extended summary</returns>
        public static List <T> getFromBitmask <T>(this DatabaseCon db, byte bitmask) where T : class
        {
            var set = db._getSetFromT <T>();

            // LINQ doesn't like using the _getBitIndex function during a query, so I go over it the old fashioned way.
            List <T> list = new List <T>();

            foreach (var value in set)
            {
                if ((bitmask & (1 << value._getBitIndex())) > 0)
                {
                    list.Add(value);
                }
            }

            return(list);
        }
Esempio n. 6
0
        /// <summary>
        /// Populates a drop down box (combobox) with the descriptions of `T` from the database.
        ///
        /// For example, if `T` were `device_type`, then the drop down would contain all of the descriptions/names of
        /// all the entries in the device_type table.
        ///
        /// It is a requirement that `T` contains a `description` field.
        /// </summary>
        /// <typeparam name="T">The database type to use</typeparam>
        /// <param name="db">The database connection</param>
        /// <param name="dropDown">The dropdown to populate</param>
        /// <param name="list">This list will be filled with all of the records from the table</param>
        /// <param name="additionalProcessing">
        ///     This function will be called with each record of `T` from the database, in case any additional action is required.
        ///
        ///     The records are passed in order of description.
        ///
        ///     This alleviates the need to then create another foreach right after this function, just to do some additional action.
        /// </param>
        public static void populateDropDownWithT <T>(this DatabaseCon db, System.Windows.Controls.ComboBox dropDown, out List <T> list, Action <T> additionalProcessing = null) where T : class
        {
            if (db == null)
            {
                throw new ArgumentNullException("db");
            }

            if (dropDown == null)
            {
                throw new ArgumentNullException("dropDown");
            }

            list = db._getSetFromT <T>().ToList();
            foreach (var value in list.OrderBy(v => { dynamic dyV = v; return(dyV.description); }))
            {
                dynamic dyValue = value;
                dropDown.Items.Add(dyValue.description);

                additionalProcessing?.Invoke(value);
            }
        }