- Timestamp:
- 01/14/18 11:24:22 (7 years ago)
- Location:
- cpp/frams
- Files:
-
- 8 edited
Legend:
- Unmodified
- Added
- Removed
-
cpp/frams/_demos/f0_variants_test.cpp
r534 r720 30 30 modelparam.select(&m); 31 31 gen+="m:"; 32 modelparam.save 2(gen,omit_default_values ? &defaultmodel : NULL);32 modelparam.saveSingleLine(gen,omit_default_values ? &defaultmodel : NULL); 33 33 34 34 Part *p; … … 40 40 partparam.select(p); 41 41 gen+="p:"; 42 partparam.save 2(gen,omit_default_values ? &defaultpart : NULL);42 partparam.saveSingleLine(gen,omit_default_values ? &defaultpart : NULL); 43 43 } 44 44 for (int i=0;j=(Joint*)m.getJoint(i);i++) … … 47 47 jointparam.setParamTab(j->usedelta?f0_joint_paramtab:f0_nodeltajoint_paramtab); 48 48 gen+="j:"; 49 jointparam.save 2(gen,omit_default_values ? &defaultjoint : NULL);49 jointparam.saveSingleLine(gen,omit_default_values ? &defaultjoint : NULL); 50 50 } 51 51 for (int i=0;n=(Neuro*)m.getNeuro(i);i++) … … 53 53 neuroparam.select(n); 54 54 gen+="n:"; 55 neuroparam.save 2(gen,omit_default_values ? &defaultneuro : NULL);55 neuroparam.saveSingleLine(gen,omit_default_values ? &defaultneuro : NULL); 56 56 } 57 57 for (int a=0;n=(Neuro*)m.getNeuro(a);a++) … … 67 67 connparam.select(&nc); 68 68 gen+="c:"; 69 connparam.save 2(gen,omit_default_values ? &defaultconn : NULL);69 connparam.saveSingleLine(gen,omit_default_values ? &defaultconn : NULL); 70 70 } 71 71 } … … 106 106 } 107 107 108 printf("\nthis example shows how to save a f0 genotype using low-level ParamInterface::save 2() calls\n");108 printf("\nthis example shows how to save a f0 genotype using low-level ParamInterface::saveSingleLine() calls\n"); 109 109 110 110 SString f0_skipping_defaults; … … 125 125 ( format 1 ) 126 126 127 this example shows how to save a f0 genotype using low-level ParamInterface::save 2() calls127 this example shows how to save a f0 genotype using low-level ParamInterface::saveSingleLine() calls 128 128 129 129 ==== with defdata (skips default values) ====== -
cpp/frams/genetics/fF/fF_genotype.h
r667 r720 36 36 { 37 37 SString s = serialized; 38 int p = 0; //position in string39 return ((param.load 2(s, p) == param.getPropCount()) && (p== s.len()));38 ParamInterface::LoadOptions opts; 39 return ((param.load(ParamInterface::FormatSingleLine, s, &opts) == param.getPropCount()) && (opts.offset == s.len())); 40 40 } 41 41 … … 43 43 { 44 44 SString tmp; 45 param.save 2(tmp, NULL/*object containing default values for comparison*/, false/*add CR*/, false/*force field names*/);45 param.saveSingleLine(tmp, NULL/*object containing default values for comparison*/, false/*add CR*/, false/*force field names*/); 46 46 return string(tmp.c_str()); 47 47 } -
cpp/frams/model/model.cpp
r660 r720 407 407 SString mod_props; 408 408 modelparam.select(this); 409 modelparam.save 2(mod_props, handle_defaults ? &defaultmodel : NULL, true, !handle_defaults);409 modelparam.saveSingleLine(mod_props, handle_defaults ? &defaultmodel : NULL, true, !handle_defaults); 410 410 if (mod_props.len() > 1) //are there any non-default values? ("\n" is empty) 411 411 { … … 419 419 len = gen.len(); 420 420 gen += "p:"; 421 partparam.save 2(gen, handle_defaults ? &defaultpart : NULL, true, !handle_defaults);421 partparam.saveSingleLine(gen, handle_defaults ? &defaultpart : NULL, true, !handle_defaults); 422 422 if (map) 423 423 map->add(len, gen.len() - 1, partToMap(i)); … … 429 429 jointparam.setParamTab(j->usedelta ? f0_joint_paramtab : f0_nodeltajoint_paramtab); 430 430 gen += "j:"; 431 jointparam.save 2(gen, handle_defaults ? &defaultjoint : NULL, true, !handle_defaults);431 jointparam.saveSingleLine(gen, handle_defaults ? &defaultjoint : NULL, true, !handle_defaults); 432 432 if (map) 433 433 map->add(len, gen.len() - 1, jointToMap(i)); … … 438 438 len = gen.len(); 439 439 gen += "n:"; 440 neuroparam.save 2(gen, handle_defaults ? &defaultneuro : NULL, true, !handle_defaults);440 neuroparam.saveSingleLine(gen, handle_defaults ? &defaultneuro : NULL, true, !handle_defaults); 441 441 if (map) 442 442 map->add(len, gen.len() - 1, neuroToMap(i)); … … 469 469 len = gen.len(); 470 470 gen += "c:"; 471 connparam.save 2(gen, handle_defaults ? &defaultconn : NULL, true, !handle_defaults);471 connparam.saveSingleLine(gen, handle_defaults ? &defaultconn : NULL, true, !handle_defaults); 472 472 if (map) 473 473 map->add(len, gen.len() - 1, neuroToMap(n->refno)); … … 582 582 { 583 583 error_message = SString::empty(); 584 int pos = 0; const char*t = line.c_str(); 585 for (; *t; t++, pos++) 584 const char*t = line.c_str(); 585 ParamInterface::LoadOptions opts; 586 for (; *t; t++, opts.offset++) 586 587 if (!strchr(" \r\t", *t)) break; 587 588 if (*t == '#') return 0; … … 592 593 Part *p = new Part(); 593 594 partparam.select(p); 594 pos += 2; 595 if (partparam.load2(line, pos) & ParamInterface::LOAD2_PARSE_FAILED) { delete p; error_message = "Invalid 'p:'"; return -1; } 595 opts.offset += 2; 596 partparam.load(ParamInterface::FormatSingleLine, line, &opts); 597 if (opts.parse_failed) { delete p; error_message = "Invalid 'p:'"; return -1; } 596 598 p->o.rotate(p->rot); 597 599 parts += p; … … 604 606 Param modelparam(f0_model_paramtab); 605 607 modelparam.select(this); 606 pos += 2; 607 if (modelparam.load2(line, pos) & ParamInterface::LOAD2_PARSE_FAILED) { error_message = "Invalid 'm:'"; return -1; } 608 opts.offset += 2; 609 modelparam.load(ParamInterface::FormatSingleLine, line, &opts); 610 if (opts.parse_failed) { error_message = "Invalid 'm:'"; return -1; } 608 611 return 0; 609 612 } … … 613 616 Joint *j = new Joint(); 614 617 jointparam.select(j); 615 pos+= 2;618 opts.offset += 2; 616 619 j->owner = this; 617 if (jointparam.load2(line, pos) & ParamInterface::LOAD2_PARSE_FAILED) { delete j; error_message = "Invalid 'j:'"; return -1; } 620 jointparam.load(ParamInterface::FormatSingleLine, line, &opts); 621 if (opts.parse_failed) { delete j; error_message = "Invalid 'j:'"; return -1; } 618 622 bool p1_ok = false, p2_ok = false; 619 623 if ((p1_ok = ((j->p1_refno >= 0) && (j->p1_refno < getPartCount()))) && … … 642 646 Neuro *nu = new Neuro(); 643 647 neuroparam.select(nu); 644 pos += 2; 645 if (neuroparam.load2(line, pos) & ParamInterface::LOAD2_PARSE_FAILED) { delete nu; error_message = "Invalid 'n:'"; return -1; } 648 opts.offset += 2; 649 neuroparam.load(ParamInterface::FormatSingleLine, line, &opts); 650 if (opts.parse_failed) { delete nu; error_message = "Invalid 'n:'"; return -1; } 646 651 #ifdef MODEL_V1_COMPATIBLE 647 652 if (nu->neuro_refno>=0) // parent specified... … … 718 723 NeuroConn c; 719 724 ncparam.select(&c); 720 pos += 2; 721 if (ncparam.load2(line, pos) & ParamInterface::LOAD2_PARSE_FAILED) { error_message = "Invalid 'c:'"; return -1; } 725 opts.offset += 2; 726 ncparam.load(ParamInterface::FormatSingleLine, line, &opts); 727 if (opts.parse_failed) { error_message = "Invalid 'c:'"; return -1; } 722 728 bool n1_ok = false, n2_ok = false; 723 729 if ((n1_ok = ((c.n1_refno >= 0) && (c.n1_refno < getNeuroCount()))) … … 741 747 Neuro *nu=new Neuro(); 742 748 neuroitemparam.select(nu); 743 pos+=3; 744 if (neuroitemparam.load2(line,pos) & ParamInterface::LOAD2_PARSE_FAILED) {delete nu; return -1;} 749 opts.offset+=3; 750 neuroitemparam.loadSingleLine(line,opts); 751 if (opts.parse_failed) {delete nu; return -1;} 745 752 // illegal parent? 746 753 if ((nu->neuro_refno<0)||(nu->neuro_refno>=old_getNeuroCount())) -
cpp/frams/neuro/neuroimpl.cpp
r492 r720 1 1 // This file is a part of Framsticks SDK. http://www.framsticks.com/ 2 // Copyright (C) 1999-201 5Maciej Komosinski and Szymon Ulatowski.2 // Copyright (C) 1999-2018 Maciej Komosinski and Szymon Ulatowski. 3 3 // See LICENSE.txt for details. 4 4 … … 14 14 #endif 15 15 16 const int NeuroImpl::ENDDRAWING =-9999;17 const int NeuroImpl::MAXDRAWINGXY =0xffff;18 19 int NeuroNetImpl::mytags_id =0;16 const int NeuroImpl::ENDDRAWING = -9999; 17 const int NeuroImpl::MAXDRAWINGXY = 0xffff; 18 19 int NeuroNetImpl::mytags_id = 0; 20 20 21 21 ///////////////////////////////////////////////////////// 22 22 23 23 #define FIELDSTRUCT NeuroNetConfig 24 static ParamEntry nncfg_paramtab[] =25 { 26 {"Creature: Neurons",1,3,"nnsim",},27 {"randinit",1,0,"Random initialization","f 0 10 0.01",FIELD(randominit),"Allowed range for initializing all neuron states with uniform distribution random numbers and zero mean. Set to 0 for deterministic initialization."},28 {"nnoise",1,0,"Noise","f 0 1 0",FIELD(nnoise),"Gaussian neural noise: a random value is added to each neural output in each simulation step. Set standard deviation here to add random noise, or 0 for deterministic simulation."},29 {"touchrange",1,0,"T receptor range","f 0 100 1",FIELD(touchrange),},30 {0,0,0,},31 }; 24 static ParamEntry nncfg_paramtab[] = 25 { 26 { "Creature: Neurons", 1, 3, "nnsim", }, 27 { "randinit", 1, 0, "Random initialization", "f 0 10 0.01", FIELD(randominit), "Allowed range for initializing all neuron states with uniform distribution random numbers and zero mean. Set to 0 for deterministic initialization." }, 28 { "nnoise", 1, 0, "Noise", "f 0 1 0", FIELD(nnoise), "Gaussian neural noise: a random value is added to each neural output in each simulation step. Set standard deviation here to add random noise, or 0 for deterministic simulation." }, 29 { "touchrange", 1, 0, "T receptor range", "f 0 100 1", FIELD(touchrange), }, 30 { 0, 0, 0, }, 31 }; 32 32 #undef FIELDSTRUCT 33 33 34 34 NeuroNetConfig::NeuroNetConfig(NeuroFactory *fac) 35 :par(nncfg_paramtab, this),36 37 38 39 35 :par(nncfg_paramtab, this), 36 randominit(0.01), 37 nnoise(0), 38 touchrange(1), 39 factory(fac) 40 40 {} 41 41 … … 44 44 NeuroNetImpl::NeuroNetImpl(Model& model, NeuroNetConfig& conf 45 45 #ifdef NEURO_SIGNALS 46 , ChannelSpace *ch47 #endif 48 )49 :mod(model), config(conf),50 isbuilt(1),errorcount(0)46 , ChannelSpace *ch 47 #endif 48 ) 49 :mod(model), config(conf), 50 isbuilt(1), errorcount(0) 51 51 #ifdef NEURO_SIGNALS 52 ,channels(ch) 53 #endif 54 { 55 if (!mytags_id) mytags_id=mod.userdata.newID(); 56 57 Neuro *n; 58 NeuroImpl *ni; 59 Joint *j; 60 int i; 61 DB(printf("makeNeuroNet(%p)\n",&mod)); 62 63 minorder=3; maxorder=0; 64 errorcount=0; 65 66 for (i=0;j=mod.getJoint(i);i++) 67 j->flags&=~(4+8); // todo: !!!neuroitems shouldn't use model fields!!! 68 69 for (i=0;n=mod.getNeuro(i);i++) 70 { 71 ni=conf.factory->createNeuroImpl(n); 72 n->userdata[mytags_id]=ni; 73 if (!ni) { errorcount++; 74 logPrintf("NeuroNetImpl","create",LOG_WARN,"neuron #%d (%s) implementation not available", 75 i,n->getClassName().c_str()); 76 continue; } // implementation not available?! 77 ni->owner=this; 78 ni->neuro=n; 79 ni->readParam(); 80 } 81 82 for (i=0;n=mod.getNeuro(i);i++) 83 { 84 n->state+=(rnd01-0.5)*config.randominit; 85 ni=(NeuroImpl*)n->userdata[mytags_id]; 86 if (!ni) continue; 87 if (!ni->lateinit()) 88 { ni->status=NeuroImpl::InitError; errorcount++; 89 logPrintf("NeuroNetImpl","create",LOG_WARN,"neuron #%d (%s) initialization failed", 90 i,n->getClassName().c_str()); 91 continue; } 92 ni->status=NeuroImpl::InitOk; 93 int order=ni->getSimOrder(); 94 if (order<0) order=0; else if (order>2) order=2; 95 if (order<minorder) minorder=order; 96 if (order>maxorder) maxorder=order; 97 neurons[order]+=ni; 98 if (ni->getNeedPhysics()) 99 neurons[3]+=ni; 100 } 101 cnode=mod.delmodel_list.add(STATRICKCALLBACK(this,&NeuroNetImpl::destroyNN,0)); 52 , channels(ch) 53 #endif 54 { 55 if (!mytags_id) mytags_id = mod.userdata.newID(); 56 57 Neuro *n; 58 NeuroImpl *ni; 59 Joint *j; 60 int i; 61 DB(printf("makeNeuroNet(%p)\n", &mod)); 62 63 minorder = 3; maxorder = 0; 64 errorcount = 0; 65 66 for (i = 0; j = mod.getJoint(i); i++) 67 j->flags &= ~(4 + 8); // todo: !!!neuroitems shouldn't use model fields!!! 68 69 for (i = 0; n = mod.getNeuro(i); i++) 70 { 71 ni = conf.factory->createNeuroImpl(n); 72 n->userdata[mytags_id] = ni; 73 if (!ni) 74 { 75 errorcount++; 76 logPrintf("NeuroNetImpl", "create", LOG_WARN, "neuron #%d (%s) implementation not available", 77 i, n->getClassName().c_str()); 78 continue; 79 } // implementation not available?! 80 ni->owner = this; 81 ni->neuro = n; 82 ni->readParam(); 83 } 84 85 for (i = 0; n = mod.getNeuro(i); i++) 86 { 87 n->state += (rnd01 - 0.5)*config.randominit; 88 ni = (NeuroImpl*)n->userdata[mytags_id]; 89 if (!ni) continue; 90 if (!ni->lateinit()) 91 { 92 ni->status = NeuroImpl::InitError; 93 errorcount++; 94 logPrintf("NeuroNetImpl", "create", LOG_WARN, "neuron #%d (%s) initialization failed", 95 i, n->getClassName().c_str()); 96 continue; 97 } 98 ni->status = NeuroImpl::InitOk; 99 int order = ni->getSimOrder(); 100 if (order < 0) order = 0; else if (order>2) order = 2; 101 if (order < minorder) minorder = order; 102 if (order > maxorder) maxorder = order; 103 neurons[order] += ni; 104 if (ni->getNeedPhysics()) 105 neurons[3] += ni; 106 } 107 cnode = mod.delmodel_list.add(STATRICKCALLBACK(this, &NeuroNetImpl::destroyNN, 0)); 102 108 } 103 109 104 110 void NeuroNetImpl::destroyNN(CALLBACKARGS) 105 111 { 106 if (!isbuilt) return;107 DB(printf("destroyNeuroNet(%p)\n",&mod));108 NeuroImpl *ni;109 Neuro *n;110 for (int i=0;n=mod.getNeuro(i);i++)111 { 112 ni=(NeuroImpl*)n->userdata[mytags_id];113 delete ni;114 n->userdata[mytags_id]=0;115 } 116 mod.delmodel_list.remove(cnode);117 isbuilt=0; errorcount=0;118 delete this;112 if (!isbuilt) return; 113 DB(printf("destroyNeuroNet(%p)\n", &mod)); 114 NeuroImpl *ni; 115 Neuro *n; 116 for (int i = 0; n = mod.getNeuro(i); i++) 117 { 118 ni = (NeuroImpl*)n->userdata[mytags_id]; 119 delete ni; 120 n->userdata[mytags_id] = 0; 121 } 122 mod.delmodel_list.remove(cnode); 123 isbuilt = 0; errorcount = 0; 124 delete this; 119 125 } 120 126 121 127 NeuroNetImpl::~NeuroNetImpl() 122 128 { 123 destroyNN(0,0);129 destroyNN(0, 0); 124 130 } 125 131 126 132 void NeuroNetImpl::simulateNeuroNet() 127 133 { 128 NeuroImpl *ni; 129 for (int order=minorder;order<=maxorder;order++) 130 { 134 NeuroImpl *ni; 135 for (int order = minorder; order <= maxorder; order++) 136 { 137 int i; 138 SList &nlist = neurons[order]; 139 for (i = 0; ni = (NeuroImpl*)nlist(i); i++) 140 ni->go(); 141 for (i = 0; ni = (NeuroImpl*)nlist(i); i++) 142 ni->commit(); 143 } 144 } 145 146 void NeuroNetImpl::simulateNeuroPhysics() 147 { 148 NeuroImpl *ni; 131 149 int i; 132 SList &nlist=neurons[order]; 133 for (i=0;ni=(NeuroImpl*)nlist(i);i++) 134 ni->go(); 135 for (i=0;ni=(NeuroImpl*)nlist(i);i++) 136 ni->commit(); 137 } 138 } 139 140 void NeuroNetImpl::simulateNeuroPhysics() 141 { 142 NeuroImpl *ni; 143 int i; 144 SList &nlist=neurons[3]; 145 for (i=0;ni=(NeuroImpl*)nlist(i);i++) 146 ni->goPhysics(); 150 SList &nlist = neurons[3]; 151 for (i = 0; ni = (NeuroImpl*)nlist(i); i++) 152 ni->goPhysics(); 147 153 } 148 154 … … 151 157 void NeuroImpl::setChannelCount(int c) 152 158 { 153 if (c<1) c=1; 154 if (c==channels) return; 155 if (c<channels) {channels=c; chstate.trim(c-1); chnewstate.trim(c-1); return;} 156 double s=getState(channels-1); 157 chnewstate.setSize(c-1); 158 chstate.setSize(c-1); 159 for(int i=channels;i<c;i++) 160 {chstate(i-1)=s; chnewstate(i-1)=s;} 161 channels=c; 162 } 163 164 void NeuroImpl::setState(double st,int channel) 165 { 166 validateNeuroState(st); 167 if (channel>=channels) channel=channels-1; 168 if (channel<=0) {newstate=st;return;} 169 chnewstate(channel-1)=st; 170 } 171 172 void NeuroImpl::setCurrentState(double st,int channel) 173 { 174 validateNeuroState(st); 175 if (channel>=channels) channel=channels-1; 176 if (channel<=0) {neuro->state=st; return;} 177 chstate(channel-1)=st; 159 if (c < 1) c = 1; 160 if (c == channels) return; 161 if (c < channels) { channels = c; chstate.trim(c - 1); chnewstate.trim(c - 1); return; } 162 double s = getState(channels - 1); 163 chnewstate.setSize(c - 1); 164 chstate.setSize(c - 1); 165 for (int i = channels; i < c; i++) 166 { 167 chstate(i - 1) = s; 168 chnewstate(i - 1) = s; 169 } 170 channels = c; 171 } 172 173 void NeuroImpl::setState(double st, int channel) 174 { 175 validateNeuroState(st); 176 if (channel >= channels) channel = channels - 1; 177 if (channel <= 0) { newstate = st; return; } 178 chnewstate(channel - 1) = st; 179 } 180 181 void NeuroImpl::setCurrentState(double st, int channel) 182 { 183 validateNeuroState(st); 184 if (channel >= channels) channel = channels - 1; 185 if (channel <= 0) { neuro->state = st; return; } 186 chstate(channel - 1) = st; 178 187 } 179 188 180 189 double NeuroImpl::getNewState(int channel) 181 190 { 182 if (neuro->flags&Neuro::HoldState) return getState(channel);183 if (channel>=channels) channel=channels-1;184 if (channel<=0) {return newstate;}185 return chnewstate(channel-1);191 if (neuro->flags&Neuro::HoldState) return getState(channel); 192 if (channel >= channels) channel = channels - 1; 193 if (channel <= 0) { return newstate; } 194 return chnewstate(channel - 1); 186 195 } 187 196 188 197 double NeuroImpl::getState(int channel) 189 198 { 190 if (channel>=channels) channel=channels-1;191 if (channel<=0) return neuro->state;192 return chstate(channel-1);199 if (channel >= channels) channel = channels - 1; 200 if (channel <= 0) return neuro->state; 201 return chstate(channel - 1); 193 202 } 194 203 195 204 void NeuroImpl::commit() 196 205 { 197 if (!(neuro->flags&Neuro::HoldState))198 { 199 if (channels>1)200 chstate=chnewstate;201 neuro->state=newstate;202 if (owner->getConfig().nnoise>0.0)206 if (!(neuro->flags&Neuro::HoldState)) 207 { 208 if (channels > 1) 209 chstate = chnewstate; 210 neuro->state = newstate; 211 if (owner->getConfig().nnoise > 0.0) 203 212 { 204 neuro->state+=RndGen.GaussStd()*owner->getConfig().nnoise;205 if (channels>1)206 for(int i=0;i<chstate.size();i++)207 chstate(0)+=RndGen.GaussStd()*owner->getConfig().nnoise;213 neuro->state += RndGen.GaussStd()*owner->getConfig().nnoise; 214 if (channels > 1) 215 for (int i = 0; i < chstate.size(); i++) 216 chstate(0) += RndGen.GaussStd()*owner->getConfig().nnoise; 208 217 } 209 218 } … … 212 221 int NeuroImpl::getInputChannelCount(int i) 213 222 { 214 if ((i<0)||(i >= neuro->getInputCount())) return 1;215 Neuro *nu=neuro->getInput(i);216 NeuroImpl *ni=NeuroNetImpl::getImpl(nu);217 if (!ni) return 1;218 return ni->channels;219 } 220 221 double NeuroImpl::getInputState(int i, int channel)222 { 223 if ((i<0)||(i >= neuro->getInputCount())) return 0;224 Neuro *nu=neuro->getInput(i);225 if (channel<=0) return nu->state;226 NeuroImpl *ni=NeuroNetImpl::getImpl(nu);227 if (!ni) return nu->state;228 if (channel>=ni->channels) channel=ni->channels-1;229 if (!channel) return nu->state;230 return ni->chstate(channel-1);223 if ((i < 0) || (i >= neuro->getInputCount())) return 1; 224 Neuro *nu = neuro->getInput(i); 225 NeuroImpl *ni = NeuroNetImpl::getImpl(nu); 226 if (!ni) return 1; 227 return ni->channels; 228 } 229 230 double NeuroImpl::getInputState(int i, int channel) 231 { 232 if ((i < 0) || (i >= neuro->getInputCount())) return 0; 233 Neuro *nu = neuro->getInput(i); 234 if (channel <= 0) return nu->state; 235 NeuroImpl *ni = NeuroNetImpl::getImpl(nu); 236 if (!ni) return nu->state; 237 if (channel >= ni->channels) channel = ni->channels - 1; 238 if (!channel) return nu->state; 239 return ni->chstate(channel - 1); 231 240 } 232 241 233 242 double NeuroImpl::getWeightedInputState(int i, int channel) 234 243 { 235 if ((i<0)||(i >= neuro->getInputCount())) return 0;236 double w;237 Neuro *nu=neuro->getInput(i,w);238 if (channel<=0) return nu->state * w;239 NeuroImpl *ni=NeuroNetImpl::getImpl(nu);240 if (!ni) return nu->state * w;241 if (channel>=ni->channels) channel=ni->channels-1;242 if (!channel) return w * nu->state;243 return w * ni->chstate(channel-1);244 if ((i < 0) || (i >= neuro->getInputCount())) return 0; 245 double w; 246 Neuro *nu = neuro->getInput(i, w); 247 if (channel <= 0) return nu->state * w; 248 NeuroImpl *ni = NeuroNetImpl::getImpl(nu); 249 if (!ni) return nu->state * w; 250 if (channel >= ni->channels) channel = ni->channels - 1; 251 if (!channel) return w * nu->state; 252 return w * ni->chstate(channel - 1); 244 253 } 245 254 246 255 double NeuroImpl::getInputSum(int startwith) 247 256 { 248 if (startwith<0) return 0;249 Neuro *inp;250 double sum=0.0;251 while(inp=neuro->getInput(startwith++))252 sum+=inp->state;253 return sum;257 if (startwith < 0) return 0; 258 Neuro *inp; 259 double sum = 0.0; 260 while (inp = neuro->getInput(startwith++)) 261 sum += inp->state; 262 return sum; 254 263 } 255 264 256 265 double NeuroImpl::getWeightedInputSum(int startwith) 257 266 { 258 if (startwith<0) return 0;259 Neuro *inp;260 double sum=0.0;261 double w;262 while(inp=neuro->getInput(startwith++,w))263 sum+=inp->state*w;264 return sum;267 if (startwith < 0) return 0; 268 Neuro *inp; 269 double sum = 0.0; 270 double w; 271 while (inp = neuro->getInput(startwith++, w)) 272 sum += inp->state*w; 273 return sum; 265 274 } 266 275 267 276 void NeuroImpl::readParam() 268 277 { 269 Param par; 270 if (!paramentries) return; 271 par.setParamTab(paramentries); 272 par.select(this); 273 par.setDefault(); 274 int zero=0; 275 par.load2(neuro->getClassParams(),zero); 278 Param par; 279 if (!paramentries) return; 280 par.setParamTab(paramentries); 281 par.select(this); 282 par.setDefault(); 283 par.load(ParamInterface::FormatSingleLine, neuro->getClassParams()); 276 284 } 277 285 278 286 Param& NeuroImpl::getStaticParam() 279 287 { 280 static Param p(neuroimpl_tab,0,"Neuro");281 return p;288 static Param p(neuroimpl_tab, 0, "Neuro"); 289 return p; 282 290 } 283 291 … … 291 299 292 300 #define FIELDSTRUCT NeuroImpl 293 ParamEntry neuroimpl_tab[] =294 { 295 {"Neuro",1,27+NEUROIMPL_SIGNAL_PROPS,"Neuro","Live Neuron object."},296 297 {"getInputState",0,0,"Get input signal","p f(d input)",PROCEDURE(p_get),},298 {"getInputWeight",0,0,"Get input weight","p f(d input)",PROCEDURE(p_getweight),},299 {"getWeightedInputState",0,0,"Get weighted input signal","p f(d input)",PROCEDURE(p_getw),},300 {"getInputSum",0,0,"Get signal sum","p f(d input)",PROCEDURE(p_getsum),},301 {"getWeightedInputSum",0,0,"Get weighted signal sum","p f(d input)",PROCEDURE(p_getwsum),"Uses any number of inputs starting with the specified input. getWeightedInputSum(0)=weightedInputSum"},302 {"getInputCount",0,PARAM_READONLY,"Get input count","d",GETONLY(count),},303 {"inputSum",0,PARAM_READONLY,"Full signal sum","f",GETONLY(sum),},304 {"weightedInputSum",0,PARAM_READONLY,"Full weighted signal sum","f",GETONLY(wsum),},305 {"getInputChannelCount",0,0,"Get channel count for input","p d(d input)",PROCEDURE(p_getchancount),},306 {"getInputStateChannel",0,0,"Get input signal from channel","p f(d input,d channel)",PROCEDURE(p_getchan),},307 {"getWeightedInputStateChannel",0,0,"Get weighted input signal from channel","p f(d input,d channel)",PROCEDURE(p_getwchan),},308 {"state",0,0,"Neuron state (channel 0)","f",GETSET(state),"When read, returns the current neuron state.\nWhen written, sets the 'internal' neuron state that will become current in the next step.\nTypically you should use this field, and not currState."},309 {"channelCount",0,0,"Number of output channels","d",GETSET(channels),},310 {"getStateChannel",0,0,"Get state for channel","p f(d channel)",PROCEDURE(p_getstate),},311 {"setStateChannel",0,0,"Set state for channel","p(d channel,f value)",PROCEDURE(p_setstate),},312 {"hold",0,0,"Hold state","d 0 1",GETSET(hold),"\"Holding\" means keeping the neuron state as is, blocking the regular neuron operation. This is useful when your script needs to inject some control signals into the NN. Without \"holding\", live neurons would be constantly overwriting your changes, and the rest of the NN could see inconsistent states, depending on the connections. Setting hold=1 ensures the neuron state will be only set by you, and not by the neuron. The enforced signal value can be set using Neuro.currState before or after setting hold=1. Set hold=0 to resume normal operation.",},313 {"currState",0,0,"Current neuron state (channel 0)","f",GETSET(cstate),"When read, it behaves just like the 'state' field.\nWhen written, changes the current neuron state immediately, which disturbs the regular synchronous NN operation.\nThis feature should only be used while controlling the neuron 'from outside' (like a neuro probe) and not in the neuron definition. See also: Neuro.hold",},314 {"setCurrStateChannel",0,0,"Set current neuron state for channel","p(d channel,f value)",PROCEDURE(p_setcstate),"Analogous to \"currState\"."},315 {"position_x",0,PARAM_READONLY,"Position x","f",GETONLY(position_x),},316 {"position_y",0,PARAM_READONLY,"Position y","f",GETONLY(position_y),},317 {"position_z",0,PARAM_READONLY,"Position z","f",GETONLY(position_z),},318 {"creature",0,PARAM_READONLY,"Gets owner creature","o Creature",GETONLY(creature),},319 {"part",0,PARAM_READONLY,"The Part object where this neuron is located","o MechPart",GETONLY(part),},320 {"joint",0,PARAM_READONLY,"The Joint object where this neuron is located","o MechJoint",GETONLY(joint),},321 {"neuroproperties",0,PARAM_READONLY,"Custom neuron fields","o NeuroProperties",GETONLY(fields),322 "Neurons can have different fields depending on their class. Script neurons have their fields defined using the \"property:\" syntax. If you develop a custom neuron script you should use the NeuroProperties object for accessing your own neuron fields. The Neuro.neuroproperties property is meant for accessing the neuron fields from the outside script.\n"323 "Examples:\n"324 "var c=Populations.createFromString(\"X[N]\");\n"325 "Simulator.print(\"standard neuron inertia=\"+c.getNeuro(0).neuroproperties.in);\n"326 "c=Populations.createFromString(\"X[Nn,e:0.1]\");\n"327 "Simulator.print(\"noisy neuron error rate=\"+c.getNeuro(0).neuroproperties.e);\n"328 "\n"329 "The Interface object can be used to discover which fields are available for a certain neuron object:\n"330 "c=Populations.createFromString(\"X[N]\");\n"331 "var iobj=Interface.makeFrom(c.getNeuro(0).neuroproperties);\n"332 "var i;\n"333 "for(i=0;i<iobj.size;i++)\n"334 " Simulator.print(iobj.getId(i)+\" (\"+iobj.getName(i)+\")\");",},335 {"def",0,PARAM_READONLY,"Neuron definition from which this live neuron was built","o NeuroDef",GETONLY(neurodef),},336 {"classObject",0,PARAM_READONLY,"Neuron class for this neuron","o NeuroClass",GETONLY(classObject),},301 ParamEntry neuroimpl_tab[] = 302 { 303 { "Neuro", 1, 27 + NEUROIMPL_SIGNAL_PROPS, "Neuro", "Live Neuron object." }, 304 305 { "getInputState", 0, 0, "Get input signal", "p f(d input)", PROCEDURE(p_get), }, 306 { "getInputWeight", 0, 0, "Get input weight", "p f(d input)", PROCEDURE(p_getweight), }, 307 { "getWeightedInputState", 0, 0, "Get weighted input signal", "p f(d input)", PROCEDURE(p_getw), }, 308 { "getInputSum", 0, 0, "Get signal sum", "p f(d input)", PROCEDURE(p_getsum), }, 309 { "getWeightedInputSum", 0, 0, "Get weighted signal sum", "p f(d input)", PROCEDURE(p_getwsum), "Uses any number of inputs starting with the specified input. getWeightedInputSum(0)=weightedInputSum" }, 310 { "getInputCount", 0, PARAM_READONLY, "Get input count", "d", GETONLY(count), }, 311 { "inputSum", 0, PARAM_READONLY, "Full signal sum", "f", GETONLY(sum), }, 312 { "weightedInputSum", 0, PARAM_READONLY, "Full weighted signal sum", "f", GETONLY(wsum), }, 313 { "getInputChannelCount", 0, 0, "Get channel count for input", "p d(d input)", PROCEDURE(p_getchancount), }, 314 { "getInputStateChannel", 0, 0, "Get input signal from channel", "p f(d input,d channel)", PROCEDURE(p_getchan), }, 315 { "getWeightedInputStateChannel", 0, 0, "Get weighted input signal from channel", "p f(d input,d channel)", PROCEDURE(p_getwchan), }, 316 { "state", 0, 0, "Neuron state (channel 0)", "f", GETSET(state), "When read, returns the current neuron state.\nWhen written, sets the 'internal' neuron state that will become current in the next step.\nTypically you should use this field, and not currState." }, 317 { "channelCount", 0, 0, "Number of output channels", "d", GETSET(channels), }, 318 { "getStateChannel", 0, 0, "Get state for channel", "p f(d channel)", PROCEDURE(p_getstate), }, 319 { "setStateChannel", 0, 0, "Set state for channel", "p(d channel,f value)", PROCEDURE(p_setstate), }, 320 { "hold", 0, 0, "Hold state", "d 0 1", GETSET(hold), "\"Holding\" means keeping the neuron state as is, blocking the regular neuron operation. This is useful when your script needs to inject some control signals into the NN. Without \"holding\", live neurons would be constantly overwriting your changes, and the rest of the NN could see inconsistent states, depending on the connections. Setting hold=1 ensures the neuron state will be only set by you, and not by the neuron. The enforced signal value can be set using Neuro.currState before or after setting hold=1. Set hold=0 to resume normal operation.", }, 321 { "currState", 0, 0, "Current neuron state (channel 0)", "f", GETSET(cstate), "When read, it behaves just like the 'state' field.\nWhen written, changes the current neuron state immediately, which disturbs the regular synchronous NN operation.\nThis feature should only be used while controlling the neuron 'from outside' (like a neuro probe) and not in the neuron definition. See also: Neuro.hold", }, 322 { "setCurrStateChannel", 0, 0, "Set current neuron state for channel", "p(d channel,f value)", PROCEDURE(p_setcstate), "Analogous to \"currState\"." }, 323 { "position_x", 0, PARAM_READONLY, "Position x", "f", GETONLY(position_x), }, 324 { "position_y", 0, PARAM_READONLY, "Position y", "f", GETONLY(position_y), }, 325 { "position_z", 0, PARAM_READONLY, "Position z", "f", GETONLY(position_z), }, 326 { "creature", 0, PARAM_READONLY, "Gets owner creature", "o Creature", GETONLY(creature), }, 327 { "part", 0, PARAM_READONLY, "The Part object where this neuron is located", "o MechPart", GETONLY(part), }, 328 { "joint", 0, PARAM_READONLY, "The Joint object where this neuron is located", "o MechJoint", GETONLY(joint), }, 329 { "neuroproperties", 0, PARAM_READONLY, "Custom neuron fields", "o NeuroProperties", GETONLY(fields), 330 "Neurons can have different fields depending on their class. Script neurons have their fields defined using the \"property:\" syntax. If you develop a custom neuron script you should use the NeuroProperties object for accessing your own neuron fields. The Neuro.neuroproperties property is meant for accessing the neuron fields from the outside script.\n" 331 "Examples:\n" 332 "var c=Populations.createFromString(\"X[N]\");\n" 333 "Simulator.print(\"standard neuron inertia=\"+c.getNeuro(0).neuroproperties.in);\n" 334 "c=Populations.createFromString(\"X[Nn,e:0.1]\");\n" 335 "Simulator.print(\"noisy neuron error rate=\"+c.getNeuro(0).neuroproperties.e);\n" 336 "\n" 337 "The Interface object can be used to discover which fields are available for a certain neuron object:\n" 338 "c=Populations.createFromString(\"X[N]\");\n" 339 "var iobj=Interface.makeFrom(c.getNeuro(0).neuroproperties);\n" 340 "var i;\n" 341 "for(i=0;i<iobj.size;i++)\n" 342 " Simulator.print(iobj.getId(i)+\" (\"+iobj.getName(i)+\")\");", }, 343 { "def", 0, PARAM_READONLY, "Neuron definition from which this live neuron was built", "o NeuroDef", GETONLY(neurodef), }, 344 { "classObject", 0, PARAM_READONLY, "Neuron class for this neuron", "o NeuroClass", GETONLY(classObject), }, 337 345 #ifdef NEURO_SIGNALS 338 {"signals",0,PARAM_READONLY,"Signals","o NeuroSignals",FIELD(sigs_obj),},339 #endif 340 341 {0,0,0,},346 { "signals", 0, PARAM_READONLY, "Signals", "o NeuroSignals", FIELD(sigs_obj), }, 347 #endif 348 349 { 0, 0, 0, }, 342 350 }; 343 351 #undef FIELDSTRUCT 344 352 345 353 #ifdef NEURO_SIGNALS 346 ParamEntry neurosignals_paramtab[] =347 348 {"NeuroSignals",1,8,"NeuroSignals","Signals attached to a neuron.\nSee also: Signal, WorldSignals, CreatureSignals.\nscripts/light.neuro and scripts/seelight.neuro are simple custom neuron examples demonstrating how to send/receive signals between creatures.",},354 ParamEntry neurosignals_paramtab[] = 355 { 356 { "NeuroSignals", 1, 8, "NeuroSignals", "Signals attached to a neuron.\nSee also: Signal, WorldSignals, CreatureSignals.\nscripts/light.neuro and scripts/seelight.neuro are simple custom neuron examples demonstrating how to send/receive signals between creatures.", }, 349 357 350 358 #define FIELDSTRUCT NeuroSignals 351 SIGNPAR_ADD(""),352 SIGNPAR_RECEIVE(""),353 SIGNPAR_RECEIVESET(""),354 SIGNPAR_RECEIVEFILTER(""),355 SIGNPAR_RECEIVESINGLE(""),359 SIGNPAR_ADD(""), 360 SIGNPAR_RECEIVE(""), 361 SIGNPAR_RECEIVESET(""), 362 SIGNPAR_RECEIVEFILTER(""), 363 SIGNPAR_RECEIVESINGLE(""), 356 364 #undef FIELDSTRUCT 357 365 358 366 #define FIELDSTRUCT SignalSet 359 SIGNSETPAR_GET,360 SIGNSETPAR_SIZE,361 SIGNSETPAR_CLEAR,367 SIGNSETPAR_GET, 368 SIGNSETPAR_SIZE, 369 SIGNSETPAR_CLEAR, 362 370 #undef FIELDSTRUCT 363 {0,0,0,},364 }; 371 { 0, 0, 0, }, 372 }; 365 373 366 374 Param& NeuroSignals::getStaticParam() 367 375 { 368 static Param p(neurosignals_paramtab,0);369 return p;376 static Param p(neurosignals_paramtab, 0); 377 return p; 370 378 } 371 379 #endif 372 380 373 381 #ifdef NEURO_SIGNALS 374 class NeuroSigSource : public SigSource375 { 376 377 NeuroImpl* owner;378 379 NeuroSigSource(NeuroImpl *n,Creature *c):SigSource(0,c),owner(n) {}380 bool update();382 class NeuroSigSource : public SigSource 383 { 384 protected: 385 NeuroImpl* owner; 386 public: 387 NeuroSigSource(NeuroImpl *n, Creature *c) :SigSource(0, c), owner(n) {} 388 bool update(); 381 389 }; 382 390 383 391 bool NeuroSigSource::update() 384 392 { 385 Pt3D p;386 if (owner->getPosition(p))387 { 388 setLocation(p);389 return true;390 } 391 return false;393 Pt3D p; 394 if (owner->getPosition(p)) 395 { 396 setLocation(p); 397 return true; 398 } 399 return false; 392 400 } 393 401 394 402 Creature *NeuroSignals::getCreature() 395 403 { 396 if (!cr)397 { 398 cr=owner->getCreature();399 } 400 return cr;404 if (!cr) 405 { 406 cr = owner->getCreature(); 407 } 408 return cr; 401 409 } 402 410 403 411 void NeuroSignals::p_add(PARAMPROCARGS) 404 412 { 405 SigSource *s=new NeuroSigSource(owner,getCreature());406 if (owner->owner->channels)407 { 408 SigChannel *ch=owner->owner->channels->getChannel(args->getString(),true);409 ch->addSource(s);410 } 411 else412 SigChannel::dummy_channel.addSource(s);413 sigs+=s;414 s->setupObject(ret);413 SigSource *s = new NeuroSigSource(owner, getCreature()); 414 if (owner->owner->channels) 415 { 416 SigChannel *ch = owner->owner->channels->getChannel(args->getString(), true); 417 ch->addSource(s); 418 } 419 else 420 SigChannel::dummy_channel.addSource(s); 421 sigs += s; 422 s->setupObject(ret); 415 423 } 416 424 417 425 void NeuroSignals::p_receive(PARAMPROCARGS) 418 426 { 419 SigChannel *ch; Pt3D p;420 if (owner->owner->channels && (ch=owner->owner->channels->getChannel(args->getString(),false)) && owner->getPosition(p))421 ret->setDouble(ch->receive(&p,getCreature()));422 else423 ret->setDouble(0);427 SigChannel *ch; Pt3D p; 428 if (owner->owner->channels && (ch = owner->owner->channels->getChannel(args->getString(), false)) && owner->getPosition(p)) 429 ret->setDouble(ch->receive(&p, getCreature())); 430 else 431 ret->setDouble(0); 424 432 } 425 433 426 434 void NeuroSignals::p_receiveFilter(PARAMPROCARGS) 427 435 { 428 SigChannel *ch; Pt3D p;429 if (owner->owner->channels && (ch=owner->owner->channels->getChannel(args[3].getString(),false)) && owner->getPosition(p))430 ret->setDouble(ch->receive(&p,getCreature(),args[2].getDouble(),args[1].getDouble(),args[0].getDouble()));431 else432 ret->setDouble(0);436 SigChannel *ch; Pt3D p; 437 if (owner->owner->channels && (ch = owner->owner->channels->getChannel(args[3].getString(), false)) && owner->getPosition(p)) 438 ret->setDouble(ch->receive(&p, getCreature(), args[2].getDouble(), args[1].getDouble(), args[0].getDouble())); 439 else 440 ret->setDouble(0); 433 441 } 434 442 435 443 void NeuroSignals::p_receiveSet(PARAMPROCARGS) 436 444 { 437 SigChannel *ch; Pt3D p;438 SigVector *vec=new SigVector();439 if (owner->owner->channels && (ch=owner->owner->channels->getChannel(args[1].getString(),false)) && owner->getPosition(p))440 ch->receiveSet(vec,&p,getCreature(),args[0].getDouble());441 ret->setObject(vec->makeObject());445 SigChannel *ch; Pt3D p; 446 SigVector *vec = new SigVector(); 447 if (owner->owner->channels && (ch = owner->owner->channels->getChannel(args[1].getString(), false)) && owner->getPosition(p)) 448 ch->receiveSet(vec, &p, getCreature(), args[0].getDouble()); 449 ret->setObject(vec->makeObject()); 442 450 } 443 451 444 452 void NeuroSignals::p_receiveSingle(PARAMPROCARGS) 445 453 { 446 SigChannel *ch; Pt3D p;447 if (owner->owner->channels && (ch=owner->owner->channels->getChannel(args[1].getString(),false)) && owner->getPosition(p))448 { 449 SigSource *src=ch->receiveSingle(&p,getCreature(),args[0].getDouble(),0,1e99);450 if (src)454 SigChannel *ch; Pt3D p; 455 if (owner->owner->channels && (ch = owner->owner->channels->getChannel(args[1].getString(), false)) && owner->getPosition(p)) 456 { 457 SigSource *src = ch->receiveSingle(&p, getCreature(), args[0].getDouble(), 0, 1e99); 458 if (src) 451 459 { 452 src->setupObject(ret);453 return;460 src->setupObject(ret); 461 return; 454 462 } 455 463 } 456 ret->setEmpty();464 ret->setEmpty(); 457 465 } 458 466 #endif … … 460 468 #ifndef SDK_WITHOUT_FRAMS 461 469 extern ParamEntry creature_paramtab[]; 462 static Param creature_param(creature_paramtab, 0);470 static Param creature_param(creature_paramtab, 0); 463 471 #endif 464 472 … … 466 474 { 467 475 #ifndef SDK_WITHOUT_FRAMS 468 CreatMechObject *cmo=(CreatMechObject *)neuro->owner->userdata[CreatMechObject::modeltags_id];469 return cmo->creature;476 CreatMechObject *cmo = (CreatMechObject *)neuro->owner->userdata[CreatMechObject::modeltags_id]; 477 return cmo->creature; 470 478 #else 471 return 0;479 return 0; 472 480 #endif 473 481 } … … 476 484 { 477 485 #ifndef SDK_WITHOUT_FRAMS 478 ret->setObject(ExtObject(&creature_param,getCreature()));486 ret->setObject(ExtObject(&creature_param, getCreature())); 479 487 #endif 480 488 } … … 483 491 { 484 492 #ifndef SDK_WITHOUT_FRAMS 485 Part *pa;486 if (pa=neuro->getPart())487 ret->setObject(ExtObject(&MechPart::getStaticParam(),((MechPart *)pa->userdata[CreatMechObject::modeltags_id])));488 else489 ret->setEmpty();493 Part *pa; 494 if (pa = neuro->getPart()) 495 ret->setObject(ExtObject(&MechPart::getStaticParam(), ((MechPart *)pa->userdata[CreatMechObject::modeltags_id]))); 496 else 497 ret->setEmpty(); 490 498 #endif 491 499 } … … 494 502 { 495 503 #ifndef SDK_WITHOUT_FRAMS 496 Joint *jo;497 if (jo=neuro->getJoint())498 ret->setObject(ExtObject(&MechJoint::getStaticParam(),((MechJoint*)jo->userdata[CreatMechObject::modeltags_id])));499 else500 ret->setEmpty();504 Joint *jo; 505 if (jo = neuro->getJoint()) 506 ret->setObject(ExtObject(&MechJoint::getStaticParam(), ((MechJoint*)jo->userdata[CreatMechObject::modeltags_id]))); 507 else 508 ret->setEmpty(); 501 509 #endif 502 510 } … … 505 513 { 506 514 #ifndef SDK_WITHOUT_FRAMS 507 Part *pa; Joint *jo; 508 if (pa=neuro->getPart()) 509 {pos=((MechPart *)pa->userdata[CreatMechObject::modeltags_id])->p; return true;} 510 if (jo=neuro->getJoint()) 511 { 512 if (neuro->getClass()->getVisualHints() & NeuroClass::AtFirstPart) 513 pos=((MechPart*)jo->part1->userdata[CreatMechObject::modeltags_id])->p; 514 else if (neuro->getClass()->getVisualHints() & NeuroClass::AtSecondPart) 515 pos=((MechPart*)jo->part2->userdata[CreatMechObject::modeltags_id])->p; 516 else pos=(((MechPart*)jo->part1->userdata[CreatMechObject::modeltags_id])->p 517 +((MechPart*)jo->part2->userdata[CreatMechObject::modeltags_id])->p)/2; 518 return true; 519 } 520 #endif 521 return false; 515 Part *pa; Joint *jo; 516 if (pa = neuro->getPart()) 517 { 518 pos = ((MechPart *)pa->userdata[CreatMechObject::modeltags_id])->p; 519 return true; 520 } 521 if (jo = neuro->getJoint()) 522 { 523 if (neuro->getClass()->getVisualHints() & NeuroClass::AtFirstPart) 524 pos = ((MechPart*)jo->part1->userdata[CreatMechObject::modeltags_id])->p; 525 else if (neuro->getClass()->getVisualHints() & NeuroClass::AtSecondPart) 526 pos = ((MechPart*)jo->part2->userdata[CreatMechObject::modeltags_id])->p; 527 else pos = (((MechPart*)jo->part1->userdata[CreatMechObject::modeltags_id])->p 528 + ((MechPart*)jo->part2->userdata[CreatMechObject::modeltags_id])->p) / 2; 529 return true; 530 } 531 #endif 532 return false; 522 533 } 523 534 524 535 void NeuroImpl::get_position_x(ExtValue *ret) 525 {Pt3D pos; if (getPosition(pos)) ret->setDouble(pos.x); else ret->setEmpty();} 536 { 537 Pt3D pos; 538 if (getPosition(pos)) ret->setDouble(pos.x); else ret->setEmpty(); 539 } 526 540 void NeuroImpl::get_position_y(ExtValue *ret) 527 {Pt3D pos; if (getPosition(pos)) ret->setDouble(pos.y); else ret->setEmpty();} 541 { 542 Pt3D pos; 543 if (getPosition(pos)) ret->setDouble(pos.y); else ret->setEmpty(); 544 } 528 545 void NeuroImpl::get_position_z(ExtValue *ret) 529 {Pt3D pos; if (getPosition(pos)) ret->setDouble(pos.z); else ret->setEmpty();} 546 { 547 Pt3D pos; 548 if (getPosition(pos)) ret->setDouble(pos.z); else ret->setEmpty(); 549 } 530 550 531 551 532 552 void NeuroImpl::createFieldsObject() 533 553 { 534 fields_param=new Param(paramentries?paramentries:(ParamEntry*)&empty_paramtab,this,"NeuroProperties");535 fields_object=new ExtObject(fields_param);554 fields_param = new Param(paramentries ? paramentries : (ParamEntry*)&empty_paramtab, this, "NeuroProperties"); 555 fields_object = new ExtObject(fields_param); 536 556 } 537 557 538 558 void NeuroImpl::get_fields(ExtValue *ret) 539 559 { 540 if (!fields_object)541 createFieldsObject();542 ret->setObject(*fields_object);560 if (!fields_object) 561 createFieldsObject(); 562 ret->setObject(*fields_object); 543 563 } 544 564 545 565 void NeuroImpl::get_neurodef(ExtValue *ret) 546 566 { 547 ret->setObject(ExtObject(&Neuro::getStaticParam(),neuro));567 ret->setObject(ExtObject(&Neuro::getStaticParam(), neuro)); 548 568 } 549 569 … … 551 571 { 552 572 #ifndef SDK_WITHOUT_FRAMS 553 NeuroClassExt::makeStaticObject(ret,neuroclass);573 NeuroClassExt::makeStaticObject(ret, neuroclass); 554 574 #endif 555 575 } … … 557 577 NeuroImpl::~NeuroImpl() 558 578 { 559 if (fields_param)560 { 561 delete fields_param;562 delete fields_object;563 } 564 } 579 if (fields_param) 580 { 581 delete fields_param; 582 delete fields_object; 583 } 584 } -
cpp/frams/param/multiparamload.cpp
r535 r720 1 1 // This file is a part of Framsticks SDK. http://www.framsticks.com/ 2 // Copyright (C) 1999-201 5Maciej Komosinski and Szymon Ulatowski.2 // Copyright (C) 1999-2018 Maciej Komosinski and Szymon Ulatowski. 3 3 // See LICENSE.txt for details. 4 4 … … 10 10 void MultiParamLoader::init() 11 11 { 12 file=0; ownfile=0;13 status=0;14 reset();12 file = 0; ownfile = 0; 13 status = 0; 14 reset(); 15 15 } 16 16 17 17 void MultiParamLoader::reset() 18 18 { 19 status=0;20 breakcond=OnError;21 aborting=false;22 emptyparam.setParamTab(empty_paramtab);23 linenum=0;19 status = 0; 20 breakcond = OnError; 21 aborting = false; 22 emptyparam.setParamTab(empty_paramtab); 23 linenum = 0; 24 24 } 25 25 26 26 int MultiParamLoader::findObject(const ExtObject &o) 27 27 { 28 for(int i=0;i<objects.size();i++)29 if ((*objects(i))==o)30 return i;31 return -1;28 for (int i = 0; i < objects.size(); i++) 29 if ((*objects(i)) == o) 30 return i; 31 return -1; 32 32 } 33 33 34 34 void MultiParamLoader::removeObject(const ExtObject &o) 35 35 { 36 int i=findObject(o);37 if (i>=0)38 { 39 delete objects(i);40 objects-=i;36 int i = findObject(o); 37 if (i >= 0) 38 { 39 delete objects(i); 40 objects -= i; 41 41 } 42 42 } … … 44 44 void MultiParamLoader::clearObjects() 45 45 { 46 FOREACH(ExtObject*,o,objects)47 delete o;48 objects.clear();46 FOREACH(ExtObject*, o, objects) 47 delete o; 48 objects.clear(); 49 49 } 50 50 51 51 void MultiParamLoader::load() 52 52 { 53 clearstack();54 if (!file)55 { 56 lasterror="can't open file";57 status=OnError;58 return;59 } 60 status=Loading;61 aborting=false;53 clearstack(); 54 if (!file) 55 { 56 lasterror = "can't open file"; 57 status = OnError; 58 return; 59 } 60 status = Loading; 61 aborting = false; 62 62 } 63 63 64 64 void MultiParamLoader::abort() 65 65 { 66 if (file && ownfile)67 { 68 delete file;69 file=0;70 } 71 clearstack();72 status=Finished;73 aborting=true;66 if (file && ownfile) 67 { 68 delete file; 69 file = 0; 70 } 71 clearstack(); 72 status = Finished; 73 aborting = true; 74 74 } 75 75 76 76 void MultiParamLoader::load(VirtFILE *f) 77 77 { 78 abort();79 ownfile=0;80 file=f;81 load();78 abort(); 79 ownfile = 0; 80 file = f; 81 load(); 82 82 } 83 83 84 84 void MultiParamLoader::load(const char* filename) 85 85 { 86 abort();87 ownfile=1;88 file=Vfopen(filename,FOPEN_READ_BINARY);89 load();86 abort(); 87 ownfile = 1; 88 file = Vfopen(filename, FOPEN_READ_BINARY); 89 load(); 90 90 } 91 91 92 92 int MultiParamLoader::go() 93 93 { 94 SString buf; 95 if (status==OnError) return status; 96 int unexpected_line = 0; 97 while (!finished()) 98 { 99 if ((status==BeforeObject) || ((status==BeforeUnknown) && !lastobject.isEmpty())) 100 { 101 Param tmp_param; 102 ParamInterface *pi=lastobject.getParamInterface(tmp_param); 103 pi->load(file,true,&aborting,&linenum); 104 if ((status!=Finished) && maybeBreak(AfterObject)) 105 break; 106 unexpected_line = 0; 107 continue; 108 } 109 else if (status==BeforeUnknown) 110 { 111 logPrintf("MultiParamLoader","go",LOG_WARN,"Skipping object '%s'",lastunknown.c_str()); 112 loadObjectNow(&emptyparam,false); 113 continue; 114 } 115 if (!loadSStringLine(file,buf)) 116 { 117 unexpected_line = 0; 118 if (!returnFromIncluded()) 119 { 120 abort(); 121 break; 122 } 123 else 94 SString buf; 95 if (status == OnError) return status; 96 int unexpected_line = 0; 97 while (!finished()) 98 { 99 if ((status == BeforeObject) || ((status == BeforeUnknown) && !lastobject.isEmpty())) 100 { 101 Param tmp_param; 102 ParamInterface *pi = lastobject.getParamInterface(tmp_param); 103 ParamInterface::LoadOptions opts; 104 opts.abortable = &aborting; 105 opts.warn_unknown_fields = true; 106 opts.linenum = &linenum; 107 pi->load(ParamInterface::FormatMultiLine, file, &opts); 108 if ((status != Finished) && maybeBreak(AfterObject)) 109 break; 110 unexpected_line = 0; 124 111 continue; 125 112 } 126 linenum++; 127 if (buf[0]=='#') 128 { 129 unexpected_line = 0; 130 if (buf.startsWith("#include")) 131 { 132 const char* t=strchr(buf.c_str(),'\"'),*t2=0; 133 if (t) 134 t2=strchr(t+1,'\"'); 135 if (t2) 113 else if (status == BeforeUnknown) 114 { 115 logPrintf("MultiParamLoader", "go", LOG_WARN, "Skipping object '%s'", lastunknown.c_str()); 116 loadObjectNow(&emptyparam, false); 117 continue; 118 } 119 if (!loadSStringLine(file, buf)) 120 { 121 unexpected_line = 0; 122 if (!returnFromIncluded()) 123 { 124 abort(); 125 break; 126 } 127 else 128 continue; 129 } 130 linenum++; 131 if (buf[0] == '#') 132 { 133 unexpected_line = 0; 134 if (buf.startsWith("#include")) 135 { 136 const char* t = strchr(buf.c_str(), '\"'), *t2 = 0; 137 if (t) 138 t2 = strchr(t + 1, '\"'); 139 if (t2) 136 140 { 137 SString filename(t+1,t2-t-1);138 includeFile(filename);141 SString filename(t + 1, t2 - t - 1); 142 includeFile(filename); 139 143 } 140 else144 else 141 145 { 142 const char* thisfilename=file->VgetPath();143 logPrintf("MultiParamLoader","go",LOG_WARN,"invalid \"%s\"%s%s",buf.c_str(),144 (thisfilename?" in ":""),(thisfilename?thisfilename:""));146 const char* thisfilename = file->VgetPath(); 147 logPrintf("MultiParamLoader", "go", LOG_WARN, "invalid \"%s\"%s%s", buf.c_str(), 148 (thisfilename ? " in " : ""), (thisfilename ? thisfilename : "")); 145 149 } 150 continue; 151 } 152 else if ((status != Finished) && maybeBreak(OnComment)) 153 { 154 lastcomment = buf.substr(1); 155 break; 156 } 146 157 continue; 147 } 148 else if ((status!=Finished) && maybeBreak(OnComment)) 149 { 150 lastcomment=buf.substr(1); 151 break; 152 } 153 continue; 154 } 155 buf=trim(buf); 156 if (buf.len()==0) 157 unexpected_line = 0; 158 else if ((buf.len()>1)&&(buf[buf.len()-1]==':')) 159 { 160 unexpected_line = 0; 161 lastunknown=0; 162 lastunknown=buf.substr(0,buf.len()-1); 163 lastobject.setEmpty(); 164 FOREACH(ExtObject*,o,objects) 165 { 166 if (!strcmp(o->interfaceName(),lastunknown.c_str())) {lastobject=*o; break;} 158 } 159 buf = trim(buf); 160 if (buf.len() == 0) 161 unexpected_line = 0; 162 else if ((buf.len() > 1) && (buf[buf.len() - 1] == ':')) 163 { 164 unexpected_line = 0; 165 lastunknown = 0; 166 lastunknown = buf.substr(0, buf.len() - 1); 167 lastobject.setEmpty(); 168 FOREACH(ExtObject*, o, objects) 169 { 170 if (!strcmp(o->interfaceName(), lastunknown.c_str())) { lastobject = *o; break; } 167 171 } 168 172 if (!lastobject.isEmpty()) 169 173 { 170 174 if (maybeBreak(BeforeObject)) 171 175 break; 172 176 } 173 177 else 174 178 { 175 179 if (maybeBreak(BeforeUnknown)) 176 180 break; 177 } 178 179 } 181 } 182 183 } 184 else 185 { 186 switch (unexpected_line) 187 { 188 case 0: 189 { 190 const char* thisfilename = file->VgetPath(); 191 logPrintf("MultiParamLoader", "go", LOG_WARN, "Ignored unexpected line %d%s", 192 linenum, 193 thisfilename ? SString::sprintf(" while reading '%s'", thisfilename).c_str() : ""); 194 } 195 break; 196 197 case 1: 198 logPrintf("MultiParamLoader", "go", LOG_WARN, "The following line(s) were also unexpected and were ignored"); 199 break; 200 } 201 unexpected_line++; 202 } 203 } 204 return status; 205 } 206 207 bool MultiParamLoader::alreadyIncluded(const char* filename) 208 { 209 int i; 210 const char* t; 211 for (i = 0; i < filestack.size(); i++) 212 { 213 t = filestack(i)->VgetPath(); 214 if (!t) continue; 215 if (!strcmp(filename, t)) return true; 216 } 217 return false; 218 } 219 220 void MultiParamLoader::includeFile(SString& filename) 221 { 222 const char* thisfilename = file->VgetPath(); 223 SString newfilename; 224 const char* t = thisfilename ? strrchr(thisfilename, PATH_SEPARATOR_CHAR) : 0; 225 226 if (thisfilename && t) 227 { 228 newfilename.append(thisfilename, t - thisfilename + 1); 229 newfilename += filename; 230 } 180 231 else 181 { 182 switch(unexpected_line) 183 { 184 case 0: 185 { 186 const char* thisfilename=file->VgetPath(); 187 logPrintf("MultiParamLoader","go", LOG_WARN, "Ignored unexpected line %d%s", 188 linenum, 189 thisfilename ? SString::sprintf(" while reading '%s'",thisfilename).c_str():""); 190 } 191 break; 192 193 case 1: 194 logPrintf("MultiParamLoader","go", LOG_WARN, "The following line(s) were also unexpected and were ignored"); 195 break; 196 } 197 unexpected_line++; 198 } 199 } 200 return status; 201 } 202 203 bool MultiParamLoader::alreadyIncluded(const char* filename) 204 { 205 int i; 206 const char* t; 207 for(i=0;i<filestack.size();i++) 208 { 209 t=filestack(i)->VgetPath(); 210 if (!t) continue; 211 if (!strcmp(filename,t)) return true; 212 } 213 return false; 214 } 215 216 void MultiParamLoader::includeFile(SString& filename) 217 { 218 const char* thisfilename=file->VgetPath(); 219 SString newfilename; 220 const char* t=thisfilename?strrchr(thisfilename,PATH_SEPARATOR_CHAR):0; 221 222 if (thisfilename && t) 223 { 224 newfilename.append(thisfilename,t-thisfilename+1); 225 newfilename+=filename; 226 } 227 else 228 newfilename=filename; 229 230 if (alreadyIncluded(newfilename.c_str())) 231 { 232 logPrintf("MultiParamLoader","include",LOG_WARN,"circular reference ignored (\"%s\")", 233 filename.c_str()); 234 return; 235 } 236 237 VirtFILE *f=Vfopen(newfilename.c_str(),FOPEN_READ_BINARY); 238 if (!f) 239 { 240 logPrintf("MultiParamLoader","include",LOG_WARN,"\"%s\" not found",newfilename.c_str()); 241 } 242 else 243 { 244 filestack+=file; 245 file=f; 232 newfilename = filename; 233 234 if (alreadyIncluded(newfilename.c_str())) 235 { 236 logPrintf("MultiParamLoader", "include", LOG_WARN, "circular reference ignored (\"%s\")", 237 filename.c_str()); 238 return; 239 } 240 241 VirtFILE *f = Vfopen(newfilename.c_str(), FOPEN_READ_BINARY); 242 if (!f) 243 { 244 logPrintf("MultiParamLoader", "include", LOG_WARN, "\"%s\" not found", newfilename.c_str()); 245 } 246 else 247 { 248 filestack += file; 249 file = f; 246 250 } 247 251 } … … 249 253 VirtFILE* MultiParamLoader::popstack() 250 254 { 251 if (!filestack.size()) return 0;252 VirtFILE* f=filestack(filestack.size()-1);253 filestack.remove(filestack.size()-1);254 return f;255 if (!filestack.size()) return 0; 256 VirtFILE* f = filestack(filestack.size() - 1); 257 filestack.remove(filestack.size() - 1); 258 return f; 255 259 } 256 260 257 261 void MultiParamLoader::clearstack() 258 262 { 259 VirtFILE *f;260 while(f=popstack()) delete f;263 VirtFILE *f; 264 while (f = popstack()) delete f; 261 265 } 262 266 263 267 bool MultiParamLoader::returnFromIncluded() 264 268 { 265 if (!filestack.size()) return false; 266 if (file) delete file; 267 file=popstack(); 268 return true; 269 } 270 271 int MultiParamLoader::loadObjectNow(const ExtObject& o,bool warn_unknown_fields) 272 { 273 Param tmp_param; 274 ParamInterface *pi=o.getParamInterface(tmp_param); 275 pi->load(file,warn_unknown_fields,&aborting,&linenum); 276 status=AfterObject; 277 return 0; 269 if (!filestack.size()) return false; 270 if (file) delete file; 271 file = popstack(); 272 return true; 273 } 274 275 int MultiParamLoader::loadObjectNow(const ExtObject& o, bool warn_unknown_fields) 276 { 277 Param tmp_param; 278 ParamInterface *pi = o.getParamInterface(tmp_param); 279 ParamInterface::LoadOptions opts; 280 opts.abortable = &aborting; 281 opts.warn_unknown_fields = warn_unknown_fields; 282 opts.linenum = &linenum; 283 pi->load(ParamInterface::FormatMultiLine, file, &opts); 284 status = AfterObject; 285 return 0; 278 286 } 279 287 280 288 int MultiParamLoader::run() 281 289 { 282 int stat;283 breakOn(OnError);284 while(stat=go())285 if (stat==OnError)290 int stat; 291 breakOn(OnError); 292 while (stat = go()) 293 if (stat == OnError) 286 294 { 287 295 abort(); 288 296 return 0; 289 297 } 290 return 1;298 return 1; 291 299 } 292 300 293 301 SString MultiParamLoader::currentFilePathForErrorMessage() 294 302 { 295 const char* filename=getFile()->VgetPath();296 if (filename)297 return SString::sprintf(" in '%s'",filename);298 return SString::empty();299 } 303 const char* filename = getFile()->VgetPath(); 304 if (filename) 305 return SString::sprintf(" in '%s'", filename); 306 return SString::empty(); 307 } -
cpp/frams/param/param.cpp
r704 r720 10 10 #include "common/log.h" 11 11 #include <frams/util/sstringutils.h> 12 #include <common/virtfile/stringfile.h> 12 13 13 14 //#define SAVE_ALL_NAMES … … 356 357 } 357 358 358 void SimpleAbstractParam::save 2(SString& f, void *defdata, bool addcr, bool all_names)359 void SimpleAbstractParam::saveSingleLine(SString& f, void *defdata, bool addcr, bool all_names) 359 360 { // defdata!=NULL -> does not save default values 360 361 const char *p; … … 421 422 } 422 423 423 int ParamInterface::load(VirtFILE* f, bool warn_unknown_fields, bool *abortable, int *linenum) 424 int ParamInterface::load(FileFormat format, VirtFILE* f, LoadOptions *options) 425 { 426 LoadOptions default_options; 427 if (options == NULL) 428 options = &default_options; 429 switch (format) 430 { 431 case FormatMultiLine: 432 return loadMultiLine(f, *options); 433 434 case FormatSingleLine: 435 { 436 StringFILE *sf = dynamic_cast<StringFILE*>(f); 437 SString s; 438 if (sf) 439 { 440 s = sf->getString().c_str(); 441 options->offset += sf->Vtell(); 442 } 443 else 444 { 445 if (!loadSStringLine(f, s)) 446 return -1; 447 } 448 return loadSingleLine(s, *options); 449 } 450 } 451 return -1; 452 } 453 454 int ParamInterface::load(FileFormat format, const SString &s, LoadOptions *options) 455 { 456 LoadOptions default_options; 457 if (options == NULL) 458 options = &default_options; 459 switch (format) 460 { 461 case FormatMultiLine: 462 { 463 string std_string(s.c_str()); 464 StringFILE f(std_string); 465 return loadMultiLine(&f, *options); 466 } 467 468 case FormatSingleLine: 469 return loadSingleLine(s, *options); 470 } 471 return -1; 472 } 473 474 int ParamInterface::loadMultiLine(VirtFILE* f, LoadOptions &options) 424 475 { 425 476 SString buf; … … 434 485 if ((i = findId("beforeLoad")) >= 0) 435 486 call(i, NULL, NULL); 436 while (((! abortable) || (!*abortable)) && loadSStringLine(f, buf))437 { 438 if ( linenum) (*linenum)++;487 while (((!options.abortable) || (!*options.abortable)) && loadSStringLine(f, buf)) 488 { 489 if (options.linenum) (*options.linenum)++; 439 490 const char* t = buf.c_str(); 440 491 p0 = t; while (isblank(*p0)) p0++; … … 448 499 case 0: 449 500 logPrintf("ParamInterface", "load", LOG_WARN, "Ignored unexpected line %s while reading object '%s'", 450 linenum ?451 SString::sprintf("%d", * linenum).c_str()501 options.linenum ? 502 SString::sprintf("%d", *options.linenum).c_str() 452 503 : SString::sprintf("'%s'", p0).c_str(), 453 504 getName()); … … 472 523 { 473 524 fileinfo = SString::sprintf(" while reading from '%s'", fname); 474 if ( linenum)475 fileinfo += SString::sprintf(" (line %d)", * linenum);525 if (options.linenum) 526 fileinfo += SString::sprintf(" (line %d)", *options.linenum); 476 527 } 477 528 logPrintf("ParamInterface", "load", LOG_WARN, "Multiple '%s.%s' fields found%s", getName(), id(i), fileinfo.c_str()); … … 496 547 int ch; while ((ch = f->Vgetc()) != EOF) if (ch == '\n') break; 497 548 unquoteTilde(s); 498 if ( linenum && (flags(i)&PARAM_LINECOMMENT))499 s = SString::sprintf("@file %s\n@line %d\n", f->VgetPath(), * linenum + 1) + s;549 if (options.linenum && (flags(i)&PARAM_LINECOMMENT)) 550 s = SString::sprintf("@file %s\n@line %d\n", f->VgetPath(), *options.linenum + 1) + s; 500 551 set(i, s.c_str()); 501 if ( linenum)502 (* linenum) += lfcount;552 if (options.linenum) 553 (*options.linenum) += lfcount; 503 554 } 504 555 else … … 510 561 } 511 562 } 512 else if ( warn_unknown_fields)563 else if (options.warn_unknown_fields) 513 564 { 514 565 SString name(p0, p_len); … … 521 572 if (!readUntilTilde(f, s)) 522 573 closingTildeError(this, f, -1); 523 if ( linenum)574 if (options.linenum) 524 575 { 525 576 const char* tmp = s.c_str(); … … 530 581 lfcount++; tmp++; 531 582 } 532 (* linenum) += lfcount;583 (*options.linenum) += lfcount; 533 584 } 534 585 int ch; while ((ch = f->Vgetc()) != EOF) if (ch == '\n') break; … … 705 756 { 706 757 const char *t; 707 if (((*(t = type(i))) == 'd') && (strchr(t, '~') !=NULL)) //type is int and contains enum labels758 if (((*(t = type(i))) == 'd') && (strchr(t, '~') != NULL)) //type is int and contains enum labels 708 759 { 709 760 paInt mn, mx, def; … … 1131 1182 } 1132 1183 1133 int ParamInterface::load 2(const SString &s, int &poz)1184 int ParamInterface::loadSingleLine(const SString &s, LoadOptions &options) 1134 1185 { 1135 1186 int i; // the index number of the parameter … … 1145 1196 SString tmpvalue; 1146 1197 bool parse_failed = false; 1147 if ( poz>= s.len()) return fields_loaded;1148 t = s.c_str() + poz;1149 1150 lin = getline(s, poz, len); // all fields must be encoded in a single line1198 if (options.offset >= s.len()) return fields_loaded; 1199 t = s.c_str() + options.offset; 1200 1201 lin = getline(s, options.offset, len); // all fields must be encoded in a single line 1151 1202 if (!len) return fields_loaded; // empty line = end 1152 1203 i = 0; … … 1241 1292 #endif 1242 1293 } 1243 return fields_loaded | (parse_failed ? LOAD2_PARSE_FAILED : 0); 1294 if (parse_failed) options.parse_failed = true; 1295 return fields_loaded; 1244 1296 } 1245 1297 -
cpp/frams/param/param.h
r650 r720 28 28 #define PARAM_NOSTATIC 256 //< (FramScript) don't access this member in a static object (ClassName.field) 29 29 #define PARAM_CONST 512 //< (FramScript) constant value 30 #define PARAM_CANOMITNAME 1024 //< affects Param::save 2()/load2() - for example one-liners in f0 genetic encoding30 #define PARAM_CANOMITNAME 1024 //< affects Param::saveSingleLine()/loadSingleLine() - for example one-liners in f0 genetic encoding 31 31 #define PARAM_DONTLOAD 2048 //< Param::load() skips this field 32 32 #define PARAM_NOISOLATION 4096 //< don't use proxy object in master/slave interactions … … 170 170 void quickCopyFrom(ParamInterface *src); 171 171 172 enum FileFormat { FormatMultiLine, FormatSingleLine }; // FormatJSON in the future? 173 struct LoadOptions { 174 bool warn_unknown_fields; bool *abortable; int *linenum; int offset; bool parse_failed; 175 LoadOptions() : warn_unknown_fields(false), abortable(NULL), linenum(NULL), offset(0), parse_failed(false) {} 176 }; 177 172 178 int save(VirtFILE*, const char* altname = NULL, bool force = 0); 173 179 int saveprop(VirtFILE*, int i, const char* p, bool force = 0); 174 int load(VirtFILE*, bool warn_unknown_fields = true, bool *abortable = NULL, int *linenum = NULL);///< @return the number of fields loaded 175 int load2(const SString &, int &);///< @return the number of fields loaded (or'ed with LOAD2_PARSE_FAILED if a parsing error was detected) 180 181 int load(FileFormat format, VirtFILE*, LoadOptions *load_options = NULL);///< @return the number of fields loaded 182 int load(FileFormat format, const SString &, LoadOptions *load_options = NULL);///< @return the number of fields loaded 183 protected: 184 int loadMultiLine(VirtFILE*, LoadOptions &options);///< @return the number of fields loaded 185 int loadSingleLine(const SString &, LoadOptions &options);///< @return the number of fields loaded 186 public: 176 187 177 188 static const char* SERIALIZATION_PREFIX; 178 static const int LOAD2_PARSE_FAILED = (1 << 30); ///< this bit is set in return value from load2 if a parse error was detected while loading. usage: if (load2(...) & LOAD2_PARSE_FAILED) ...179 static const int LOAD2_IGNORE_PARSE_FAILED = (~LOAD2_PARSE_FAILED); ///< bitmask to be used if the parsing error is to be ignored. usage: int number_of_loaded_fields=load2(...) & LOAD2_IGNORE_PARSE_FAILED;180 189 181 190 static bool isValidTypeDescription(const char* t); … … 299 308 300 309 int isequal(int i, void* defdata); 301 void save 2(SString&, void *defdata, bool addcr = true, bool all_names = true);310 void saveSingleLine(SString&, void *defdata, bool addcr = true, bool all_names = true); 302 311 303 312 virtual void setDefault(); -
cpp/frams/param/syntparam.cpp
r286 r720 8 8 #include <math.h> 9 9 10 SyntParam::SyntParam(ParamEntry *init_pe, SString* autostr,bool handle_defaults_when_saving)10 SyntParam::SyntParam(ParamEntry *init_pe, SString* autostr, bool handle_defaults_when_saving) 11 11 :autostring(autostr) 12 12 { 13 Param::setParamTab(init_pe);14 pe=ParamObject::makeParamTab(this);15 Param::setParamTab(pe);16 if (handle_defaults_when_saving)13 Param::setParamTab(init_pe); 14 pe = ParamObject::makeParamTab(this); 15 Param::setParamTab(pe); 16 if (handle_defaults_when_saving) 17 17 { 18 def_obj=ParamObject::makeObject(pe); 19 Param::select(def_obj); 18 def_obj = ParamObject::makeObject(pe); 19 Param::select(def_obj); 20 Param::setDefault(); 21 } 22 else 23 def_obj = NULL; 24 obj = ParamObject::makeObject(pe); 25 Param::select(obj); 20 26 Param::setDefault(); 21 } 22 else 23 def_obj=NULL; 24 obj=ParamObject::makeObject(pe); 25 Param::select(obj); 26 Param::setDefault(); 27 revert(); 27 revert(); 28 28 } 29 29 30 30 SyntParam::SyntParam(const SyntParam& src) 31 :Param(), autostring(src.autostring)31 :Param(), autostring(src.autostring) 32 32 { 33 Param::setParamTab(src.pe);34 pe=ParamObject::makeParamTab(this);35 Param::setParamTab(pe);36 obj=ParamObject::dupObject(src.obj);37 def_obj=src.def_obj ? ParamObject::dupObject(src.def_obj) : NULL;38 Param::select(obj);33 Param::setParamTab(src.pe); 34 pe = ParamObject::makeParamTab(this); 35 Param::setParamTab(pe); 36 obj = ParamObject::dupObject(src.obj); 37 def_obj = src.def_obj ? ParamObject::dupObject(src.def_obj) : NULL; 38 Param::select(obj); 39 39 } 40 40 41 41 SyntParam::~SyntParam() 42 42 { 43 update();44 ParamObject::freeParamTab(pe);45 ParamObject::freeObject(obj);46 ParamObject::freeObject(def_obj);43 update(); 44 ParamObject::freeParamTab(pe); 45 ParamObject::freeObject(obj); 46 ParamObject::freeObject(def_obj); 47 47 } 48 48 49 49 void SyntParam::update(SString *s) 50 50 { 51 if (!s) s=autostring;52 if (s) {*s=""; Param::save2(*s,def_obj,0);}51 if (!s) s = autostring; 52 if (s) { *s = ""; Param::saveSingleLine(*s, def_obj, 0); } 53 53 } 54 54 55 55 void SyntParam::revert(SString *s) 56 56 { 57 if (!s) s=autostring; 58 if (s) { 59 int p=0; 60 Param::load2(*s,p); 57 if (!s) s = autostring; 58 if (s) { 59 Param::load(ParamInterface::FormatSingleLine, *s); 61 60 } 62 61 } 63 64 65 66 67
Note: See TracChangeset
for help on using the changeset viewer.