Index: Core/Algo.h =================================================================== --- Core/Algo.h (revision 13888) +++ Core/Algo.h (working copy) @@ -271,3 +271,41 @@ x.Add(i); return x; } + +template < class SortRange > +void RemoveDuplicates( SortRange& V ) +{ + int n = 0, i = 1; + while ( i < V.GetCount() ) { + do { + if ( i >= V.GetCount() ) + return; + if ( V[ i ] == V[ n ] ) + V.Remove( i ); + else + break; + } while ( true ); + ++n; + ++i; + } +}; + +template < class SortRange, class OnRemove > +void RemoveDuplicates( SortRange& V, const OnRemove& On_Remove ) +{ + int n = 0, i = 1; + while ( i < V.GetCount() ) { + do { + if ( i >= V.GetCount() ) + return; + if ( V[ i ] == V[ n ] ) { + On_Remove( i ); + V.Remove( i ); + } else + break; + } while ( true ); + ++n; + ++i; + } +}; + \ No newline at end of file Index: Core/Vcont.h =================================================================== --- Core/Vcont.h (revision 13888) +++ Core/Vcont.h (working copy) @@ -165,6 +165,8 @@ void Remove(const Vector& sorted_list); template void RemoveIf(Condition c); + template + void RemoveIf(Condition c, OnRemove On_Remove); void InsertN(int i, int count = 1); T& Insert(int i) { InsertN(i); return Get(i); } @@ -311,7 +313,9 @@ void Remove(const Vector& sorted_list); template void RemoveIf(Condition c); - void InsertN(int i, int count = 1); + template + void RemoveIf(Condition c, OnRemove On_Remove); +void InsertN(int i, int count = 1); T& Insert(int i) { InsertN(i); return Get(i); } void Insert(int i, const T& x, int count); T& Insert(int i, const T& x) { Insert(i, x, 1); return Get(i); } Index: Core/Vcont.hpp =================================================================== --- Core/Vcont.hpp (revision 13888) +++ Core/Vcont.hpp (working copy) @@ -299,6 +299,20 @@ } template +template +void Vector::RemoveIf(Condition c, OnRemove On_Remove) +{ + int ti = 0; + for(int i = 0; i < items; i++) + if(c(i)) { + On_Remove( i ); + (vector + i)->~T(); + } else + *((Data_S_*)vector + ti++) = *((Data_S_*)vector + i); + items = ti; +} + +template void Vector::RawInsert(int q, int count) { ASSERT(count >= 0); @@ -576,6 +590,19 @@ vector.Trim(ti); } +template +template +void Array::RemoveIf(Condition c, OnRemove On_Remove) +{ + int ti = 0; + for(int i = 0; i < vector.GetCount(); i++) + if(c(i)) { + On_Remove( i ); + delete (T *)vector[i]; + } else + vector[ti++] = vector[i]; + vector.Trim(ti); +} template void Array::Set(int i, const T& x, int count) { Index: CtrlLib/ArrayCtrl.cpp =================================================================== --- CtrlLib/ArrayCtrl.cpp (revision 13888) +++ CtrlLib/ArrayCtrl.cpp (working copy) @@ -46,7 +46,7 @@ return *this; } -ArrayCtrl::Column& ArrayCtrl::Column::ConvertBy(Function cv) +ArrayCtrl::Column& ArrayCtrl::Column::ConvertBy( const Function< Value ( const Value& ) >& cv ) { convertby = cv; ClearCache(); @@ -55,6 +55,15 @@ return *this; } +ArrayCtrl::Column& ArrayCtrl::Column::SetSetter( const Function< void ( const Value&, int i ) >& st ) +{ + Setter = st; + ClearCache(); + arrayctrl->Refresh(); + arrayctrl->SyncInfo(); + return *this; +} + ArrayCtrl::Column& ArrayCtrl::Column::SetFormat(const char *fmt) { FormatConvert::SetFormat(fmt); @@ -429,7 +438,14 @@ ASSERT(IsCursor()); Column& m = column[j]; if(m.edit) - m.edit->SetData(GetColumn(cursor, j)); + if ( m.pos.GetCount() > 0 ) + m.edit->SetData(GetColumn(cursor, j)); + else + if ( m.convertby ) + m.edit->SetData( m.convertby( cursor ) ); + else + if ( m.convert ) + m.edit->SetData( m.convert->Format( cursor ) ); } void ArrayCtrl::CtrlSetData(int j) { @@ -1260,7 +1276,10 @@ Column& m = column[i]; if(m.edit && m.edit->IsModified()) { Value v = m.edit->GetData(); - if(m.pos.GetCount() == 1) { + int mp = m.pos.GetCount(); + if( mp == 0 ) { + m.Setter( v, cursor ); + } if( mp == 1) { Value& vv = array.At(cursor).line.At(Pos(m.pos[0])); if(vv != v) { iv = true; @@ -1268,7 +1287,7 @@ } } else - if(m.pos.GetCount() > 1) { + if( mp > 1 ) { ValueArray va = v; for(int j = 0; j < m.pos.GetCount(); j++) { Value& vv = array.At(cursor).line.At(Pos(m.pos[j])); @@ -1585,6 +1604,13 @@ return id; } +void ArrayCtrl::GetSelIndexes( Vector< int >& R ) +{ + for( int i = 0; i < GetCount(); ++i ) + if( IsSel( i ) ) + R.Add( i ); +} + int ArrayCtrl::GetScroll() const { return sb; @@ -1962,33 +1988,45 @@ sb.NextLine(); return true; case K_ENTER: - if(!IsCursor() && (IsInserting() || IsAppending()) && IsAppendLine()) { - DoAppend(); - return true; - } - if(editmode) { - bool ins = IsInsert() && autoappend; - if(AcceptEnter() && ins) - DoAppend(); - return true; - } - if(WhenEnterKey && IsCursor()) { - WhenEnterKey(); - return true; - } + if ( IfEditPost() ) + return true; break; case K_ESCAPE: - if(IsEdit()) { - int c = cursor; - CancelCursor(); - SetCursor(c); - return true; - } + if ( IfEditCancel() ) + return true; break; } return MenuBar::Scan(WhenBar, key); } +bool ArrayCtrl::IfEditPost() { + if(!IsCursor() && (IsInserting() || IsAppending()) && IsAppendLine()) { + DoAppend(); + return true; + } + if(editmode) { + bool ins = IsInsert() && autoappend; + if(AcceptEnter() && ins) + DoAppend(); + return true; + } + if(WhenEnterKey && IsCursor()) { + WhenEnterKey(); + return true; + } + return false; +} + +bool ArrayCtrl::IfEditCancel() { + if(IsEdit()) { + int c = cursor; + CancelCursor(); + SetCursor(c); + return true; + } + return false; +} + bool ArrayCtrl::AcceptEnter() { if(editmode) { bool ins = IsInsert(); @@ -2265,6 +2303,8 @@ void ArrayCtrl::DoInsert(int c) { if(IsReadOnly()) return; + if ( Inserter ) + Inserter( c ); Insert(c); SetCursor(c); insertmode = true; Index: CtrlLib/ArrayCtrl.h =================================================================== --- CtrlLib/ArrayCtrl.h (revision 13888) +++ CtrlLib/ArrayCtrl.h (working copy) @@ -35,6 +35,9 @@ virtual void ChildGotFocus(); virtual void ChildLostFocus(); virtual void Serialize(Stream& s); + bool IfEditPost(); + bool IfEditCancel(); + Function< void ( int ) > Inserter; public: struct IdInfo { @@ -57,7 +60,6 @@ int index; Mitor pos; const Convert *convert; - Function convertby; Ptr edit; const Display *display; Event&> factory; @@ -83,6 +85,9 @@ friend class ArrayCtrl; public: + Function< Value( const Value& ) > convertby; + Function< void ( const Value&, int i ) > Setter; + Column& Add(int _pos) { pos.Add(_pos); return *this; } Column& Add(const Id& id) { pos.Add(-arrayctrl->AsNdx(id)); return *this; } Column& AddIndex(const Id& id) { arrayctrl->AddIndex(id); return Add(id); } @@ -89,7 +94,8 @@ Column& AddIndex() { Add(arrayctrl->GetIndexCount()); arrayctrl->AddIndex(); return *this; } Column& SetConvert(const Convert& c); - Column& ConvertBy(Function cv); + Column& ConvertBy( const Function< Value( const Value& ) >& cv); + Column& SetSetter( const Function< void ( const Value&, int i ) >& st ); Column& SetFormat(const char *fmt); Column& SetDisplay(const Display& d); Column& NoEdit(); @@ -460,6 +466,7 @@ void ClearSelection(bool raise = true); bool IsSel(int i) const; Vector GetSelKeys() const; + void GetSelIndexes( Vector< int >& R ); void EnableLine(int i, bool e); void DisableLine(int i) { EnableLine(i, false); }