1 /*
2 * Hydrogen
3 * Copyright(c) 2002-2008 by Alex >Comix< Cominu [comix@users.sourceforge.net]
4 *
5 * http://www.hydrogen-music.org
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY, without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 *
21 */
22
23 #include <hydrogen/basics/pattern_list.h>
24
25 //#include <hydrogen/helpers/xml.h>
26 #include <hydrogen/basics/pattern.h>
27
28 namespace H2Core
29 {
30
31 const char* PatternList::__class_name = "PatternList";
32
PatternList()33 PatternList::PatternList() : Object( __class_name )
34 {
35 }
36
PatternList(PatternList * other)37 PatternList::PatternList( PatternList* other ) : Object( __class_name )
38 {
39 assert( __patterns.size() == 0 );
40 for ( int i=0; i<other->size(); i++ ) {
41 ( *this ) << ( new Pattern( ( *other )[i] ) );
42 }
43 }
44
~PatternList()45 PatternList::~PatternList()
46 {
47 for ( int i = 0; i < __patterns.size(); ++i ) {
48 assert ( __patterns[i] );
49 delete __patterns[i];
50 }
51 }
52
operator <<(Pattern * pattern)53 void PatternList::operator<<( Pattern* pattern )
54 {
55 // do nothing if already in __patterns
56 for( int i=0; i<__patterns.size(); i++ ) {
57 if( __patterns[i]==pattern ) return;
58 }
59 __patterns.push_back( pattern );
60 }
61
add(Pattern * pattern)62 void PatternList::add( Pattern* pattern )
63 {
64 // do nothing if already in __patterns
65 for( int i=0; i<__patterns.size(); i++ ) {
66 if( __patterns[i]==pattern ) return;
67 }
68 __patterns.push_back( pattern );
69 }
70
insert(int idx,Pattern * pattern)71 void PatternList::insert( int idx, Pattern* pattern )
72 {
73 // do nothing if already in __patterns
74 for( int i=0; i<__patterns.size(); i++ ) {
75 if( __patterns[i]==pattern ) return;
76 }
77 __patterns.insert( __patterns.begin() + idx, pattern );
78 }
79
operator [](int idx)80 Pattern* PatternList::operator[]( int idx )
81 {
82 if ( idx < 0 || idx >= __patterns.size() ) {
83 ERRORLOG( QString( "idx %1 out of [0;%2]" ).arg( idx ).arg( size() ) );
84 return nullptr;
85 }
86 assert( idx >= 0 && idx < __patterns.size() );
87 return __patterns[idx];
88 }
89
get(int idx)90 Pattern* PatternList::get( int idx )
91 {
92 if ( idx < 0 || idx >= __patterns.size() ) {
93 ERRORLOG( QString( "idx %1 out of [0;%2]" ).arg( idx ).arg( size() ) );
94 return nullptr;
95 }
96 assert( idx >= 0 && idx < __patterns.size() );
97 return __patterns[idx];
98 }
99
get(int idx) const100 const Pattern* PatternList::get( int idx ) const
101 {
102 if ( idx < 0 || idx >= __patterns.size() ) {
103 ERRORLOG( QString( "idx %1 out of [0;%2]" ).arg( idx ).arg( size() ) );
104 return nullptr;
105 }
106 assert( idx >= 0 && idx < __patterns.size() );
107 return __patterns[idx];
108 }
109
index(Pattern * pattern)110 int PatternList::index( Pattern* pattern )
111 {
112 for( int i=0; i<__patterns.size(); i++ ) {
113 if ( __patterns[i]==pattern ) return i;
114 }
115 return -1;
116 }
117
del(int idx)118 Pattern* PatternList::del( int idx )
119 {
120 assert( idx >= 0 && idx < __patterns.size() );
121 Pattern* pattern = __patterns[idx];
122 __patterns.erase( __patterns.begin() + idx );
123 return pattern;
124 }
125
del(Pattern * pattern)126 Pattern* PatternList::del( Pattern* pattern )
127 {
128 for( int i=0; i<__patterns.size(); i++ ) {
129 if( __patterns[i]==pattern ) {
130 __patterns.erase( __patterns.begin() + i );
131 return pattern;
132 }
133 }
134 return nullptr;
135 }
136
replace(int idx,Pattern * pattern)137 Pattern* PatternList::replace( int idx, Pattern* pattern )
138 {
139 /*
140 * if we insert a new pattern (copy, add new pattern, undo delete pattern and so on will do this)
141 * idx is > __pattern.size(). that's why i add +1 to assert expression
142 */
143
144 assert( idx >= 0 && idx <= __patterns.size() +1 );
145 if( idx < 0 || idx >= __patterns.size() ) {
146 ERRORLOG( QString( "index out of bounds %1 (size:%2)" ).arg( idx ).arg( __patterns.size() ) );
147 return nullptr;
148 }
149
150 __patterns.insert( __patterns.begin() + idx, pattern );
151 __patterns.erase( __patterns.begin() + idx + 1 );
152
153 //create return pattern after patternlist tätatä to return the right one
154 Pattern* ret = __patterns[idx];
155 return ret;
156 }
157
set_to_old()158 void PatternList::set_to_old()
159 {
160 for( int i=0; i<__patterns.size(); i++ ) {
161 __patterns[i]->set_to_old();
162 }
163 }
164
find(const QString & name)165 Pattern* PatternList::find( const QString& name )
166 {
167 for( int i=0; i<__patterns.size(); i++ ) {
168 if ( __patterns[i]->get_name()==name ) return __patterns[i];
169 }
170 return nullptr;
171 }
172
swap(int idx_a,int idx_b)173 void PatternList::swap( int idx_a, int idx_b )
174 {
175 assert( idx_a >= 0 && idx_a < __patterns.size() );
176 assert( idx_b >= 0 && idx_b < __patterns.size() );
177 if( idx_a == idx_b ) return;
178 //DEBUGLOG(QString("===>> SWAP %1 %2").arg(idx_a).arg(idx_b) );
179 Pattern* tmp = __patterns[idx_a];
180 __patterns[idx_a] = __patterns[idx_b];
181 __patterns[idx_b] = tmp;
182 }
183
move(int idx_a,int idx_b)184 void PatternList::move( int idx_a, int idx_b )
185 {
186 assert( idx_a >= 0 && idx_a < __patterns.size() );
187 assert( idx_b >= 0 && idx_b < __patterns.size() );
188 if( idx_a == idx_b ) return;
189 //DEBUGLOG(QString("===>> MOVE %1 %2").arg(idx_a).arg(idx_b) );
190 Pattern* tmp = __patterns[idx_a];
191 __patterns.erase( __patterns.begin() + idx_a );
192 __patterns.insert( __patterns.begin() + idx_b, tmp );
193 }
194
flattened_virtual_patterns_compute()195 void PatternList::flattened_virtual_patterns_compute()
196 {
197 for ( int i=0 ; i<__patterns.size() ; i++ ) __patterns[i]->flattened_virtual_patterns_clear();
198 for ( int i=0 ; i<__patterns.size() ; i++ ) __patterns[i]->flattened_virtual_patterns_compute();
199 }
200
virtual_pattern_del(Pattern * pattern)201 void PatternList::virtual_pattern_del( Pattern* pattern )
202 {
203 for( int i=0; i<__patterns.size(); i++ ) __patterns[i]->virtual_patterns_del( pattern );
204 }
205
check_name(QString patternName)206 bool PatternList::check_name( QString patternName )
207 {
208 if (patternName == "") {
209 return false;
210 }
211
212 for (uint i = 0; i < __patterns.size(); i++) {
213 if ( __patterns[i]->get_name() == patternName) {
214 return false;
215 }
216 }
217 return true;
218 }
219
find_unused_pattern_name(QString sourceName)220 QString PatternList::find_unused_pattern_name( QString sourceName )
221 {
222 QString unusedPatternNameCandidate;
223
224 if( sourceName.isEmpty() ) {
225 sourceName = "Pattern 11";
226 }
227
228 int i = 1;
229 QString suffix = "";
230 unusedPatternNameCandidate = sourceName;
231
232 while( !check_name( unusedPatternNameCandidate + suffix ) ) {
233 suffix = " #" + QString::number(i);
234 i++;
235 }
236
237 unusedPatternNameCandidate += suffix;
238
239 return unusedPatternNameCandidate;
240 }
241
242 }
243
244
245
246 /* vim: set softtabstop=4 noexpandtab: */
247