#include "stdafx.h" #include "DllFunc.h" #include "math.h"
void ats(double A[9],double s[3], double sp[3]) { sp[0]=A[0]*s[0]+A[1]*s[1]+A[2]*s[2]; sp[1]=A[3]*s[0]+A[4]*s[1]+A[5]*s[2]; sp[2]=A[6]*s[0]+A[7]*s[1]+A[8]*s[2]; }
ModalForce_API void __cdecl modal_force (int id, double time, double upar[], int npar, int ifbody, double pos[12], double vel[6], double acc[6], int nmode, int nnode, int nModalLoad, double *ModalLoads, int jflag, int iflag, double *result) { using namespace rd_syscall; // Parameter Information // id : Modal force sequential identification. (Input) // time : Simulation time of RD/Solver. (Input) // upar : Parameters defined by user. (Input) // npar : Number of user parameters. (Input) // ifbody : RFLEX body sequential ID. (Input) // pos : Position [1~3] and Orientation matrix [4~12] w.r.t Ground.InertiaMarker. (Input) // vel : Velocity vector w.r.t. Ground.InertiaMarker. (Input) // acc : Acceleration vector w.r.t Ground.InertiaMarker. (Input) // nmode : Number of selected mode. (Input) // nnode : Number of node. (Input) // nModalLoad : Number of selected modal load cases. (Input) // ModalLoads : Modal force vector. (Input, Size : (6 + nmode) x nModalLoad) // jflag : When RD/Solver evaluates a Jacobian, the flag is true. (Input) // iflag : When RD/Solver initializes arrays, the flag is true. (Input) // result : Returned modal froce vector. (Output, Size : 6 + nmode)
// User Statement int i,j,ierr; double *Af; int mid[9]; double MVel[3]; double MPos[3]; double MAcc[3]; double VM; double Fdir[3]; double Fscale[3]; double dtmp[3]; double Cd; double RHO; double Area[3]; double darea; double UCF;
//Initialization Af=&(pos[3]); RHO = upar[0]; Cd = upar[1]; Area[0] = upar[2]; // Assumption : Area of shell face doesn't change // for node61,63,65 Area[1] = upar[3]; // Assumption : Area of shell face doesn't change // for node17,19,21 Area[2] = upar[4]; // Assumption : Area of shell face doesn't change // for node105,107,109 mid[0] = int(upar[5]); // Node61 mid[1] = int(upar[6]); // Node63 mid[2] = int(upar[7]); // Node65 mid[3] = int(upar[8]); // Node17 mid[4] = int(upar[9]); // Node19 mid[5] = int(upar[10]); // Node21 mid[6] = int(upar[11]); // Node105 mid[7] = int(upar[12]); // Node107 mid[8] = int(upar[13]); // Node109 rd_ucf(&UCF);
for(i=0;i<6+nmode;i++){ result[i] = 0.0; }
// Test code for Air-resistance force in rflex // Cd : coefficient for a drag force // Air resistance force : 1/2*Cd*Rho(air)*v^2*Area for(i=0;i<9;i++){ sysary("TVEL",&(mid[i]),1,MVel,3,&ierr); VM=sqrt(MVel[0]*MVel[0]+MVel[1]*MVel[1]+MVel[2]*MVel[2]);
if (VM < 1.0e-17) { Fdir[0] = 0.0; Fdir[1] = 0.0; Fdir[2] = 0.0; } else { Fdir[0] = MVel[0]/VM*(-1.0); Fdir[1] = MVel[1]/VM*(-1.0); Fdir[2] = MVel[2]/VM*(-1.0); }
if(i<3) darea = Area[0]; else if(i<6) darea = Area[1]; else darea = Area[2];
dtmp[0] = Fdir[0]*(Cd*RHO*VM*VM*darea/2)/UCF; dtmp[1] = Fdir[1]*(Cd*RHO*VM*VM*darea/2)/UCF; dtmp[2] = Fdir[2]*(Cd*RHO*VM*VM*darea/2)/UCF;
// Generalized Force (w.r.t RFlex Body Ref. Frame) ats(Af,dtmp,Fscale);
for(j=0;j<6+nmode;j++){ result[j] += Fscale[0]*ModalLoads[j+(6+nmode)*(3*i)]+ Fscale[1]*ModalLoads[j+(6+nmode)*(3*i+1)]+ Fscale[2]*ModalLoads[j+(6+nmode)*(3*i+2)]; } } } |