/*************************************************************************** copyright : (C) 2001-2006 by Robby Stephenson email : robby@periapsis.org ***************************************************************************/ /*************************************************************************** * * * This program is free software; you can redistribute it and/or modify * * it under the terms of version 2 of the GNU General Public License as * * published by the Free Software Foundation; * * * ***************************************************************************/ #ifndef COLLECTION_H #define COLLECTION_H #include "field.h" #include "entry.h" #include "filter.h" #include "borrower.h" #include "datavectors.h" #include #include #include #include #include #include #include namespace Tellico { namespace Data { class EntryGroup; typedef TQDict EntryGroupDict; /** * The Collection class is the primary data object, holding a * list of fields and entries. * * A collection holds entries of a single type, whether it be books, CDs, or whatever. * It has a list of attributes which apply for the whole collection. A unique id value * identifies each collection object. * * @see Entry * @see Field * * @author Robby Stephenson */ class Collection : public TQObject, public TDEShared { TQ_OBJECT public: enum Type { Base = 1, Book = 2, Video = 3, Album = 4, Bibtex = 5, ComicBook = 6, Wine = 7, Coin = 8, Stamp = 9, Card = 10, Game = 11, File = 12, BoardGame = 13 // if you want to add custom collection types, use a number sure to be unique like 101 }; /** * The constructor is only used to create custom collections. It adds a title field, * in the "General" group. The iconName is set to be the typeName; * * @param title The title of the collection itself * @param entryTitle The title of the entries, which can be translated */ explicit Collection(const TQString& title); /** */ virtual ~Collection(); /** * Returns the type of the collection. * * @return The type */ virtual Type type() const { return Base; } /** * Returns the id of the collection. * * @return The id */ long id() const { return m_id; } /** * Returns the name of the collection. * * @return The name */ const TQString& title() const { return m_title; } /** * Sets the title of the collection. * * @param title The new collection title */ void setTitle(const TQString& title) { m_title = title; } /** * Returns the name of the entries in the collection, e.g. "book". * Not translated. * * @return The type name */ TQString typeName() const; /** * Returns a reference to the list of all the entries in the collection. * * @return The list of entries */ const EntryVec& entries() const { return m_entries; } /** * Returns a reference to the list of the collection attributes. * * @return The list of fields */ const FieldVec& fields() const { return m_fields; } EntryPtr entryById(long id); /** * Returns a reference to the list of the collection's people fields. * * @return The list of fields */ const FieldVec& peopleFields() const { return m_peopleFields; } /** * Returns a reference to the list of the collection's image fields. * * @return The list of fields */ const FieldVec& imageFields() const { return m_imageFields; } /** * Returns a reference to the list of field groups. This value is cached rather * than generated with each call, so the method should be fairly fast. * * @return The list of group names */ const TQStringList& fieldCategories() const { return m_fieldCategories; } /** * Returns the name of the field used to group the entries by default. * * @return The field name */ const TQString& defaultGroupField() const { return m_defaultGroupField; } /** * Sets the name of the default field used to group the entries. * * @param name The name of the field */ void setDefaultGroupField(const TQString& name) { m_defaultGroupField = name; } /** * Returns the number of entries in the collection. * * @return The number of entries */ size_t entryCount() const { return m_entries.count(); } /** * Adds a entry to the collection. The collection takes ownership of the entry object. * * @param entry A pointer to the entry */ void addEntries(EntryVec entries); /** * Updates the dicts that include the entry. * * @param entry A pointer to the entry */ void updateDicts(EntryVec entries); /** * Deletes a entry from the collection. * * @param entry The pointer to the entry * @return A boolean indicating if the entry was in the collection and was deleted */ bool removeEntries(EntryVec entries); /** * Adds a whole list of attributes. It's gotta be virtual since it calls * @ref addField, which is virtual. * * @param list List of attributes to add * @return A boolean indicating if the field was added or not */ virtual bool addFields(FieldVec list); /** * Adds an field to the collection, unless an field with that name * already exists. The collection takes ownership of the field object. * * @param field A pointer to the field * @return A boolean indicating if the field was added or not */ virtual bool addField(FieldPtr field); virtual bool mergeField(FieldPtr field); virtual bool modifyField(FieldPtr field); virtual bool removeField(FieldPtr field, bool force=false); virtual bool removeField(const TQString& name, bool force=false); void reorderFields(const FieldVec& list); // the reason this is not static is so I can call it from a collection pointer // it also gets virtualized for different collection types // the return values should be compared against the GOOD and PERFECT // static match constants in this class virtual int sameEntry(Data::EntryPtr, Data::EntryPtr) const; /** * Determines whether or not a certain value is allowed for an field. * * @param key The name of the field * @param value The desired value * @return A boolean indicating if the value is an allowed value for that field */ bool isAllowed(const TQString& key, const TQString& value) const; /** * Returns a list of all the field names. * * @return The list of names */ const TQStringList& fieldNames() const { return m_fieldNames; } /** * Returns a list of all the field titles. * * @return The list of titles */ const TQStringList& fieldTitles() const { return m_fieldTitles; } /** * Returns the title of an field, given its name. * * @param name The field name * @return The field title */ const TQString& fieldTitleByName(const TQString& name) const; /** * Returns the name of an field, given its title. * * @param title The field title * @return The field name */ const TQString& fieldNameByTitle(const TQString& title) const; /** * Returns a list of the values of a given field for every entry * in the collection. The values in the list are not repeated. Attribute * values which contain ";" are split into separate values. Since this method * iterates over all the entries, for large collections, it is expensive. * * @param name The name of the field * @return The list of values */ TQStringList valuesByFieldName(const TQString& name) const; /** * Returns a list of all the fields in a given category. * * @param category The name of the category * @return The field list */ FieldVec fieldsByCategory(const TQString& category); /** * Returns a pointer to an field given its name. If none is found, a NULL pointer * is returned. * * @param name The field name * @return The field pointer */ FieldPtr fieldByName(const TQString& name) const; /** * Returns a pointer to an field given its title. If none is found, a NULL pointer * is returned. This lookup is slower than by name. * * @param title The field title * @return The field pointer */ FieldPtr fieldByTitle(const TQString& title) const; /** * Returns @p true if the collection contains a field named @ref name; */ bool hasField(const TQString& name) const; /** * Returns a list of all the possible entry groups. This value is cached rather * than generated with each call, so the method should be fairly fast. * * @return The list of groups */ const TQStringList& entryGroups() const { return m_entryGroups; } /** * Returns a pointer to a dict of all the entries grouped by * a certain field * * @param name The name of the field by which the entries are grouped * @return The list of group names */ EntryGroupDict* entryGroupDictByName(const TQString& name); /** * Invalidates all group names in the collection. */ void invalidateGroups(); /** * Returns true if the collection contains at least one Image field. * * @return Returns true if the collection contains at least one Image field; */ bool hasImages() const { return !m_imageFields.isEmpty(); } void setTrackGroups(bool b) { m_trackGroups = b; } void addBorrower(Data::BorrowerPtr borrower); const BorrowerVec& borrowers() const { return m_borrowers; } /** * Clears all vectors which contain shared ptrs */ void clear(); void addFilter(FilterPtr filter); bool removeFilter(FilterPtr filter); const FilterVec& filters() const { return m_filters; } static bool mergeEntry(EntryPtr entry1, EntryPtr entry2, bool overwrite, bool askUser=false); /** * The string used for empty values. This forces consistency. */ static const char* s_emptyGroupTitle; /** * The string used for the people pseudo-group. This forces consistency. */ static const TQString s_peopleGroupName; // these are the values that should be compared against // the result from sameEntry() static const int ENTRY_GOOD_MATCH = 10; static const int ENTRY_PERFECT_MATCH = 20; signals: void signalGroupsModified(Tellico::Data::CollPtr coll, PtrVector groups); void signalRefreshField(Tellico::Data::FieldPtr field); private: TQStringList entryGroupNamesByField(EntryPtr entry, const TQString& fieldName); void removeEntriesFromDicts(EntryVec entries); void populateDict(EntryGroupDict* dict, const TQString& fieldName, EntryVec entries); void populateCurrentDicts(EntryVec entries); void cleanGroups(); bool dependentFieldHasRecursion(FieldPtr field); /* * Gets the preferred ID of the collection. Currently, it just gets incremented as * new collections are created. */ static long getID(); /** * The copy constructor is private, to ensure that it's never used. */ Collection(const Collection& coll); /** * The assignment operator is private, to ensure that it's never used. */ Collection operator=(const Collection& coll); long m_id; long m_nextEntryId; TQString m_title; TQString m_typeName; TQString m_iconName; TQString m_defaultGroupField; FieldVec m_fields; FieldVec m_peopleFields; // keep separate list of people fields FieldVec m_imageFields; // keep track of image fields TQDict m_fieldNameDict; TQDict m_fieldTitleDict; TQStringList m_fieldCategories; TQStringList m_fieldNames; TQStringList m_fieldTitles; EntryVec m_entries; TQIntDict m_entryIdDict; TQDict m_entryGroupDicts; TQStringList m_entryGroups; PtrVector m_groupsToDelete; FilterVec m_filters; BorrowerVec m_borrowers; bool m_trackGroups : 1; }; } // end namespace } //end namespace #endif