Real Time Open Sound Control librtosc
bundle-foreach.h
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2017 Johannes Lorenz
3  *
4  * Permission is hereby granted, free of charge, to any person obtaining a
5  * copy of this software and associated documentation files (the "Software"),
6  * to deal in the Software without restriction, including without limitation
7  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8  * and/or sell copies of the Software, and to permit persons to whom the
9  * Software is furnished to do so, subject to the following conditions:
10  *
11  * The above copyright notice and this permission notice (including the next
12  * paragraph) shall be included in all copies or substantial portions of the
13  * Software.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16  * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18  * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
19  * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
20  * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22  * DEALINGS IN THE SOFTWARE.
23  */
24 
31 #ifndef BUNDLE_FOREACH
32 #define BUNDLE_FOREACH
33 
34 #include <cctype>
35 #include <cstdlib>
36 #include <cstdio>
37 #include "ports.h"
38 
39 namespace rtosc {
40 
46 template<class F>
47 void bundle_foreach(const struct Port& p, const char* name, char* old_end,
48  /* data which is only being used by the ftors */
49  const char* name_buffer, const struct Ports& base,
50  void* data, void* runtime, const F& ftor,
51  /* options */
52  bool expand_bundles = true,
53  bool cut_afterwards = true)
54 {
55  char *pos = old_end;
56  while(*name != '#') *pos++ = *name++;
57  const unsigned max = atoi(name+1);
58  while(isdigit(*++name)) ;
59 
60  char* pos2;
61 
62  if(expand_bundles)
63  for(unsigned i=0; i<max; ++i)
64  {
65  const char* name2_2 = name;
66  pos2 = pos + sprintf(pos,"%d",i);
67 
68  // append everything behind the '#' (for cases like a#N/b)
69  while(*name2_2 && *name2_2 != ':')
70  *pos2++ = *name2_2++;
71 
72  ftor(&p, name_buffer, old_end, base, data, runtime);
73  }
74  else
75  {
76  const char* name2_2 = name;
77  pos2 = pos;
78 
79  // append everything behind the '#' (for cases like a#N/b)
80  while(*name2_2 && *name2_2 != ':')
81  *pos2++ = *name2_2++;
82 
83  ftor(&p, name_buffer, old_end, base, data, runtime);
84  }
85 
86  if(cut_afterwards)
87  *old_end = 0;
88  else
89  *pos2 = 0;
90 }
91 
92 // use this function if you don't want to do anything in bundle_foreach
93 // (useful to create paths if cut_afterwards is true)
94 inline void bundle_foreach_do_nothing(const Port*, const char*, const char*,
95  const Ports&, void*, void*){}
96 
97 }
98 
99 #endif // BUNDLE_FOREACH
Port in rtosc dispatching hierarchy.
Definition: ports.h:96
void bundle_foreach(const struct Port &p, const char *name, char *old_end, const char *name_buffer, const struct Ports &base, void *data, void *runtime, const F &ftor, bool expand_bundles=true, bool cut_afterwards=true)
Execute a callback for all bundle elements of a bundle port.
Definition: bundle-foreach.h:47
Ports - a dispatchable collection of Port entries.
Definition: ports.h:157
Collection of functions for ports.