home *** CD-ROM | disk | FTP | other *** search
- /******************************************************************************
- **
- ** C++ Class Library for the Amiga© system software.
- **
- ** Copyright (C) 1994 by Armin Vogt ** EMail: armin@uni-paderborn.de
- ** All Rights Reserved.
- **
- ** $Source: apphome:APlusPlus/RCS/libsource/AttrList.cxx,v $
- ** $Revision: 1.5 $
- ** $Date: 1994/05/09 21:17:52 $
- ** $Author: Armin_Vogt $
- **
- ******************************************************************************/
-
-
- #include <APlusPlus/utility/AttrList.h>
-
-
- volatile static char rcs_id[] = "$Id: AttrList.cxx,v 1.5 1994/05/09 21:17:52 Armin_Vogt Exp Armin_Vogt $";
-
-
- struct TagItem *AttrList::tmp = NULL;
- AttrList *AttrList::tmpUser = NULL;
- int AttrList::tmpMaxLength = 0;
-
-
- AttrList::AttrList(struct TagItem *tl)
- {
- taglist = tl!=NULL?CloneTagItems(tl):NULL;
- }
-
- AttrList::AttrList(LONG tag1Type,...)
- {
- taglist = CloneTagItems((struct TagItem*)&tag1Type);
- }
-
- AttrList::AttrList(const AttrList& from)
- {
- taglist = from.taglist!=NULL?CloneTagItems(from.taglist):NULL;
- }
-
- struct TagItem *AttrList::copyTagItems(struct TagItem *tlist)
- {
- return CloneTagItems(tlist);
- }
-
- void AttrList::freeTagItems(struct TagItem *tlist)
- {
- FreeTagItems(taglist);
- }
-
- AttrList::~AttrList()
- {
- freeTagItems(taglist);
- }
-
- AttrList& AttrList::operator=(const AttrList& from) // assignment is copying
- {
- if (this != &from)
- {
- freeTagItems(taglist);
- taglist = from.taglist!=NULL?CloneTagItems(from.taglist):NULL;
- }
- return *this;
- }
-
- BOOL AttrList::addAttrs(const AttrList& attrs)
- /* Enhance the IntuiObject's attribute taglist with additional tags from the given
- taglist in a way, that not already present tags will be added, while already
- present remain untouched.
- The new tags will be added at the head of the attribute taglist and initialised
- to zero.
- Note that setting the attributes is only possible by using public method
- setAttributes() or protected method setAttrs() which both will involve the
- ITransponder notification mechanism.
- */
- {
- /** Set tags in the modifying taglist that are already present in the attribute taglist
- ** to TAG_IGNORE. The remaining tags are added to the attribute taglist and set to 0.
- **/
- _dout("AttrList::addAttrs("<<attrs<<")\n");
- if (taglist==NULL)
- {
- taglist = CloneTagItems(attrs);
- _dout("addAttrs to null list.\n");
- return TRUE;
- } // for an empty AttrList only copy additional tags to this.
-
- if (FilterTagItems(taglist,(Tag*)attrs.taglist,TAGFILTER_NOT)>0)
- {
- // get the end of the taglist
- struct TagItem *tag = attrs.taglist;
- while (tag->ti_Tag != TAG_END)
- tag++;
-
- // concatenate additional taglist to attribute taglist
- tag->ti_Tag = TAG_MORE;
- tag->ti_Data = (ULONG)taglist;
-
- // copy concatenated taglist to a private memory (removes TAG_MORE)
- struct TagItem *newTL;
- if (NULL != (newTL = CloneTagItems(attrs.taglist)) )
- {
- // free old private attribute taglist copy
- freeTagItems(taglist);
-
- taglist = newTL; // set to new concatenated attribute taglist.
- _dout("IntuiObject has now attr: "<<*this<<") done.\n");
- return TRUE;
- }
- else cerr << "OUT_OF_MEMORY";
- }
- else _dout("no additional tags found\n");
-
- return FALSE;
- }
-
- BOOL AttrList::updateAttrs(const AttrList& attrlist)
- /* updates the tag data in 'this' of tags present in both 'this' and 'attrlist'
- with the corresponding tag data in attrlist.
- */
- {
- BOOL changed = FALSE; // any changes done
- AttrManipulator next(*this);
- AttrIterator read(attrlist);
-
- _dout("IntuiObject::writeTags : ");
- while (read())
- {
- if (next.findTagItem(read.tag()) )
- {
- if (read.data() != next.data())
- {
- next.writeData(read.data());
- changed = TRUE;
- }
- }
- }
- if (!changed)
- {
- _dout(" no changes.\n");
- }
- else
- {
- _dout("\n");
- }
- return changed;
- }
-
- ULONG AttrList::mapAttrs(AttrList& mapAt)
- /* Maps taglist according to mapAt. All tags that are not appearing
- in the mapAt list are being deleted (set to TAG_IGNORE). Still remaining
- valid tags will be mapped to the new tag identifiers in the mapAt list.
- */
- {
- MapTags(taglist,mapAt.taglist,FALSE);
- // include miss is FALSE, so unmatched tags are being deleted.
- // ERROR: MapTags() does NOT remove unmatched tags!!!!
- // Bug fix: use subsequent FilterTagItems().
- return filterAttrs(mapAt);
- //return 1L;
- }
- ULONG AttrList::mapAttrs(struct TagItem *mapList)
- {
- MapTags(taglist,mapList,FALSE);
- return filterAttrs(mapList);
- }
-
- ULONG AttrList::filterAttrs(AttrList& filterAt)
- /* Filters taglist according to filterTags. All tags that are not appearing
- in the filterTags array are deleted (set to TAG_IGNORE).
- The number of tags that are not set to TAG_IGNORE is returned.
- */
- {
- return FilterTagItems(taglist,(Tag*)filterAt.taglist,TAGFILTER_AND);
- }
- ULONG AttrList::filterAttrs(struct TagItem *filterList)
- {
- return FilterTagItems(taglist,(Tag*)filterList,TAGFILTER_AND);
-
- }
-
-
- //------------------- AttrIterator methods ----------------------------------------
-
- BOOL AttrIterator::findTagItem(Tag tagVal)
- {
- /** This method assumes that NextTagItem() keeps track of the scanned taglist with
- ** the 'tstate' pointer referencing to the next tag item to be fetched with NextTagItem().
- ** Since NextTagItem() does not return TAG_MORE ,TAG_SKIP and TAG_END the found tag item
- ** must be a user tag thus the following tag item is at the successing (TagItem*) address.
- **/
- if (NULL != (atTag = FindTagItem(tagVal,tstate)))
- {
- tstate = atTag+1; // set NextTagItem() internal track to next tag item
- return TRUE;
- }
- else return FALSE;
- }
-
- ostream& operator << (ostream& OS,const AttrList& attrlist)
- {
- OS <<"<"<< attrlist.taglist <<">"<<endl;
- return OS ;
- }
-