SineMC.h
Go to the documentation of this file.00001
00002 #ifndef INCLUDED_SineMC_h_
00003 #define INCLUDED_SineMC_h_
00004
00005 #include "Motion/MotionCommand.h"
00006 #include "Motion/MotionManager.h"
00007 #include <cmath>
00008
00009
00010 class SineMC : public MotionCommand {
00011 public:
00012
00013 SineMC() : MotionCommand(), lastUpdate(get_time()+FrameTime*NumFrames) {
00014 for(unsigned int i=0; i<NumOutputs; ++i) {
00015 amp[i] = (outputRanges[i][MaxRange] - outputRanges[i][MinRange]) / 2;
00016 period[i]=2000;
00017 offset[i] = (outputRanges[i][MaxRange] + outputRanges[i][MinRange]) / 2;
00018 sync(i,lastUpdate);
00019 }
00020 }
00021
00022
00023 virtual void setWeight(unsigned int i, float w) { cmds[i].weight=w; }
00024
00025 virtual float getWeight(unsigned int i) const { return cmds[i].weight; }
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035 virtual void setParams(unsigned int i, float amplitude, unsigned int period_time, float offset_value, unsigned int offset_time) {
00036 amp[i]=amplitude;
00037 period[i]=period_time;
00038 offset[i]=offset_value;
00039 start[i]=offset_time;
00040 if(cmds[i].weight<=0)
00041 cmds[i].weight=1;
00042 }
00043
00044
00045
00046
00047
00048
00049
00050 virtual void setParams(unsigned int i, float amplitude, unsigned int period_time, float offset_value) {
00051 amp[i]=amplitude;
00052 period[i]=period_time;
00053 offset[i]=offset_value;
00054 if(cmds[i].weight<=0)
00055 cmds[i].weight=1;
00056 sync(i);
00057 }
00058
00059 virtual float getAmplitude(unsigned int i) const { return amp[i]; }
00060
00061 virtual unsigned int getPeriod(unsigned int i) const { return period[i]; }
00062
00063 virtual float getOffsetValue(unsigned int i) const { return offset[i]; }
00064
00065 virtual unsigned int getOffsetTime(unsigned int i) const { return start[i]; }
00066
00067
00068 virtual float getPhase(unsigned int i) const { float x = getCount(i); return x-std::floor(x); }
00069
00070 virtual float getCount(unsigned int i) const { unsigned int t=get_time(); return float(t-start[i])/period[i]; }
00071
00072
00073 virtual float getPosition(unsigned int i) const { return cmds[i].value; }
00074
00075 virtual float getSpeed(unsigned int i) const {
00076 if(cmds[i].weight<=0)
00077 return 0;
00078 float scale = 2*static_cast<float>(M_PI)/period[i];
00079 return std::cos((lastUpdate-start[i])*scale)*amp[i]*scale*1000;
00080 }
00081
00082 virtual float getAcceleration(unsigned int i) const {
00083 if(cmds[i].weight<=0)
00084 return 0;
00085 float scale = 2*static_cast<float>(M_PI)/period[i];
00086 return -std::sin((lastUpdate-start[i])*scale)*amp[i]*scale*scale*1000*1000;
00087 }
00088
00089
00090 virtual void sync(unsigned int i) { sync(i,get_time()); }
00091
00092
00093 virtual void sync(unsigned int i, unsigned int t) {
00094 const float TWOPI = 2*static_cast<float>(M_PI);
00095 float x = (state->outputs[i]-offset[i])/amp[i];
00096 if(x>1)
00097 x=1;
00098 else if(x<-1)
00099 x=-1;
00100 start[i] = (unsigned int)rintf(t - std::asin(x)/TWOPI*period[i]);
00101 }
00102
00103
00104 virtual void syncAll() {
00105 unsigned int t=get_time();
00106 float avg=0, totw=0;
00107 for(unsigned int i=0; i<NumOutputs; ++i) {
00108 sync(i,t);
00109 avg+=cmds[i].weight * start[i];
00110 totw+=cmds[i].weight;
00111 }
00112 avg/=totw;
00113 for(unsigned int i=0; i<NumOutputs; ++i)
00114 start[i]=(unsigned int)rintf(avg);
00115 }
00116
00117 virtual int updateOutputs() {
00118 const float TWOPI = 2*static_cast<float>(M_PI);
00119 unsigned int t=get_time();
00120 unsigned int cnt=0;
00121
00122 if(NumFrames==1) {
00123
00124 for(unsigned int i=0; i<NumOutputs; ++i) {
00125 if(cmds[i].weight>0) {
00126 cmds[i].value=std::sin((t-start[i])*TWOPI/period[i])*amp[i]+offset[i];
00127 motman->setOutput(this,i,cmds[i]);
00128 ++cnt;
00129 }
00130 }
00131 } else {
00132
00133 OutputCmd tmp[NumFrames];
00134 for(unsigned int i=0; i<NumOutputs; ++i) {
00135 if(cmds[i].weight>0) {
00136 for(unsigned int f=0; f<NumFrames; ++f) {
00137 tmp[i].value=std::sin((t-start[i]+f*FrameTime)*TWOPI/period[i])*amp[i]+offset[i];
00138 tmp[i].weight=cmds[i].weight;
00139 }
00140 motman->setOutput(this,i,tmp);
00141 cmds[i].value = tmp[i].value;
00142 ++cnt;
00143 }
00144 }
00145 }
00146 lastUpdate=t+(NumFrames-1)*FrameTime;
00147 return cnt;
00148 }
00149
00150 virtual int isDirty() { return true; }
00151 virtual int isAlive() { return true; }
00152
00153 protected:
00154 OutputCmd cmds[NumOutputs];
00155 float amp[NumOutputs];
00156 unsigned int period[NumOutputs];
00157 float offset[NumOutputs];
00158 unsigned int start[NumOutputs];
00159 unsigned int lastUpdate;
00160 };
00161
00162
00163
00164
00165
00166
00167 #endif