internal void CalculateStatic()
        {
            // Статический расчёт!

            // 0. Разбиваем модель на элементы:
            //    Незагруженные распределённой нагрузкой стержни берём целиком,
            //    в противном случае - делим стержень на несколько элементов
            // 1. Создаём список узлов
            Nodes.Clear();
            for (int i = 0; i < CompsList.Count; i++)
            {
                if (CompsList[i].CompType == ComponentTypes.ctNode)
                {
                    Nodes.Add((ComponentNode)CompsList[i]);
                }
            }
            // В соответствии с количеством узлов создаём матрицу жёсткости системы и заполняем её нулями
            // Для каждого узла - три возможных перемещения
            // 0 - горизонтальное
            // 1 - вертикальное
            // 2 - поворот
            GlobalMatrix = new double[Nodes.Count * 3, Nodes.Count * 3];
            for (int i = 0; i < Nodes.Count; i++)
            {
                for (int j = 0; j < Nodes.Count; j++)
                {
                    GlobalMatrix[i, j] = 0;
                }
            }

            // 2. Создаём балочные элементы и заполняем глобальную матрицу
            Rods.Clear();
            for (int i = 0; i < CompsList.Count; i++)
            {
                if (CompsList[i].CompType == ComponentTypes.ctLinear)
                {
                    ComponentNode n1  = ((ComponentLinear)CompsList[i]).StartNode;
                    ComponentNode n2  = ((ComponentLinear)CompsList[i]).EndNode;
                    int           n1i = getNodeIndex(n1);
                    int           n2i = getNodeIndex(n2);
                    ElementBeam   b   = new ElementBeam((ComponentLinear)CompsList[i], this);
                    Rods.Add(b);
                    // Встраиваем матрицу жёсткости элемента в глобальную матрицу жёсткости
                    for (int row = 0; row < 6; row++)
                    {
                        for (int col = 0; col < 6; col++)
                        {
                            int r, c;
                            if (row < 3)
                            {
                                r = n1i * 3 + row;
                            }
                            else
                            {
                                r = n2i * 3 + row - 3;
                            }
                            if (col < 3)
                            {
                                c = n1i * 3 + col;
                            }
                            else
                            {
                                c = n2i * 3 + col - 3;
                            }
                            GlobalMatrix[r, c] += b.ExtMatrix[row, col];
                        }
                    }
                }
            }

            // 3. Создаём вектор узловых сил.
            Loads = new double[Nodes.Count * 3];
            for (int i = 0; i < Loads.Length; i++)
            {
                Loads[i] = 0;
            }
            for (int i = 0; i < CompsList.Count; i++)
            {
                if (CompsList[i].CompType == ComponentTypes.ctForce)
                {
                    ComponentLoad load = (ComponentLoad)CompsList[i];
                    ComponentNode n    = load.AppNodes[0];
                    // Сила приложена к узлу, её нужно разложить на
                    // две составляющие в глобальной системе координат
                    // - горизонтальную и вертикальную
                    // Поскольку в одном узле может быть несколько сил -
                    // складываем их
                    double force  = load.Value;
                    double cosa   = Math.Cos(load.Direction / 180 * Math.PI);
                    double sina   = Math.Sin(load.Direction / 180 * Math.PI);
                    double forceX = force * cosa;
                    double forceY = force * sina;
                    int    ind    = getNodeIndex(n) * 3;
                    // При этом, если в узле есть связь, запрещающая перемещения по указанному направлению, то
                    // соответствующую часть силы обнуляем
                    if (ind > -1)
                    {
                        // Сила по X
                        if (!n.DisallowedDisplacements.Contains(NodeDisplacement.X))
                        {
                            Loads[ind] += forceX;
                        }
                        // Сила по Y
                        if (!n.DisallowedDisplacements.Contains(NodeDisplacement.Y))
                        {
                            Loads[ind + 1] += forceY;
                        }
                    }
                }

                if (CompsList[i].CompType == ComponentTypes.ctDistributedLoad)
                {
                    // Распределённую нагрузку приводим к узловой
                    ComponentLoad   load = (ComponentLoad)CompsList[i];
                    ComponentLinear lc   = load.Beam;
                    // Найдём элемент, созданный на основе компонента lc и сообщим ему,
                    // что на нём лежит нагрузка load
                    ElementBeam beam = Rods.Find(b => b.Linear == lc);
                    if (beam != null)
                    {
                        beam.CalcEquivalentlReactions(load);
                        int ind = getNodeIndex(lc.StartNode) * 3;
                        if (ind > -1)
                        {
                            // Сила по X
                            if (!lc.StartNode.DisallowedDisplacements.Contains(NodeDisplacement.X))
                            {
                                Loads[ind] += beam.Rx1g;
                            }
                            // Сила по Y
                            if (!lc.StartNode.DisallowedDisplacements.Contains(NodeDisplacement.Y))
                            {
                                Loads[ind + 1] += beam.Ry1g;
                            }
                            // Момент
                            if (!lc.StartNode.DisallowedDisplacements.Contains(NodeDisplacement.Rotation))
                            {
                                Loads[ind + 2] += beam.M1g;
                            }
                        }
                        ind = getNodeIndex(lc.EndNode) * 3;
                        if (ind > -1)
                        {
                            // Сила по X
                            if (!lc.EndNode.DisallowedDisplacements.Contains(NodeDisplacement.X))
                            {
                                Loads[ind] += beam.Rx2g;
                            }
                            // Сила по Y
                            if (!lc.EndNode.DisallowedDisplacements.Contains(NodeDisplacement.Y))
                            {
                                Loads[ind + 1] += beam.Ry2g;
                            }
                            // Момент
                            if (!lc.EndNode.DisallowedDisplacements.Contains(NodeDisplacement.Rotation))
                            {
                                Loads[ind + 2] += beam.M2g;
                            }
                        }
                    }
                }
            }

            // 4. Применяем ограничения
            for (int i = 0; i < CompsList.Count; i++)
            {
                if (CompsList[i].CompType == ComponentTypes.ctNode)
                {
                    Block((ComponentNode)CompsList[i]);
                }
            }
            // 5. Получаем перемещения узлов в глобальной системе координат
            double[,] GlobalInverted = StarMath.inverse(GlobalMatrix);
            Displacements            = StarMath.multiply(GlobalInverted, Loads);
            // "Подчистим" перемещения от сверхмалых значений
            CleanupDisplacements();
            // Определим значения реакций в узлах - они же внутренние усилия
            for (int i = 0; i < Rods.Count; i++)
            {
                Rods[i].CalculateForces();
            }
        }
Exemple #2
0
        //rewrite
        private void MenuItem_Click(object sender, RoutedEventArgs e)
        {
            procModel = new ProcModel(Nodes.ToList(), Rods.ToList(), TypeRigidSupp);
            string result = "";

            for (int i = 0; i < procModel.matrixA.Count; i++)
            {
                for (int j = 0; j < procModel.matrixA.Count; j++)
                {
                    result += " " + procModel.matrixA[i][j].ToString();
                }
                result += "\n";
            }

            txtBox.Document.Blocks.Clear();
            txtBox.AppendText(result);

            string vecReactRes = "";

            foreach (var element in procModel.vectorReaction)
            {
                vecReactRes += element + " ";
            }

            string vecMovement = "";

            foreach (var element in procModel.vectorMovement)
            {
                vecMovement += element + " ";
            }

            string vecNullN = "";

            foreach (var element in procModel.vectorFromNullN)
            {
                vecNullN += element + " ";
            }

            string vecLengthN = "";

            foreach (var element in procModel.vectorFromLengthN)
            {
                vecLengthN += element + " ";
            }

            string vecNullU = "";

            foreach (var element in procModel.vectorFromNullU)
            {
                vecNullU += element + " ";
            }

            string vecLengthU = "";

            foreach (var element in procModel.vectorFromLengthU)
            {
                vecLengthU += element + " ";
            }

            string vecNullNormStress = "";

            foreach (var element in procModel.vectorFromNullNormStress)
            {
                vecNullNormStress += element + " ";
            }

            string vecLengthNormStress = "";

            foreach (var element in procModel.vectorFromLengthNormStress)
            {
                vecLengthNormStress += element + " ";
            }



            txtBox.AppendText("\n" + vecReactRes + "  -React vector" + "\n" + vecMovement + " -Movement vector" + "\n" + vecLengthN + " -Vector N(L)"
                              + "\n" + vecNullN + " -Vector N(0)" + "\n" + vecNullU + " -Vector U(0)" + "\n" + vecLengthU + " VectorU(L)" +
                              "\n" + vecNullNormStress + " -Vector normal stress(0)" + "\n" + vecLengthNormStress + " -Vector normal stress(L)");
        }