Skip to content
Snippets Groups Projects
Metavoxel GPU Validation 4.ipynb 299 KiB
Newer Older
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
  },
  {
   "cell_type": "code",
   "execution_count": 130,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "applyQuaternion1 (generic function with 1 method)"
      ]
     },
     "execution_count": 130,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "function setFromUnitVectors(vFrom::Vector3, vTo::Vector3)\n",
    "    # assumes direction vectors vFrom and vTo are normalized\n",
    "    EPS = 0.000000001;\n",
    "    r= dotVector3(vFrom,vTo)+1.0\n",
    "    # r =  dot(vFrom,vTo)+1\n",
    "\n",
    "    if r < EPS\n",
    "        r = 0;\n",
    "        if abs( vFrom.x ) > abs( vFrom.z ) \n",
    "            qx = - vFrom.y\n",
    "            qy = vFrom.x\n",
    "            qz = 0.0\n",
    "            qw = r\n",
    "        else \n",
    "            qx = 0.0\n",
    "            qy = -(vFrom.z)\n",
    "            qz = vFrom.y\n",
    "            qw = r\n",
    "        end\n",
    "   else \n",
    "        # crossVectors( vFrom, vTo ); // inlined to avoid cyclic dependency on Vector3\n",
    "        qx = vFrom.y * vTo.z - vFrom.z * vTo.y\n",
    "        qy = vFrom.z * vTo.x - vFrom.x * vTo.z\n",
    "        qz = vFrom.x * vTo.y - vFrom.y * vTo.x\n",
    "        qw = r\n",
    "\n",
    "    end\n",
    "    qx= (qx==-0.0) ? 0.0 : qx\n",
    "    qy= (qy==-0.0) ? 0.0 : qy\n",
    "    qz= (qz==-0.0) ? 0.0 : qz\n",
    "    qw= (qw==-0.0) ? 0.0 : qw\n",
    "        \n",
    "    \n",
    "    mx=qx*qx\n",
    "    my=qy*qy\n",
    "    mz=qz*qz\n",
    "    mw=qw*qw\n",
    "    mm=mx+my\n",
    "    mm=mm+mz\n",
    "    mm=mm+mw\n",
    "    mm=convert(Float64,mm)#??????????????????? todo check later\n",
    "    \n",
    "    l=CUDAnative.sqrt(mm)\n",
    "    \n",
    "    #l = sqrt((qx * qx) + (qy * qy) + (qz * qz)+ (qw * qw))\n",
    "    if l === 0 \n",
    "        qx = 0.0\n",
    "        qy = 0.0\n",
    "        qz = 0.0\n",
    "        qw = 1.0\n",
    "    else \n",
    "        l = 1.0 / l\n",
    "        qx = qx * l\n",
    "        qy = qy * l\n",
    "        qz = qz * l\n",
    "        qw = qw * l\n",
    "    end\n",
    "    \n",
    "    \n",
    "\n",
    "    # return qx,qy,qz,qw\n",
    "    return Quaternion(qx,qy,qz,qw)\n",
    "    \n",
    "    # return normalizeQ(Quat(qw,qx,qy,qz))\n",
    "    # return Quat(nn[1], nn[2], nn[3], nn[4])\n",
    "\n",
    "end\n",
    "\n",
    "function quatToMatrix( quaternion::Quaternion)\n",
    "\n",
    "    #te = RotationMatrix()\n",
    "    \n",
    "    x = quaternion.x\n",
    "    y = quaternion.y\n",
    "    z = quaternion.z\n",
    "    w = quaternion.w\n",
    "    \n",
    "    x2 = x + x\n",
    "    y2 = y + y\n",
    "    z2 = z + z\n",
    "    xx = x * x2\n",
    "    xy = x * y2\n",
    "    xz = x * z2\n",
    "    yy = y * y2\n",
    "    yz = y * z2\n",
    "    zz = z * z2\n",
    "    wx = w * x2\n",
    "    wy = w * y2\n",
    "    wz = w * z2\n",
    "\n",
    "    sx = 1.0\n",
    "    sy = 1.0\n",
    "    sz = 1.0\n",
    "\n",
    "    te1 = ( 1.0 - ( yy + zz ) ) * sx\n",
    "    te2 = ( xy + wz ) * sx\n",
    "    te3 = ( xz - wy ) * sx\n",
    "    te4 = 0.0\n",
    "\n",
    "    te5 = ( xy - wz ) * sy\n",
    "    te6 = ( 1.0 - ( xx + zz ) ) * sy\n",
    "    te7 = ( yz + wx ) * sy\n",
    "    te8 = 0.0\n",
    "\n",
    "    te9 = ( xz + wy ) * sz\n",
    "    te10 = ( yz - wx ) * sz\n",
    "    te11 = ( 1.0 - ( xx + yy ) ) * sz\n",
    "    te12 = 0.0\n",
    "\n",
    "    te13 = 0.0 #position.x;\n",
    "    te14 = 0.0 #position.y;\n",
    "    te15 = 0.0 #position.z;\n",
    "    te16 = 1.0\n",
    "    \n",
    "        \n",
    "    te= RotationMatrix(te1,te2,te3,te4,te5,te6,te7,te8,te9,te10,te11,te12,te13,te14,te15,te16)\n",
    "\n",
    "    return te\n",
    "\n",
    "end\n",
    "\n",
    "function  setFromRotationMatrix(m::RotationMatrix)\n",
    "    #te = m\n",
    "    #m11 = (te[ 1 ]== -0.0) ? 0.0 : te[ 1 ]\n",
    "    #m12 = (te[ 5 ]== -0.0) ? 0.0 : te[ 5 ]\n",
    "    #m13 = (te[ 9 ]== -0.0) ? 0.0 : te[ 9 ]\n",
    "    #m21 = (te[ 2 ]== -0.0) ? 0.0 : te[ 2 ]\n",
    "    #m22 = (te[ 6 ]== -0.0) ? 0.0 : te[ 6 ]\n",
    "    #m23 = (te[ 10]== -0.0) ? 0.0 : te[ 10]\n",
    "    #m31 = (te[ 3 ]== -0.0) ? 0.0 : te[ 3 ]\n",
    "    #m32 = (te[ 7 ]== -0.0) ? 0.0 : te[ 7 ]\n",
    "    #m33 = (te[ 11]== -0.0) ? 0.0 : te[ 11]\n",
    "\n",
    "    m11 = convert(Float64,m.te1 )\n",
    "    m12 = convert(Float64,m.te5 )\n",
    "    m13 = convert(Float64,m.te9 )\n",
    "    m21 = convert(Float64,m.te2 )\n",
    "    m22 = convert(Float64,m.te6 )\n",
    "    m23 = convert(Float64,m.te10)\n",
    "    m31 = convert(Float64,m.te3 )\n",
    "    m32 = convert(Float64,m.te7 )\n",
    "    m33 = convert(Float64,m.te11)\n",
    "    \n",
    "\n",
    "    y = CUDAnative.asin( clamp( m13, -1.0, 1.0 ) ) ##check if has to be changed to cuda\n",
    "\n",
    "    if ( abs( m13 ) < 0.9999999999 ) \n",
    "        \n",
    "        x = CUDAnative.atan2( - m23, m33 )\n",
    "        z = CUDAnative.atan2( - m12, m11 )#-m12, m11\n",
    "        # if(m23==0.0)\n",
    "        #     x = atan( m23, m33 )\n",
    "        # end\n",
    "        # if(m12==0.0)\n",
    "        #     z = atan( m12, m11 )\n",
    "        # end\n",
    "\n",
    "    else\n",
    "\n",
    "        x = CUDAnative.atan2( m32, m22 )\n",
    "        z = 0.0;\n",
    "\n",
    "    end\n",
    "    \n",
    "    \n",
    "    return Vector3(x,y,z)\n",
    "    \n",
    "end\n",
    "\n",
    "function setQuaternionFromEuler(euler::Vector3)\n",
    "    x=euler.x\n",
    "    y=euler.y\n",
    "    z=euler.z\n",
    "    \n",
    "    \n",
    "    c1 = CUDAnative.cos( x / 2.0 )\n",
    "    c2 = CUDAnative.cos( y / 2.0 )\n",
    "    c3 = CUDAnative.cos( z / 2.0 )\n",
    "\n",
    "    s1 = CUDAnative.sin( x / 2.0 )\n",
    "    s2 = CUDAnative.sin( y / 2.0 )\n",
    "    s3 = CUDAnative.sin( z / 2.0 )\n",
    "    \n",
    "   \n",
    "    x = s1 * c2 * c3 + c1 * s2 * s3\n",
    "    y = c1 * s2 * c3 - s1 * c2 * s3\n",
    "    z = c1 * c2 * s3 + s1 * s2 * c3\n",
    "    w = c1 * c2 * c3 - s1 * s2 * s3\n",
    "        \n",
    "    return Quaternion(x,y,z,w)\n",
    "end\n",
    "\n",
    "function applyQuaternion1(e::Vector3,q2::Quaternion)\n",
    "    x = e.x\n",
    "    y = e.y\n",
    "    z = e.z\n",
    "\n",
    "    qx = q2.x\n",
    "    qy = q2.y\n",
    "    qz = q2.z\n",
    "    qw = q2.w\n",
    "\n",
    "    # calculate quat * vector\n",
    "\n",
    "    ix = qw * x + qy * z - qz * y\n",
    "    iy = qw * y + qz * x - qx * z\n",
    "    iz = qw * z + qx * y - qy * x\n",
    "    iw = - qx * x - qy * y - qz * z\n",
    "\n",
    "    # calculate result * inverse quat\n",
    "\n",
    "    xx = ix * qw + iw * - qx + iy * - qz - iz * - qy\n",
    "    yy = iy * qw + iw * - qy + iz * - qx - ix * - qz\n",
    "    zz = iz * qw + iw * - qz + ix * - qy - iy * - qx\n",
    "    \n",
    "    d=15\n",
    "\n",
    "    return Vector3(xx,yy,zz)\n",
    "end\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 131,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "multiplyQuaternions (generic function with 1 method)"
      ]
     },
     "execution_count": 131,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "function conjugate(q::Quaternion)\n",
    "    x= (-q.x==-0) ? 0.0 : -q.x\n",
    "    y= (-q.y==-0) ? 0.0 : -q.y\n",
    "    z= (-q.z==-0) ? 0.0 : -q.z\n",
    "    w=q.w\n",
    "    x=convert(Float64,x)\n",
    "    y=convert(Float64,y)\n",
    "    z=convert(Float64,z)\n",
    "    w=convert(Float64,w)\n",
    "    return Quaternion(x,y,z,w)\n",
    "end\n",
    "\n",
    "function RotateVec3D(a::Quaternion, f::Vector3)   \n",
    "    fx= (f.x==-0) ? 0 : f.x\n",
    "    fy= (f.y==-0) ? 0 : f.y\n",
    "    fz= (f.z==-0) ? 0 : f.z\n",
    "    # fx= f.x\n",
    "    # fy= f.y\n",
    "    # fz= f.z\n",
    "    tw = fx*a.x + fy*a.y + fz*a.z\n",
    "    tx = fx*a.w - fy*a.z + fz*a.y\n",
    "    ty = fx*a.z + fy*a.w - fz*a.x\n",
    "    tz = -fx*a.y + fy*a.x + fz*a.w\n",
    "\n",
    "    return Vector3((a.w*tx+a.x*tw+a.y*tz-a.z*ty),(a.w*ty-a.x*tz+a.y*tw+a.z*tx),(a.w*tz+a.x*ty-a.y*tx+a.z*tw))\n",
    "end\n",
    "#!< Returns a vector representing the specified vector \"f\" rotated by this quaternion. @param[in] f The vector to transform.\n",
    "\n",
    "function RotateVec3DInv(a::Quaternion, f::Vector3)  \n",
    "    fx=f.x\n",
    "    fy=f.y\n",
    "    fz=f.z\n",
    "    tw = a.x*fx + a.y*fy + a.z*fz\n",
    "    tx = a.w*fx - a.y*fz + a.z*fy\n",
    "    ty = a.w*fy + a.x*fz - a.z*fx\n",
    "    tz = a.w*fz - a.x*fy + a.y*fx\n",
    "    return Vector3((tw*a.x + tx*a.w + ty*a.z - tz*a.y),(tw*a.y - tx*a.z + ty*a.w + tz*a.x),(tw*a.z + tx*a.y - ty*a.x + tz*a.w))\n",
    "end\n",
    "#!< Returns a vector representing the specified vector \"f\" rotated by the inverse of this quaternion. This is the opposite of RotateVec3D. @param[in] f The vector to transform.\n",
    "\n",
    "function ToRotationVector(a::Quaternion)  \n",
    "    if (a.w >= 1.0 || a.w <= -1.0) \n",
    "        return Vector3(0.0,0.0,0.0)\n",
    "    end\n",
    "    squareLength = 1.0-a.w*a.w; # because x*x + y*y + z*z + w*w = 1.0, but more susceptible to w noise (when \n",
    "    SLTHRESH_ACOS2SQRT= 2.4e-3; # SquareLength threshhold for when we can use square root optimization for acos. From SquareLength = 1-w*w. (calculate according to 1.0-W_THRESH_ACOS2SQRT*W_THRESH_ACOS2SQRT\n",
    "\n",
    "    if (squareLength < SLTHRESH_ACOS2SQRT) # ???????\n",
    "        x=a.x*(2.0*CUDAnative.sqrt((2-2*a.w)/squareLength))\n",
    "        y=a.y*(2.0*CUDAnative.sqrt((2-2*a.w)/squareLength))\n",
    "        z=a.z*(2.0*CUDAnative.sqrt((2-2*a.w)/squareLength))\n",
    "        x=convert(Float64,x)\n",
    "        y=convert(Float64,y)\n",
    "        z=convert(Float64,z)\n",
    " \n",
    "        return Vector3(x,y,z) ; # acos(w) = sqrt(2*(1-x)) for w close to 1. for w=0.001, error is 1.317e-6\n",
    "    else \n",
    "        x=a.x*(2.0*CUDAnative.acos(a.w)/CUDAnative.sqrt(squareLength))\n",
    "        y=a.y*(2.0*CUDAnative.acos(a.w)/CUDAnative.sqrt(squareLength))\n",
    "        z=a.z*(2.0*CUDAnative.acos(a.w)/CUDAnative.sqrt(squareLength))\n",
    "        x=convert(Float64,x)\n",
    "        y=convert(Float64,y)\n",
    "        z=convert(Float64,z)\n",
    "\n",
    "        return Vector3(x,y,z)\n",
    "    end                                    \n",
    "end \n",
    "# !< Returns a rotation vector representing this quaternion rotation. Adapted from http://www.euclideanspace.com/maths/geometry/rotations/conversions/quaternionToAngle/\n",
    "\n",
    "function FromRotationVector(VecIn::Vector3)\n",
    "    theta=VecIn*Vector3(0.5,0.5,0.5)\n",
    "    ntheta=CUDAnative.sqrt((theta.x * theta.x) + (theta.y * theta.y) + (theta.z * theta.z))\n",
    "    thetaMag2=ntheta*ntheta\n",
    "    \n",
    "    DBL_EPSILONx24 =5.328e-15\n",
    "    if thetaMag2*thetaMag2 < DBL_EPSILONx24\n",
    "        qw=1.0 - 0.5*thetaMag2\n",
    "\t\ts=1.0 - thetaMag2 / 6.0\n",
    "    else\n",
    "        thetaMag = CUDAnative.sqrt(thetaMag2)\n",
    "\t\tqw=CUDAnative.cos(thetaMag)\n",
    "\t\ts=CUDAnative.sin(thetaMag) / thetaMag\n",
    "    end\n",
    "    qx=theta.x*s\n",
    "    qy=theta.y*s\n",
    "    qz=theta.z*s\n",
    "    \n",
    "    qx=convert(Float64,qx)\n",
    "    qy=convert(Float64,qy)\n",
    "    qz=convert(Float64,qz)\n",
    "    qw=convert(Float64,qw)\n",
    "    \n",
    "    return Quaternion(qx,qy,qz,qw)\n",
    "end\n",
    "\n",
    "function multiplyQuaternions(q::Quaternion,f::Quaternion)\n",
    "    x=q.x\n",
    "    y=q.y\n",
    "    z=q.z\n",
    "    w=q.w\n",
    "    x1=w*f.x + x*f.w + y*f.z - z*f.y \n",
    "    y1=w*f.y - x*f.z + y*f.w + z*f.x\n",
    "    z1=w*f.z + x*f.y - y*f.x + z*f.w\n",
    "    w1=w*f.w - x*f.x - y*f.y - z*f.z\n",
    "#     x1=convert(Float64,x1)\n",
    "#     y1=convert(Float64,y1)\n",
    "#     z1=convert(Float64,z1)\n",
    "#     w1=convert(Float64,w1)\n",
    "\treturn Quaternion(x1,y1,z1,w1 ); #!< overload quaternion multiplication.\n",
    "end\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 132,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "axialStrain (generic function with 1 method)"
      ]
     },
     "execution_count": 132,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "function updateStrain( axialStrain,E) # ?from where strain\n",
    "    strain = axialStrain # redundant?\n",
    "    currentTransverseStrainSum=0.0 # ??? todo\n",
    "    linear=true\n",
    "    maxStrain=1000000000000000;# ?? todo later change\n",
    "    if linear\n",
    "        if axialStrain > maxStrain\n",
    "            maxStrain = axialStrain # remember this maximum for easy reference\n",
    "        end\n",
    "        return stress(axialStrain,E)\n",
    "    else \n",
    "        if (axialStrain > maxStrain) # if new territory on the stress/strain curve\n",
    "            maxStrain = axialStrain # remember this maximum for easy reference\n",
    "            returnStress = stress(axialStrain,E) # ??currentTransverseStrainSum\n",
    "            if (nu != 0.0) \n",
    "                strainOffset = maxStrain-stress(axialStrain,E)/(_eHat*(1.0-nu)) # precalculate strain offset for when we back off\n",
    "            else \n",
    "                strainOffset = maxStrain-returnStress/E # precalculate strain offset for when we back off\n",
    "            end\n",
    "        else  # backed off a non-linear material, therefore in linear region.\n",
    "            relativeStrain = axialStrain-strainOffset #  treat the material as linear with a strain offset according to the maximum plastic deformation\n",
    "            if (nu != 0.0) \n",
    "                returnStress = stress(relativeStrain,E)\n",
    "            else \n",
    "                returnStress = E*relativeStrain\n",
    "            end\n",
    "        end\n",
    "        return returnStress\n",
    "    end\n",
    "end\n",
    "\n",
    "function stress( strain , E ) #end,transverseStrainSum, forceLinear){\n",
    "    #  reference: http://www.colorado.edu/engineering/CAS/courses.d/Structures.d/IAST.Lect05.d/IAST.Lect05.pdf page 10\n",
    "    #  if (isFailed(strain)) return 0.0f; //if a failure point is set and exceeded, we've broken!\n",
    "    #   var E =setup.edges[0].stiffness; //todo change later to material ??\n",
    "    #   var E=1000000;//todo change later to material ??\n",
    "    #   var scaleFactor=1;\n",
    "    return E*strain;\n",
    "\n",
    "    #  #   if (strain <= strainData[1] || linear || forceLinear){ //for compression/first segment and linear materials (forced or otherwise), simple calculation\n",
    "\n",
    "        #   if (nu==0.0) return E*strain;\n",
    "        #   else return _eHat*((1-nu)*strain + nu*transverseStrainSum); \n",
    "        #  else return eHat()*((1-nu)*strain + nu*transverseStrainSum); \n",
    "    #  #  }\n",
    "\n",
    "      #//the non-linear feature with non-zero poissons ratio is currently experimental\n",
    "      #int DataCount = modelDataPoints();\n",
    "      #for (int i=2; i<DataCount; i++){ //go through each segment in the material model (skipping the first segment because it has already been handled.\n",
    "      #  if (strain <= strainData[i] || i==DataCount-1){ //if in the segment ending with this point (or if this is the last point extrapolate out) \n",
    "      #      float Perc = (strain-strainData[i-1])/(strainData[i]-strainData[i-1]);\n",
    "      #      float basicStress = stressData[i-1] + Perc*(stressData[i]-stressData[i-1]);\n",
    "      #      if (nu==0.0f) return basicStress;\n",
    "      #      else { //accounting for volumetric effects\n",
    "      #          float modulus = (stressData[i]-stressData[i-1])/(strainData[i]-strainData[i-1]);\n",
    "      #          float modulusHat = modulus/((1-2*nu)*(1+nu));\n",
    "      #          float effectiveStrain = basicStress/modulus; //this is the strain at which a simple linear stress strain line would hit this point at the definied modulus\n",
    "      #          float effectiveTransverseStrainSum = transverseStrainSum*(effectiveStrain/strain);\n",
    "      #          return modulusHat*((1-nu)*effectiveStrain + nu*effectiveTransverseStrainSum);\n",
    "      #      }\n",
    "      #  }\n",
    "      #}\n",
    "\n",
    "    #  assert(false); //should never reach this point\n",
    "    #  return 0.0f;\n",
    "end \n",
    "\n",
    "function axialStrain( positiveEnd,strain)\n",
    "\t#strainRatio = pVPos->material()->E/pVNeg->material()->E;\n",
    "\tstrainRatio=1.0;\n",
    "\treturn positiveEnd ? 2.0 *strain*strainRatio/(1.0+strainRatio) : 2.0*strain/(1.0+strainRatio)\n",
    "end"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 133,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "moment (generic function with 1 method)"
      ]
     },
     "execution_count": 133,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "function force(N_intForce,N_orient,N_force,static,currentTimeStep) \n",
    "    # forces from internal bonds\n",
    "    totalForce=Vector3(0,0,0)\n",
    "    # new THREE.Vector3(node.force.x,node.force.y,node.force.z);\n",
    "    #  todo \n",
    "\n",
    "\n",
    "    totalForce=totalForce+N_intForce\n",
    "\n",
    "    #  for (int i=0; i<6; i++){ \n",
    "    #  \tif (links[i]) totalForce += links[i]->force(isNegative((linkDirection)i)); # total force in LCS\n",
    "    #  }\n",
    "    totalForce = RotateVec3D(N_orient,totalForce); # from local to global coordinates\n",
    "\n",
    "\n",
    "    # assert(!(totalForce.x != totalForce.x) || !(totalForce.y != totalForce.y) || !(totalForce.z != totalForce.z)); //assert non QNAN\n",
    "\n",
    "    # other forces\n",
    "    if(static)\n",
    "        totalForce=totalForce+N_force\n",
    "    #  }else if(currentTimeStep<50){\n",
    "    #  \ttotalForce.add(new THREE.Vector3(node.force.x,node.force.y,node.force.z));\n",
    "    else\n",
    "        #  var ex=0.1;\n",
    "        #  if(node.force.y!=0){\n",
    "        #  \tvar f=400*Math.sin(currentTimeStep*ex);\n",
    "        #  \ttotalForce.add(new THREE.Vector3(0,f,0));\n",
    "\n",
    "        #  }\n",
    "        #x=N_position[node][3]\n",
    "        #t=currentTimeStep\n",
    "        #wave=getForce(x,t)\n",
    "        #totalForce=totalForce+[0 wave 0]\n",
    "    end\n",
    "\n",
    "\n",
    "    #  if (externalExists()) totalForce += external()->force(); //external forces\n",
    "    #  totalForce -= velocity()*mat->globalDampingTranslateC(); //global damping f-cv\n",
    "    #  totalForce.z += mat->gravityForce(); //gravity, according to f=mg\n",
    "\n",
    "    #  if (isCollisionsEnabled()){\n",
    "    #  \tfor (std::vector<CVX_Collision*>::iterator it=colWatch->begin(); it!=colWatch->end(); it++){\n",
    "    #  \t\ttotalForce -= (*it)->contactForce(this);\n",
    "    #  \t}\n",
    "    #  }\n",
    "    # todo make internal forces 0 again\n",
    "    # N_intForce[node]=[0 0 0] # do i really need it?\n",
    "\n",
    "    #  node.force.x=0;\n",
    "    #  node.force.y=0;\n",
    "    #  node.force.z=0;\n",
    "\n",
    "\n",
    "    return totalForce\n",
    "end\n",
    "\n",
    "\n",
    "function moment(intMoment,orient,moment) \n",
    "    #moments from internal bonds\n",
    "    totalMoment=Vector3(0,0,0)\n",
    "    # for (int i=0; i<6; i++){ \n",
    "    # \tif (links[i]) totalMoment += links[i]->moment(isNegative((linkDirection)i)); //total force in LCS\n",
    "    # }\n",
    "\n",
    "    totalMoment=totalMoment+intMoment\n",
    "    \n",
    "    \n",
    "\n",
    "    totalMoment = RotateVec3D(orient,totalMoment);\n",
    "    \n",
    "    \n",
    "\n",
    "    totalMoment=totalMoment+moment\n",
    "\n",
    "\n",
    "    #other moments\n",
    "    # if (externalExists()) totalMoment += external()->moment(); //external moments\n",
    "    # totalMoment -= angularVelocity()*mat->globalDampingRotateC(); //global damping\n",
    "\n",
    "    return totalMoment\n",
    "end"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 134,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "updateDataAndSaveFEA! (generic function with 1 method)"
      ]
     },
     "execution_count": 134,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "function updateDataAndSaveFEA!(setup,fileName)\n",
    "#     nodes      = setup[\"nodes\"]\n",
    "#     edges      = setup[\"edges\"]\n",
    "    \n",
    "#     setup[\"animation\"][\"showDisplacement\"]=false\n",
    "#     voxCount=size(nodes)[1]\n",
    "#     linkCount=size(edges)[1]\n",
    "    \n",
    "#     N_displacement=Array(metavoxel[\"N_displacementGPU\"])\n",
    "#     N_angle=Array(metavoxel[\"N_angleGPU\"])\n",
    "#     E_stress=Array(metavoxel[\"E_stressGPU\"])\n",
    "    \n",
    "#     setup[\"viz\"][\"maxStress\"]=maximum(E_stress)\n",
    "#     setup[\"viz\"][\"minStress\"]=minimum(E_stress) \n",
    "\n",
    "\n",
    "#     i=1\n",
    "# \tfor edge in edges\n",
    "#         edge[\"stress\"]=E_stress[i]\n",
    "#         i=i+1\n",
    "\n",
    "#     end\n",
    "    \n",
    " \n",
    "#     i=1          \n",
    "# \tfor node in nodes\n",
    "#         node[\"displacement\"][\"x\"]=N_displacement[i].x*100\n",
    "#         node[\"displacement\"][\"y\"]=N_displacement[i].y*100\n",
    "#         node[\"displacement\"][\"z\"]=N_displacement[i].z*100\n",
    "        \n",
    "#         node[\"angle\"][\"x\"]=N_angle[i].x\n",
    "#         node[\"angle\"][\"y\"]=N_angle[i].y\n",
    "#         node[\"angle\"][\"z\"]=N_angle[i].z\n",
    "#         i=i+1\n",
    "\n",
    "#     end\n",
    "    \n",
    "    # pass data as a json string (how it shall be displayed in a file)\n",
    "    stringdata = JSON.json(setup)\n",
    "\n",
    "    # write the file with the stringdata variable information\n",
    "    open(fileName, \"w\") do f\n",
    "            write(f, stringdata)\n",
    "         end\n",
    "    \n",
    "end"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 135,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "updateDataAndSave! (generic function with 1 method)"
      ]
     },
     "execution_count": 135,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "function updateDataAndSave!(metavoxel,setup,fileName)\n",
    "    nodes      = setup[\"nodes\"]\n",
    "    edges      = setup[\"edges\"]\n",
    "    \n",
    "    setup[\"animation\"][\"showDisplacement\"]=true\n",
    "    voxCount=size(nodes)[1]\n",
    "    linkCount=size(edges)[1]\n",
    "    \n",
    "    N_displacement=Array(metavoxel[\"N_displacementGPU\"])\n",
    "    N_angle=Array(metavoxel[\"N_angleGPU\"])\n",
    "    E_stress=Array(metavoxel[\"E_stressGPU\"])\n",
    "    \n",
    "    setup[\"viz\"][\"maxStress\"]=maximum(E_stress)\n",
    "    setup[\"viz\"][\"minStress\"]=minimum(E_stress) \n",
    "\n",
    "\n",
    "    i=1\n",
    "\tfor edge in edges\n",
    "        edge[\"stress\"]=E_stress[i]\n",
    "        i=i+1\n",
    "\n",
    "    end\n",
    "    \n",
    " \n",
    "    i=1          \n",
    "\tfor node in nodes\n",
    "        node[\"displacement\"][\"x\"]=N_displacement[i].x/15\n",
    "        node[\"displacement\"][\"y\"]=N_displacement[i].y/15\n",
    "        node[\"displacement\"][\"z\"]=N_displacement[i].z/15\n",
    "        \n",
    "        node[\"angle\"][\"x\"]=N_angle[i].x\n",
    "        node[\"angle\"][\"y\"]=N_angle[i].y\n",
    "        node[\"angle\"][\"z\"]=N_angle[i].z\n",
    "        i=i+1\n",
    "\n",
    "    end\n",
    "    \n",
    "    # pass data as a json string (how it shall be displayed in a file)\n",
    "    stringdata = JSON.json(setup)\n",
    "\n",
    "    # write the file with the stringdata variable information\n",
    "    open(fileName, \"w\") do f\n",
    "            write(f, stringdata)\n",
    "         end\n",
    "    \n",
    "end"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 136,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "runMetavoxelGPU! (generic function with 1 method)"
      ]
     },
     "execution_count": 136,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "function runMetavoxelGPU!(setup,numTimeSteps,latticeSize,displacements,returnEvery,save)\n",
    "    function initialize!(setup)\n",
    "        nodes      = setup[\"nodes\"]\n",
    "        edges      = setup[\"edges\"]\n",
    "\n",
    "        i=1\n",
    "        # pre-calculate current position\n",
    "        for node in nodes\n",
    "            # element=parse(Int,node[\"id\"][2:end])\n",
    "            N_position[i]=Vector3(node[\"position\"][\"x\"]*15.0,node[\"position\"][\"y\"]*15.0,node[\"position\"][\"z\"]*15.0)\n",
    "            N_restrained[i]=node[\"restrained_degrees_of_freedom\"][1] ## todo later consider other degrees of freedom\n",
    "            N_displacement[i]=Vector3(node[\"displacement\"][\"x\"]*15,node[\"displacement\"][\"y\"]*15,node[\"displacement\"][\"z\"]*15)\n",
    "            N_angle[i]=Vector3(node[\"angle\"][\"x\"],node[\"angle\"][\"y\"],node[\"angle\"][\"z\"])\n",
    "            N_force[i]=Vector3(node[\"force\"][\"x\"],node[\"force\"][\"y\"],node[\"force\"][\"z\"])\n",
    "            N_currPosition[i]=Vector3(node[\"position\"][\"x\"]*15.0,node[\"position\"][\"y\"]*15.0,node[\"position\"][\"z\"]*15.0)\n",
    "\n",
    "            # for dynamic simulations\n",
    "            # append!(N_posTimeSteps,[[]])\n",
    "            # append!(N_angTimeSteps,[[]])\n",
    "\n",
    "            i=i+1\n",
    "        end \n",
    "\n",
    "        i=1\n",
    "        # pre-calculate the axis\n",
    "        for edge in edges\n",
    "            # element=parse(Int,edge[\"id\"][2:end])\n",
    "\n",
    "            # find the nodes that the lements connects\n",
    "            fromNode = nodes[edge[\"source\"]+1]\n",
    "            toNode = nodes[edge[\"target\"]+1]\n",
    "\n",
    "\n",
    "            node1 = [fromNode[\"position\"][\"x\"]*15.0 fromNode[\"position\"][\"y\"]*15.0 fromNode[\"position\"][\"z\"]*15.0]\n",
    "            node2 = [toNode[\"position\"][\"x\"]*15.0 toNode[\"position\"][\"y\"]*15.0 toNode[\"position\"][\"z\"]*15.0]\n",
    "\n",
    "            length=norm(node2-node1)\n",
    "            axis=normalize(collect(Iterators.flatten(node2-node1)))\n",
    "\n",
    "            E_source[i]=edge[\"source\"]+1\n",
    "            E_target[i]=edge[\"target\"]+1\n",
    "            E_area[i]=edge[\"area\"]\n",
    "            E_density[i]=edge[\"density\"]\n",
    "            E_stiffness[i]=edge[\"stiffness\"]\n",
    "            E_axis[i]=Vector3(axis[1],axis[2],axis[3])\n",
    "            E_currentRestLength[i]=length #?????? todo change\n",
    "#             E_currentRestLength[i]=75/sqrt(2)\n",
    "#             println(length)\n",
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
    "            \n",
    "\n",
    "            N_edgeID[E_source[i],N_currEdge[E_source[i]]]=i\n",
    "            N_edgeFirst[E_source[i],N_currEdge[E_source[i]]]=true\n",
    "            N_currEdge[E_source[i]]+=1\n",
    "\n",
    "            N_edgeID[E_target[i],N_currEdge[E_target[i]]]=i\n",
    "            N_edgeFirst[E_target[i],N_currEdge[E_target[i]]]=false\n",
    "            N_currEdge[E_target[i]]+=1\n",
    "\n",
    "\n",
    "            # for dynamic simulations\n",
    "            # append!(E_stressTimeSteps,[[]])\n",
    "\n",
    "            i=i+1\n",
    "        end \n",
    "    end\n",
    "    function simulateParallel!(metavoxel,numTimeSteps,dt,returnEvery)\n",
    "        # initialize(setup)\n",
    "\n",
    "        for i in 1:numTimeSteps\n",
    "            #println(\"Timestep:\",i)\n",
    "            doTimeStep!(metavoxel,dt,i)\n",
    "            if(mod(i,returnEvery)==0)\n",
    "                append!(displacements,[Array(metavoxel[\"N_displacementGPU\"])])\n",
    "            end\n",
    "        end\n",
    "    end\n",
    "    \n",
    "    ########\n",
    "    voxCount=0\n",
    "    linkCount=0\n",
    "    nodes      = setup[\"nodes\"]\n",
    "    edges      = setup[\"edges\"]\n",
    "    voxCount=size(nodes)[1]\n",
    "    linkCount=size(edges)[1]\n",
    "    strain =0 #todooo moveeee\n",
    "    maxNumEdges=10\n",
    "\n",
    "    ########\n",
    "    voxCount=0\n",
    "    linkCount=0\n",
    "    nodes      = setup[\"nodes\"]\n",
    "    edges      = setup[\"edges\"]\n",
    "    voxCount=size(nodes)[1]\n",
    "    linkCount=size(edges)[1]\n",
    "    strain =0 #todooo moveeee\n",
    "\n",
    "    ############# nodes\n",
    "    N_position=fill(Vector3(),voxCount)\n",
    "    N_restrained=zeros(Bool, voxCount)\n",
    "    N_displacement=fill(Vector3(),voxCount)\n",
    "    N_angle=fill(Vector3(),voxCount)\n",
    "    N_currPosition=fill(Vector3(),voxCount)\n",
    "    N_linMom=fill(Vector3(),voxCount)\n",
    "    N_angMom=fill(Vector3(),voxCount)\n",
    "    N_intForce=fill(Vector3(),voxCount)\n",
    "    N_intMoment=fill(Vector3(),voxCount)\n",
    "    N_moment=fill(Vector3(),voxCount)\n",
    "    # N_posTimeSteps=[]\n",
    "    # N_angTimeSteps=[]\n",
    "    N_force=fill(Vector3(),voxCount)\n",
    "    N_orient=fill(Quaternion(),voxCount)\n",
    "    N_edgeID=fill(-1,(voxCount,maxNumEdges))\n",
    "    N_edgeFirst=fill(true,(voxCount,maxNumEdges))\n",
    "    N_currEdge=fill(1,voxCount)\n",
    "\n",
    "    ############# edges\n",
    "    E_source=fill(0,linkCount)\n",
    "    E_target=fill(0,linkCount)\n",
    "    E_area=fill(0.0f0,linkCount)\n",
    "    E_density=fill(0.0f0,linkCount)\n",
    "    E_stiffness=fill(0.0f0,linkCount)\n",
    "    E_stress=fill(0.0f0,linkCount)\n",
    "    E_axis=fill(Vector3(1.0,0.0,0.0),linkCount)\n",
    "    E_currentRestLength=fill(0.0f0,linkCount)\n",
    "    E_pos2=fill(Vector3(),linkCount)\n",
    "    E_angle1v=fill(Vector3(),linkCount)\n",
    "    E_angle2v=fill(Vector3(),linkCount)\n",
    "    E_angle1=fill(Quaternion(),linkCount)\n",
    "    E_angle2=fill(Quaternion(),linkCount)\n",
    "\n",
    "    E_intForce1=fill(Vector3(),linkCount)\n",
    "    E_intMoment1=fill(Vector3(),linkCount) \n",
    "\n",
    "    E_intForce2=fill(Vector3(),linkCount)\n",
    "    E_intMoment2=fill(Vector3(),linkCount)\n",
    "    E_damp=fill(false,linkCount)\n",
    "\n",
    "    E_currentTransverseStrainSum=fill(0.0f0,linkCount)# TODO remove ot incorporate\n",
    "    # E_stressTimeSteps=[]\n",
    "\n",
    "\n",
    "    #################################################################\n",
    "    initialize!(setup)\n",
    "    #################################################################\n",
    "\n",
    "    ########################## turn to cuda arrays\n",
    "    ############# nodes\n",
    "    N_positionGPU=    CuArray(N_position)      \n",
    "    N_restrainedGPU=  CuArray(N_restrained)  \n",
    "    N_displacementGPU=CuArray(N_displacement)   \n",
    "    N_angleGPU=       CuArray(N_angle)       \n",
    "    N_currPositionGPU=CuArray(N_currPosition)    \n",
    "    N_linMomGPU=      CuArray(N_linMom)        \n",
    "    N_angMomGPU=      CuArray(N_angMom)        \n",
    "    N_intForceGPU=    CuArray(N_intForce)     \n",
    "    N_intMomentGPU=   CuArray(N_intMoment)        \n",
    "    N_momentGPU=      CuArray(N_moment)         \n",
    "    N_forceGPU=       CuArray(N_force)           \n",
    "    N_orientGPU=      CuArray(N_orient)       \n",
    "    N_edgeIDGPU=      CuArray(N_edgeID)         \n",
    "    N_edgeFirstGPU=   CuArray(N_edgeFirst)         \n",
    "\n",
    "\n",
    "    ############# edges\n",
    "    E_sourceGPU=                    CuArray(E_source)   \n",
    "    E_targetGPU=                    CuArray(E_target)\n",
    "    E_areaGPU=                      CuArray(E_area)                             \n",
    "    E_densityGPU=                   CuArray(E_density)\n",
    "    E_stiffnessGPU=                 CuArray(E_stiffness)\n",
    "    E_stressGPU=                    CuArray(E_stress)\n",
    "    E_axisGPU=                      CuArray(E_axis)          \n",
    "    E_currentRestLengthGPU=         CuArray(E_currentRestLength)\n",
    "    E_pos2GPU=                      CuArray(E_pos2)\n",
    "    E_angle1vGPU=                   CuArray(E_angle1v)\n",
    "    E_angle2vGPU=                   CuArray(E_angle2v)\n",
    "    E_angle1GPU=                    CuArray(E_angle1)\n",
    "    E_angle2GPU=                    CuArray(E_angle2)\n",
    "    E_currentTransverseStrainSumGPU=CuArray(E_currentTransverseStrainSum)\n",
    "    E_intForce1GPU=                 CuArray(E_intForce1) \n",
    "    E_intMoment1GPU=                CuArray(E_intMoment1)  \n",
    "    E_intForce2GPU=                 CuArray(E_intForce2) \n",
    "    E_intMoment2GPU=                CuArray(E_intMoment2)\n",
    "    E_dampGPU=                      CuArray(E_damp) \n",
    "    # E_stressTimeSteps=[]\n",
    "\n",
    "\n",
    "    #########################################\n",
    "    metavoxel = Dict(\n",
    "        \"N_positionGPU\" => N_positionGPU,    \n",
    "        \"N_restrainedGPU\" => N_restrainedGPU,  \n",
    "        \"N_displacementGPU\" => N_displacementGPU,\n",
    "        \"N_angleGPU\" => N_angleGPU,       \n",
    "        \"N_currPositionGPU\" => N_currPositionGPU,\n",
    "        \"N_linMomGPU\" => N_linMomGPU,      \n",
    "        \"N_angMomGPU\" => N_angMomGPU,      \n",
    "        \"N_intForceGPU\" => N_intForceGPU,    \n",
    "        \"N_intMomentGPU\" => N_intMomentGPU,   \n",
    "        \"N_momentGPU\" => N_momentGPU,      \n",
    "        \"N_forceGPU\" => N_forceGPU,       \n",
    "        \"N_orientGPU\" => N_orientGPU,      \n",
    "        \"N_edgeIDGPU\" => N_edgeIDGPU,      \n",
    "        \"N_edgeFirstGPU\" => N_edgeFirstGPU,\n",
    "        \"E_sourceGPU\" =>E_sourceGPU,                    \n",
    "        \"E_targetGPU\" =>E_targetGPU,                    \n",
    "        \"E_areaGPU\" =>E_areaGPU,                      \n",
    "        \"E_densityGPU\" =>E_densityGPU,                   \n",
    "        \"E_stiffnessGPU\" =>E_stiffnessGPU,                 \n",
    "        \"E_stressGPU\" =>E_stressGPU,                    \n",
    "        \"E_axisGPU\" =>E_axisGPU,                      \n",
    "        \"E_currentRestLengthGPU\" =>E_currentRestLengthGPU,         \n",
    "        \"E_pos2GPU\" =>E_pos2GPU,                      \n",
    "        \"E_angle1vGPU\" =>E_angle1vGPU,                   \n",
    "        \"E_angle2vGPU\" =>E_angle2vGPU,                   \n",
    "        \"E_angle1GPU\" =>E_angle1GPU,                    \n",
    "        \"E_angle2GPU\" =>E_angle2GPU,                    \n",
    "        \"E_currentTransverseStrainSumGPU\" =>E_currentTransverseStrainSumGPU,\n",
    "        \"E_intForce1GPU\" =>E_intForce1GPU,                 \n",
    "        \"E_intMoment1GPU\" =>E_intMoment1GPU,                \n",
    "        \"E_intForce2GPU\" =>E_intForce2GPU,                 \n",
    "        \"E_intMoment2GPU\" =>E_intMoment2GPU,                \n",
    "        \"E_dampGPU\" =>E_dampGPU                      \n",
    "    )\n",
    "\n",
    "    #########################################\n",
    "    \n",
    "\n",
    "    dt=0.0251646\n",
    "    E = 2000  # MPa\n",
    "    s=2.38\n",
    "    mass=10  \n",
    "    \n",
    "    \n",
    "    \n",
    "    MaxFreq2=E*s/mass\n",
    "    dt= 1/(6.283185*sqrt(MaxFreq2))\n",
    "#     dt=0.0001646\n",
    "    println(\"dt: $dt\")\n",
    "#     println(N_force)\n",
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
    "    \n",
    "    append!(displacements,[Array(metavoxel[\"N_displacementGPU\"])])\n",
    "    \n",
    "    t=@timed doTimeStep!(metavoxel,dt,0)\n",
    "    append!(displacements,[Array(metavoxel[\"N_displacementGPU\"])])\n",
    "    time=t[2]\n",
    "    println(\"first timestep took $time seconds\")\n",
    "    t=@timed simulateParallel!(metavoxel,numTimeSteps-1,dt,returnEvery)\n",
    "    time=t[2]\n",
    "    \n",
    "    if save\n",
    "        updateDataAndSave!(metavoxel,setup,\"../../json/trialJuliaParallelGPU.json\")\n",
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
    "    end\n",
    "    println(\"ran latticeSize $latticeSize with $voxCount voxels and $linkCount edges for $numTimeSteps time steps took $time seconds\")\n",
    "    return\n",
    "end"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 137,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "fea (generic function with 1 method)"
      ]
     },
     "execution_count": 137,
Amira Abdel-Rahman's avatar
Amira Abdel-Rahman committed
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "function fea(setup)\n",
    "    #######################################################\n",
    "    function points(element, properties)\n",
    "        elements = properties[\"elements\"]\n",
    "        nodes = properties[\"nodes\"]\n",
    "        degrees_of_freedom = properties[\"degrees_of_freedom\"]\n",
    "\n",
    "        # find the nodes that the lements connects\n",
    "        fromNode = elements[element][1]\n",
    "        toNode = elements[element][2]\n",
    "\n",
    "        # the coordinates for each node\n",
    "        fromPoint = nodes[fromNode]\n",
    "        toPoint = nodes[toNode]\n",
    "\n",
    "        # find the degrees of freedom for each node\n",
    "        dofs = degrees_of_freedom[fromNode]\n",
    "        dofs=vcat(dofs,degrees_of_freedom[toNode])\n",
    "\n",
    "        return fromPoint, toPoint, dofs\n",
    "    end\n",