/*! \file pipropertystorage.h * \brief Storage of properties for GUI usage * * This file declare PIPropertyStorage */ /* PIP - Platform Independent Primitives Storage of properties for GUI usage Ivan Pelipenko peri4ko@yandex.ru, Andrey Bychkov work.a.b@yandex.ru This program is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this program. If not, see . */ #ifndef PIPROPERTYSTORAGE_H #define PIPROPERTYSTORAGE_H #include "pivariant.h" /** * @brief Key-value storage, based on PIVector with PIPropertyStorage::Property elements. Each element in vector * contains unique name and you can identify property by name with propertyValueByName(), propertyByName(). * You can add property using addProperty(const Property&), addProperty(const PIString&, const PIVariant&, const PIString&, int). */ class PIP_EXPORT PIPropertyStorage { public: PIPropertyStorage() {} /** * @brief PIPropertyStorage element. */ struct PIP_EXPORT Property { Property(const PIString & n = PIString(), const PIString & c = PIString(), const PIVariant & v = PIVariant(), int f = 0): name(n), comment(c), value(v), flags(f) {} Property(const Property & o): name(o.name), comment(o.comment), value(o.value), flags(o.flags) {} Property(Property && o) {swap(o);} Property & operator =(const Property & v) { name = v.name; comment = v.comment; value = v.value; flags = v.flags; return *this; } Property & operator =(Property && v) {swap(v); return *this;} bool toBool() const {return value.toBool();} int toInt() const {return value.toInt();} float toFloat() const {return value.toFloat();} double toDouble() const {return value.toDouble();} PIString toString() const {return value.toString();} void swap(Property & o) { name.swap(o.name); comment.swap(o.comment); value.swap(o.value); piSwap(flags, o.flags); } /*! Uniqueue id of property */ PIString name; /*! Optional description of property */ PIString comment; /*! Custom value of property */ PIVariant value; /*! Abstract flags which may be used for user needs */ int flags; }; PIPropertyStorage(const PIVector & pl) {props = pl;} PIPropertyStorage(PIVector && pl): props(std::move(pl)) {} typedef PIVector::const_iterator const_iterator; typedef PIVector::iterator iterator; typedef Property value_type; iterator begin() {return props.begin();} const_iterator begin() const {return props.begin();} iterator end() {return props.end();} const_iterator end() const {return props.end();} int length() const {return props.length();} int size() const {return props.size();} bool isEmpty() const {return props.isEmpty();} Property & front() {return props.front();} const Property & front() const {return props.front();} Property & back() {return props.back();} const Property & back() const {return props.back();} void removeAt(int i) {props.remove(i);} void clear() {props.clear();} PIPropertyStorage copy() const {return PIPropertyStorage(*this);} int propertiesCount() const {return props.size();} PIVector & properties() {return props;} const PIVector & properties() const {return props;} const PIPropertyStorage & propertyStorage() const {return *this;} /** * @brief Check if property with \a name exists * @return "true" if property exists */ bool isPropertyExists(const PIString & _name) const; /** * @brief Remove all properties */ void clearProperties() {props.clear();} /** * @brief Add property if name isn't present in storage, otherwrise update existing property with same name. * @return "true" if new property added, else if update existing property return "false" * @param p to copy in storage */ bool addProperty(const Property & p); bool addProperty(Property && p); /** * @brief First of all construct Property with method params. After then add property if name isn't present * in storage, otherwrise update existing property with same name. * @return "true" if new property added, else if update existing property return "false" */ bool addProperty(const PIString & _name, const PIVariant & _def_value, const PIString & _comment = PIString(), int _flags = 0); /** * @brief Remove property with \a name * @return "true" if property exists and removed */ bool removeProperty(const PIString & _name); /** * @brief Remove properties wich has \a flag set * @return removed properties count */ int removePropertiesByFlag(int flag); /** * @brief Merge other \a properties_ into this * @param flag_ignore - properties wich has this flag set will be ignored in merge */ void updateProperties(const PIVector & properties_, int flag_ignore = 0); /** * @brief Search property by name and return it. * * @param name of property * @return property value or default constructed Property */ Property propertyByName(const PIString & name) const; /** * @brief Search property by name and return property value. * * @param name of property * @return property value or invalid PIVariant if name unknown */ PIVariant propertyValueByName(const PIString & name) const; /** * @brief Set value of property with specific name if name is present in storage. * * @param name of property to set value * @param value to set * @return "true" if property exists and updated */ bool setPropertyValue(const PIString & name, const PIVariant & value); /** * @brief Set comment of property with specific name if name is present in storage. * * @param name of property to set comment * @param comment to set * @return "true" if property exists and updated */ bool setPropertyComment(const PIString & name, const PIString & comment); /** * @brief Set flags of property with specific name if name is present in storage. * * @param name of property to set flags * @param flags to set * @return "true" if property exists and updated */ bool setPropertyFlags(const PIString & name, int flags); PIPropertyStorage & operator <<(const PIPropertyStorage::Property & p) {props << p; return *this;} PIPropertyStorage & operator <<(const PIVector & p) {props << p; return *this;} PIPropertyStorage & operator <<(const PIPropertyStorage & p) {props << p.props; return *this;} Property & operator[](int i) {return props[i];} const Property & operator[](int i) const {return props[i];} Property & operator[](const PIString & name); const Property operator[](const PIString & name) const; static Property parsePropertyLine(PIString l); protected: PIVector props; }; inline PIByteArray & operator <<(PIByteArray & s, const PIPropertyStorage::Property & v) {s << v.name << v.value << v.comment << v.flags; return s;} inline PIByteArray & operator >>(PIByteArray & s, PIPropertyStorage::Property & v) {s >> v.name >> v.value >> v.comment >> v.flags; return s;} inline PIByteArray & operator <<(PIByteArray & s, const PIPropertyStorage & v) {s << v.properties(); return s;} inline PIByteArray & operator >>(PIByteArray & s, PIPropertyStorage & v) {s >> v.properties(); return s;} #endif // PIPROPERTYSTORAGE_H