public Matrix CalcLocalStiffnessMatrix(Element targetElement)
        {
            var intg = new GaussianIntegrator();

            intg.GammaPointCount = 2;
            intg.XiPointCount    = 2;
            intg.EtaPointCount   = 2;

            intg.A2 = 1;
            intg.A1 = -1;

            intg.F2 = (gama => + 1);
            intg.F1 = (gama => - 1);

            intg.G2 = (eta, gama) => + 1;
            intg.G1 = (eta, gama) => - 1;

            intg.H = new FunctionMatrixFunction((xi, eta, gamma) =>
            {
                var b = this.GetBMatrixAt(targetElement, new double[] { xi, eta, gamma });
                var d = this.GetDMatrixAt(targetElement, new double[] { xi, eta, gamma });
                var j = this.GetJMatrixAt(targetElement, new double[] { xi, eta, gamma });

                var buf = targetElement.MatrixPool.Allocate(b.ColumnCount, b.ColumnCount);

                CalcUtil.Bt_D_B(b, d, buf);

                //var detj = Math.Abs(j.Determinant());

                //buf.MultiplyByConstant(detj);

                return(buf);
            });

            var res = intg.Integrate();

            return(res);
        }
        public Force[] GetLocalEquivalentNodalLoads(Element targetElement, ElementalLoad load)
        {
            var tr = targetElement.GetTransformationManager();

            #region uniform

            if (load is BriefFiniteElementNet.Loads.UniformLoad)
            {
                var ul = load as BriefFiniteElementNet.Loads.UniformLoad;

                var localDir = ul.Direction.GetUnit();

                if (ul.CoordinationSystem == CoordinationSystem.Global)
                {
                    localDir = tr.TransformGlobalToLocal(localDir);
                }

                var ux = localDir.X * ul.Magnitude;
                var uy = localDir.Y * ul.Magnitude;
                var uz = localDir.Z * ul.Magnitude;

                var intg = new GaussianIntegrator();

                intg.A1 = -1;
                intg.A2 = 1;

                intg.F1 = gama => - 1;
                intg.F2 = gama => 1;

                intg.G1 = (eta, gama) => 0;
                intg.G2 = (eta, gama) => 1;

                intg.GammaPointCount = 1;
                intg.XiPointCount    = intg.EtaPointCount = 2;

                intg.H = new FunctionMatrixFunction((xi, eta, gama) =>
                {
                    var shp = GetNMatrixAt(targetElement, xi, eta, 0);
                    var j   = GetJMatrixAt(targetElement, xi, eta, 0);
                    shp.MultiplyByConstant(j.Determinant());
                    shp.MultiplyByConstant(uz);

                    return(shp);
                }
                                                    );


                var res = intg.Integrate();

                var localForces = new Force[4];

                for (var i = 0; i < 4; i++)
                {
                    localForces[i] = new Force(0, 0, res[i, 0], 0, 0, 0);
                }

                throw new NotImplementedException();
                var globalForces = localForces.Select(i => tr.TransformLocalToGlobal(i)).ToArray();

                return(globalForces);
            }

            #endregion

            #region non uniform
            if (load is BriefFiniteElementNet.Loads.PartialNonUniformLoad)  // TODO
            {
                //TODO
                throw new NotImplementedException();

                var ul = load as BriefFiniteElementNet.Loads.PartialNonUniformLoad;

                var localDir = ul.Direction.GetUnit();

                if (ul.CoordinationSystem == CoordinationSystem.Global)
                {
                    localDir = tr.TransformGlobalToLocal(localDir);
                }

                /*
                 * var interpolator = new Func<double, double, double>((xi,eta)=>
                 * {
                 *  var shp = GetNMatrixAt(targetElement, xi, eta, 0).Transpose();
                 *  var frc = new Matrix(4, 1);
                 *  //frc.FillColumn(0, ul.NodalMagnitudes);
                 *  var mult = shp * frc;
                 *
                 *  return mult[0, 0];
                 * });
                 *
                 * var ux = new Func<double, double, double>((xi, eta) => localDir.X * interpolator(xi, eta));
                 * var uy = new Func<double, double, double>((xi, eta) => localDir.Y * interpolator(xi, eta));
                 * var uz = new Func<double, double, double>((xi, eta) => localDir.Z * interpolator(xi, eta));
                 */

                var st = ul.StartLocation;
                var en = ul.EndLocation;

                var intg = new GaussianIntegrator();

                intg.A1 = 0;
                intg.A2 = 1;

                intg.F1 = gama => st.Eta;
                intg.F2 = gama => en.Eta;

                intg.G1 = (eta, gama) => st.Xi;
                intg.G2 = (eta, gama) => en.Xi;

                var order = ul.SeverityFunction.Degree;

                intg.GammaPointCount = 1;
                intg.XiPointCount    = intg.EtaPointCount = 2;

                throw new Exception();

                intg.H = new FunctionMatrixFunction((xi, eta, gama) =>
                {
                    var shp = GetNMatrixAt(targetElement, xi, eta, 0);
                    var j   = GetJMatrixAt(targetElement, xi, eta, 0);
                    shp.MultiplyByConstant(j.Determinant());

                    //var uzm = ul.SeverityFunction.Evaluate(xi, eta);

                    //shp.MultiplyByConstant(uzm);

                    return(shp);
                }
                                                    );

                var res = intg.Integrate();

                var localForces = new Force[4];

                for (var i = 0; i < 4; i++)
                {
                    localForces[i] = new Force(0, 0, res[i, 0], 0, 0, 0);
                }

                return(localForces);
            }

            #endregion

            throw new NotImplementedException();
        }
        public static Matrix CalcLocalKMatrix_Bar(IElementHelper helper, Element targetElement)
        {
            var elm = targetElement as BarElement;

            if (elm == null)
            {
                throw new Exception();
            }

            var nb = helper.GetBMaxOrder(targetElement);
            var nd = elm.Material.GetMaxFunctionOrder();
            var nt = elm.Section.GetMaxFunctionOrder();
            var nj = helper.GetDetJOrder(targetElement);


            var sum = new int[3];

            foreach (var i in new int[][] { nb, nd, nb, nt, nj })//B D B |J|
            {
                for (int j = 0; j < 3; j++)
                {
                    sum[j] += i[j];
                }
            }

            var nXi   = sum[0] / 2 + 1;
            var nEta  = sum[1] / 2 + 1;
            var nGama = sum[2] / 2 + 1;

            //nXi += 2;

            //var ng = (2*nb + nd + nj)/2 + 1;
            var intg = new GaussianIntegrator();

            intg.A1 = 0;
            intg.A2 = 1;

            intg.F1            = (gama => 0);
            intg.F2            = (gama => 1);
            intg.EtaPointCount = 1;

            intg.G1 = (eta, gamma) => - 1;
            intg.G2 = (eta, gamma) => + 1;

            intg.GammaPointCount = nGama;
            intg.XiPointCount    = nXi;
            intg.EtaPointCount   = nEta;

            /*
             * intg.H = new FunctionMatrixFunction((xi, eta, gama) =>
             * {
             *  var b = helper.GetBMatrixAt(elm, xi);
             *  var d = helper.GetDMatrixAt(elm, xi);
             *  var j = helper.GetJMatrixAt(elm, xi);
             *
             *  var buf_ =
             *      //new Matrix(b.ColumnCount, b.ColumnCount);
             *      targetElement.CreateOrRentMatrixFromPool(b.ColumnCount, b.ColumnCount);
             *
             *  Matrix.TransposeMultiply(b, b, buf_);
             *
             *  //var buf_2 = b.Transpose() * d * b;
             *  buf_.MultiplyByConstant(d[0, 0] * Math.Abs(j.Determinant()));
             *
             *  b.ReturnToPool();
             *  d.ReturnToPool();
             *  j.ReturnToPool();
             *
             *  return buf_;
             * });*/

            intg.H = new MultiplierMatrixFunction(elm, helper);

            intg.MatrixPool = elm.MatrixPool;

            var res = intg.Integrate();

            return(res);
        }
        public static Matrix CalcLocalKMatrix_Triangle(IElementHelper helper, Element targetElement)
        {
            var qq = targetElement as TriangleElement;

            if (qq == null)
            {
                throw new Exception();
            }

            var trans = qq.GetLambdaMatrix().Transpose();

            var nb = helper.GetBMaxOrder(targetElement);
            var nd = qq.Material.GetMaxFunctionOrder();
            var nt = qq.Section.GetMaxFunctionOrder();
            var nj = helper.GetDetJOrder(targetElement);

            var sum = new int[3];

            foreach (var i in new int[][] { nb, nd, nb, nt, nj })
            {
                for (int j = 0; j < 3; j++)
                {
                    sum[j] += i[j];
                }
            }

            var nXi   = sum[0] / 2 + 1;
            var nEta  = sum[1] / 2 + 1;
            var nGama = sum[2] / 2 + 1;

            var intg = new GaussianIntegrator();

            intg.GammaPointCount = nGama;
            intg.XiPointCount    = nXi;
            intg.EtaPointCount   = nEta;

            intg.A2 = 1;
            intg.A1 = 0;

            intg.F2 = (gama => 1);
            intg.F1 = (gama => 0);

            intg.G2 = ((eta, gama) => 1 - eta);
            intg.G1 = ((eta, gama) => 0);

            intg.H = new FunctionMatrixFunction((xi, eta, gama) =>
            {
                var b = helper.GetBMatrixAt(qq, xi, eta);
                var d = helper.GetDMatrixAt(qq, xi, eta);
                var j = helper.GetJMatrixAt(qq, xi, eta);

                var buf = new Matrix(b.ColumnCount, b.ColumnCount);

                CalcUtil.Bt_D_B(b, d, buf);

                buf.MultiplyByConstant((j.Determinant()));

                return(buf);
            });

            var res = intg.Integrate();

            return(res);
        }
        public static Matrix CalcLocalCMatrix_Bar(IElementHelper helper, Element targetElement)
        {
            var elm = targetElement as BarElement;

            if (elm == null)
            {
                throw new Exception();
            }

            var nn = helper.GetNMaxOrder(targetElement);
            var nd = elm.Material.GetMaxFunctionOrder();
            var nt = elm.Section.GetMaxFunctionOrder();
            var nj = helper.GetDetJOrder(targetElement);

            var sum = new int[3];

            foreach (var i in new int[][] { nn, nd, nt, nn, nj })
            {
                for (int j = 0; j < 3; j++)
                {
                    sum[j] += i[j];
                }
            }

            var nXi   = sum[0] / 2 + 1;
            var nEta  = sum[1] / 2 + 1;
            var nGama = sum[2] / 2 + 1;

            //var nRho = elm.Material.GetMaxFunctionOrder().Max() + elm.Section.GetMaxFunctionOrder();
            //var ng = (2 * nn + nRho + nj) / 2 + 1;

            var intg = new GaussianIntegrator();

            intg.GammaPointCount = nGama;
            intg.XiPointCount    = nXi;
            intg.EtaPointCount   = nEta;

            intg.A1 = 0;
            intg.A2 = 1;

            intg.F1            = (gama => 0);
            intg.F2            = (gama => 1);
            intg.EtaPointCount = 1;

            intg.G1 = (eta, gamma) => - 1;
            intg.G2 = (eta, gamma) => + 1;
            //intg.XiPointCount = ng;

            intg.H = new FunctionMatrixFunction((xi, eta, gama) =>
            {
                var n  = helper.GetNMatrixAt(elm, xi);
                var mu = helper.GetMuMatrixAt(elm, xi);
                var j  = helper.GetJMatrixAt(elm, xi);

                var buf_ = n.Transpose() * mu * n;
                buf_.MultiplyByConstant(j.Determinant());

                return(buf_);
            });

            var res = intg.Integrate();

            return(res);
        }
Exemple #6
0
        public Force[] GetLocalEquivalentNodalLoads(Element targetElement, Load load)
        {
            //https://www.quora.com/How-should-I-perform-element-forces-or-distributed-forces-to-node-forces-translation-in-the-beam-element

            if (load is Loads.UniformLoad)
            {
                var ul = load as Loads.UniformLoad;

                var localDir = ul.Direction;

                if (ul.CoordinationSystem == CoordinationSystem.Global)
                {
                    var tr = targetElement.GetTransformationManager();
                    localDir = tr.TransformGlobalToLocal(ul.Direction);
                }

                var ux = localDir.X * ul.Magnitude;
                var uy = localDir.Y * ul.Magnitude;
                var uz = localDir.Z * ul.Magnitude;

                var intg = new GaussianIntegrator();
                intg.A1           = -1;
                intg.A2           = +1;
                intg.XiPointCount = 2;
                intg.H            = new FunctionMatrixFunction((xi, eta, gama) =>
                {
                    var mtx = new Matrix(4, 0);
                    var shp = GetNMatrixAt(targetElement, xi, eta, gama);

                    return(shp);
                });

                var res = intg.Integrate();

                var buf = new Force[2];

                var fy0 = res[0, 0];
                var mz0 = res[1, 0];
                var fy1 = res[2, 0];
                var mz1 = res[3, 0];

                buf[0] = new Force(0, fy0, 0, 0, 0, mz0);
                buf[1] = new Force(0, fy1, 0, 0, 0, mz1);

                return(buf);
            }


            if (load is Loads.ConcentratedLoad)
            {
                var ul = load as Loads.ConcentratedLoad;

                var localforce = ul.Force;

                if (ul.CoordinationSystem == CoordinationSystem.Global)
                {
                    var tr = targetElement.GetTransformationManager();
                    localforce = tr.TransformGlobalToLocal(ul.Force);
                }

                var shp = GetNMatrixAt(targetElement, ul.ForceIsoLocation);
                throw new NotImplementedException();
            }

            throw new NotImplementedException();
        }
        public Force[] GetLocalEquivalentNodalLoads(Element targetElement, ElementalLoad load)
        {
            var hex = targetElement as HexahedralElement;
            var n   = hex.Nodes.Length;


            var tr = targetElement.GetTransformationManager();

            #region uniform

            if (load is UniformLoad || load is PartialNonUniformLoad)
            {
                Func <double, double> magnitude;
                Vector localDir;

                double xi0, xi1;
                double eta0, eta1;
                double lambda0, lambda1;

                int degree;//polynomial degree of magnitude function

                #region inits
                if (load is UniformLoad)
                {
                    var uld = (load as UniformLoad);

                    magnitude = (xi => uld.Magnitude);
                    localDir  = uld.Direction;

                    if (uld.CoordinationSystem == CoordinationSystem.Global)
                    {
                        localDir = tr.TransformGlobalToLocal(localDir);
                    }

                    localDir = localDir.GetUnit();

                    xi0 = -1;
                    xi1 = 1;

                    eta0 = -1;
                    eta1 = 1;

                    lambda0 = -1;
                    lambda1 = 1;

                    degree = 0;
                }
                else if (load is PartialNonUniformLoad)
                {
                    var uld = (load as PartialNonUniformLoad);

                    magnitude = (xi => uld.GetMagnitudeAt(targetElement, new IsoPoint(xi)));
                    localDir  = uld.Direction;

                    if (uld.CoordinationSystem == CoordinationSystem.Global)
                    {
                        localDir = tr.TransformGlobalToLocal(localDir);
                    }

                    localDir = localDir.GetUnit();

                    xi0 = uld.StartLocation.Xi;
                    xi1 = uld.EndLocation.Xi;

                    eta0 = uld.StartLocation.Eta;
                    eta1 = uld.EndLocation.Eta;

                    lambda0 = uld.StartLocation.Lambda;
                    lambda1 = uld.EndLocation.Lambda;

                    degree = uld.SeverityFunction.Degree[0];// Coefficients.Length;
                }
                else
                {
                    throw new NotImplementedException();
                }

                localDir = localDir.GetUnit();
                #endregion

                {
                    var nOrd = GetNMaxOrder(targetElement);

                    //var gpt = (nOrd + degree) / 2 + 1;//gauss point count

                    var intg = new GaussianIntegrator();

                    intg.A1 = lambda0;
                    intg.A2 = lambda1;

                    intg.F1 = gama => eta0;
                    intg.F2 = gama => eta1;

                    intg.G1 = (eta, gama) => xi0;
                    intg.G2 = (eta, gama) => xi1;

                    intg.XiPointCount    = (nOrd[0] + degree) / 2 + 1;
                    intg.EtaPointCount   = (nOrd[1] + degree) / 2 + 1;
                    intg.GammaPointCount = (nOrd[2] + degree) / 2 + 1;

                    intg.MatrixPool = hex.MatrixPool;

                    intg.H = new FunctionMatrixFunction((xi, eta, gama) =>
                    {
                        var shp = GetNMatrixAt(targetElement, xi, eta, gama);

                        var shp2 = hex.MatrixPool.Allocate(3, shp.ColumnCount);

                        shp2.AssembleInside(shp, 0, 0);
                        shp2.AssembleInside(shp, 1, 0);
                        shp2.AssembleInside(shp, 2, 0);


                        var j = GetJMatrixAt(targetElement, xi, 0, 0);
                        shp.MultiplyByConstant(j.Determinant());

                        var q__ = magnitude(xi);

                        var q_ = localDir * q__;

                        shp2.MultiplyRowByConstant(0, q_.X);
                        shp2.MultiplyRowByConstant(1, q_.Y);
                        shp2.MultiplyRowByConstant(2, q_.Z);

                        return(shp2);
                    });


                    var res = intg.Integrate();

                    var localForces = new Force[2];

                    //res is 3x8 matrix, each columns has x,y and z components for force on each node
                    for (var i = 0; i < 8; i++)
                    {
                        var fx = res[0, i];
                        var fy = res[1, i];
                        var fz = res[2, i];

                        localForces[i] = new Force(fx, fy, fz, 0, 0, 0);
                    }

                    return(localForces);
                }
            }

            #endregion

            #region ConcentratedLoad

            if (load is ConcentratedLoad)
            {
                var cl = load as ConcentratedLoad;

                var localforce = cl.Force;

                if (cl.CoordinationSystem == CoordinationSystem.Global)
                {
                    localforce = tr.TransformGlobalToLocal(localforce);
                }

                var buf = new Force[n];

                var ns = GetNMatrixAt(targetElement, cl.ForceIsoLocation.Xi, cl.ForceIsoLocation.Eta, cl.ForceIsoLocation.Lambda);

                for (var i = 0; i < n; i++)
                {
                    buf[i] = localforce * ns[0, i];
                }

                return(buf);
            }

            #endregion


            throw new NotImplementedException();
        }
        public static Matrix CalcLocalKMatrix_Triangle(IElementHelper helper, Element targetElement)
        {
            var tri = targetElement as TriangleElement;

            if (tri == null)
            {
                throw new Exception();
            }

            var trans = tri.GetLambdaMatrix().Transpose();

            //var nb = helper.GetBMaxOrder(targetElement);
            //var nd = tri.Material.GetMaxFunctionOrder();
            //var nt = tri.Section.GetMaxFunctionOrder().Max();
            //var nj = helper.GetDetJOrder(targetElement);


            var nn = helper.GetNMaxOrder(targetElement);
            var nd = tri.Material.GetMaxFunctionOrder();
            var nt = tri.Section.GetMaxFunctionOrder();
            var nj = helper.GetDetJOrder(targetElement);

            var sum = new int[3];

            foreach (var i in new int[][] { nn, nd, nt, nn, nj })
            {
                for (int j = 0; j < 3; j++)
                {
                    sum[j] += i[j];
                }
            }

            var nXi   = sum[0] / 2 + 1;
            var nEta  = sum[1] / 2 + 1;
            var nGama = sum[2] / 2 + 1;



            //var ng = (nb + nd + nt + nj)/2 + 1;

            var intg = new GaussianIntegrator();

            intg.GammaPointCount = nGama;
            intg.XiPointCount    = nXi;
            intg.EtaPointCount   = nEta;

            intg.A2 = 1;
            intg.A1 = 0;

            intg.F2 = (gama => 1);
            intg.F1 = (gama => 0);

            intg.G2 = ((eta, gama) => 1 - eta);
            intg.G1 = ((eta, gama) => 0);

            //intg.GammaPointCount = 1;
            //intg.XiPointCount = intg.EtaPointCount = ng;

            intg.H = new FunctionMatrixFunction((xi, eta, gama) =>
            {
                var b = helper.GetBMatrixAt(tri, xi, eta);
                var d = helper.GetDMatrixAt(tri, xi, eta);
                var j = helper.GetJMatrixAt(tri, xi, eta);
                var t = tri.Section.GetThicknessAt(xi, eta);

                var buf = MatrixPool.Allocate(9, 9);

                CalcUtil.Bt_D_B(b, d, buf);

                buf.MultiplyByConstant(t * j.Determinant());

                return(buf);
            });

            var res = intg.Integrate();

            return(res);
        }
        public static Matrix CalcLocalKMatrix_Quad(IElementHelper helper, Element targetElement)
        {
            var qq = targetElement as QuadrilaturalElement;

            if (qq == null)
            {
                throw new Exception();
            }

            var trans = qq.GetLambdaMatrix().Transpose();

            var nb = helper.GetBMaxOrder(targetElement);
            var nd = qq.Material.GetMaxFunctionOrder();
            var nt = qq.Section.GetMaxFunctionOrder();
            var nj = helper.GetDetJOrder(targetElement);

            var sum = new int[3];

            foreach (var i in new int[][] { nb, nd, nb, nt, nj })
            {
                for (int j = 0; j < 3; j++)
                {
                    sum[j] += i[j];
                }
            }

            var nXi   = sum[0] / 2 + 1;
            var nEta  = sum[1] / 2 + 1;
            var nGama = sum[2] / 2 + 1;

            var intg = new GaussianIntegrator();

            intg.GammaPointCount = nGama;
            intg.XiPointCount    = nXi;
            intg.EtaPointCount   = nEta;

            intg.A2 = 1;
            intg.A1 = 0;

            intg.F2 = (gama => + 1);
            intg.F1 = (gama => - 1);

            intg.G2 = (eta, gama) => + 1;
            intg.G1 = (eta, gama) => - 1;   // formula 4.53 (Development of Membrane, Plate and Flat Shell Elements in Java) --> see GaussianIntegrator.cs for correct variable assignment

            intg.H = new FunctionMatrixFunction((xi, eta, gama) =>
            {
                var b    = helper.GetBMatrixAt(qq, xi, eta);
                var d    = helper.GetDMatrixAt(qq, xi, eta);
                var j    = helper.GetJMatrixAt(qq, xi, eta);
                var detj = Math.Abs(j.Determinant());

                var buf = new Matrix(b.ColumnCount, b.ColumnCount); // result matrix , TODO: use matrix pool

                CalcUtil.Bt_D_B(b, d, buf);                         // multiplicates three matrices

                buf.Scale(detj);

                return(buf);
            });


            var res = intg.Integrate();

            return(res);
        }
        public static Matrix CalcLocalKMatrix_Tetrahedron(IElementHelper helper, Element targetElement)
        {
            var qq = targetElement as TetrahedronElement;

            if (qq == null)
            {
                throw new Exception();
            }

            var trans = qq.GetLambdaMatrix().Transpose();

            var nb = helper.GetBMaxOrder(targetElement);
            var nd = qq.Material.GetMaxFunctionOrder();
            var nj = helper.GetDetJOrder(targetElement);

            var sum = new int[3];

            foreach (var i in new int[][] { nb, nd, nb, nj })
            {
                for (int j = 0; j < 3; j++)
                {
                    sum[j] += i[j];
                }
            }

            var nXi   = sum[0] / 2 + 1;
            var nEta  = sum[1] / 2 + 1;
            var nGama = sum[2] / 2 + 1;

            var intg = new GaussianIntegrator();

            intg.GammaPointCount = nGama;
            intg.XiPointCount    = nXi;
            intg.EtaPointCount   = nEta;

            intg.A2 = 1;
            intg.A1 = 0;

            intg.F2 = (gama => 1 - gama);
            intg.F1 = (gama => 0);

            intg.G2 = ((eta, gama) => 1 - eta - gama);
            intg.G1 = ((eta, gama) => 0);

            intg.H = new FunctionMatrixFunction((xi, eta, gama) =>
            {
                var b = helper.GetBMatrixAt(qq, xi, eta);
                var d = helper.GetDMatrixAt(qq, xi, eta);
                var j = helper.GetJMatrixAt(qq, xi, eta);

                var buf = new Matrix(b.ColumnCount, b.ColumnCount);

                CalcUtil.Bt_D_B(b, d, buf);

                var detj = Math.Abs(j.Determinant());

                buf.Scale(detj); // is this correct? this is pretty close to formula 4.53 for DKQ-ELements (4.31 is without detj)

                return(buf);
            });

            var res = intg.Integrate();

            return(res);
        }