コード例 #1
0
    void updateDrawData()
    {
        int n_spokes = m_wheel_model.get_nspokes();

        m_spoke_lines       = new Vector3[n_spokes, 2];
        m_spoke_lines_color = new Color[n_spokes];
        m_kgf_pos           = new Vector3[n_spokes];
        m_kgf_pos_rect      = new Rect[n_spokes];
        m_font_kgf_st       = new GUIStyle[n_spokes];
        m_kgf_string        = new string[n_spokes];

        double angle = Math.Atan2(1.0, 1.0) * 8 / n_spokes;


        double rim_radius = m_wheel_model.get_rim_d_mm() / 2.0 / 1000.0;

        for (int i = 0; i < n_spokes; ++i)
        {
            Vector3 hub_point    = (Vector3)m_wheel_model.get_hub_point(i);
            Vector3 nipple_point = (Vector3)m_wheel_model.get_nipple_point(i);


            Vector3 center;
            if ((i % 2) == 0)
            {
                center = m_left_rect_center;
            }
            else
            {
                center = m_right_rect_center;
            }

            Vector3 edgep           = new Vector3((float)(center.x + Math.Sin(i * angle + angle * 0.5) * m_square_radius), (float)(center.y + Math.Cos(i * angle + angle * 0.5) * m_square_radius));
            Vector3 center_edge_vec = (edgep - center).normalized;



            Vector3 circle_p2 = edgep - center_edge_vec * (m_circle_button_radius * 2.2f);
            Vector3 circle_p1 = circle_p2 - center_edge_vec * (m_circle_button_radius * 2.2f);

            m_circle_buttons[i, 0] = circle_p1;
            m_circle_buttons[i, 1] = circle_p2;

            m_kgf_pos[i]      = circle_p1 - center_edge_vec * (m_font_black_st.lineHeight * 1.3f);
            m_kgf_pos_rect[i] = new Rect(m_kgf_pos[i].x - 50, (Screen.height - m_kgf_pos[i].y) - 50, 100, 100);

            m_kgf_string[i] = string.Format("{0}", (int)m_wheel_model.get_spoke_kgf(i));


            Vector3 p2 = m_kgf_pos[i] - center_edge_vec * (m_font_black_st.lineHeight);
            Vector3 p1 = center + (hub_point / (float)rim_radius) * ((p2 - center).magnitude);

            Vector3 hsv = m_wheel_model.get_hsv_stress(i);

            p1.z = 0;
            p2.z = 0;

            Color c = Color.HSVToRGB(hsv.x, hsv.y, hsv.z);

            m_spoke_lines[i, 0]    = p1;
            m_spoke_lines[i, 1]    = p2;
            m_spoke_lines_color[i] = c;

            m_font_kgf_st[i]                  = new GUIStyle();
            m_font_kgf_st[i].font             = m_font;
            m_font_kgf_st[i].fontSize         = (int)(m_square_radius * 0.075f);
            m_font_kgf_st[i].normal.textColor = Color.yellow;
            m_font_kgf_st[i].alignment        = TextAnchor.MiddleCenter;
        }
    }
コード例 #2
0
    void m_WheelModel_compute_and_rebuild_mesh()
    {
        m_WheelModel.compute();

        m_WheelModel_left_side_disbalance  = m_WheelModel.getSpokeForceKgfSideDisbalance(false);
        m_WheelModel_right_side_disbalance = m_WheelModel.getSpokeForceKgfSideDisbalance(true);

        double total_disbalance = m_WheelModel_left_side_disbalance + m_WheelModel_right_side_disbalance;

        if (total_disbalance < m_WheelModel.spokes_count)
        {
            m_wheel_quality_Text.text  = "Идеальное";
            m_wheel_quality_Text.color = new Color(0, 0.8f, 0);
        }
        else
        if (total_disbalance < m_WheelModel.spokes_count * 2)
        {
            m_wheel_quality_Text.text  = "Хорошее";
            m_wheel_quality_Text.color = new Color(0.5f, 0.8f, 0);
        }
        else
        if (total_disbalance < m_WheelModel.spokes_count * 4)
        {
            m_wheel_quality_Text.text  = "Сойдёт";
            m_wheel_quality_Text.color = new Color(0.8f, 0.8f, 0);
        }
        else
        if (total_disbalance < m_WheelModel.spokes_count * 6)
        {
            m_wheel_quality_Text.text  = "Плохое";
            m_wheel_quality_Text.color = new Color(0.8f, 0.5f, 0);
        }
        else
        {
            m_wheel_quality_Text.text  = "Ужасное";
            m_wheel_quality_Text.color = new Color(0.8f, 0, 0);
        };

        /*
         * for (int i=0; i<m_WheelModel.spokes_count; ++i )
         * {
         *  Log.g.add( string.Format("{0} {1:0.00}", i, m_WheelModel.getSpokeForceKgf( i )) );
         * }*/

        double angle_per_section = 360.0 / m_wheel_mesh_sections_count;

        Points3D[] rim_sections = new Points3D[m_wheel_mesh_sections_count + 1];
        for (int i = 0; i < m_wheel_mesh_sections_count + 1; ++i)
        {
            Points3D rim_section = m_rim_base_sections[i].copy();

            Vector3D rim_center         = m_WheelModel.get_rim_center();
            Vector3D rim_point          = m_WheelModel.getRimPointByAngle(i * angle_per_section, 0, 0);
            Vector3D rim_bent_egg_point = m_WheelModel.getRimPointByAngle(i * angle_per_section, m_bent_on_every_100kgf, m_egg_on_every_100kgf);
            Vector3D Y = (rim_center - rim_point).normalized();
            Vector3D X = -m_WheelModel.get_rim_cross_axis();

            rim_section.rotate(Matrix3x3.fromVerticalVectors(X, Y, X.cross(Y).normalized()), Vector3D.zero);

            double angle = Vector3D.angleBetween(rim_bent_egg_point - rim_center, rim_point - rim_center);
            if (angle > Math.PI / 10000)
            {
                rim_section.rotate(Y.cross(X).normalized(), angle, Vector3D.zero);
            }

            rim_section.move(rim_bent_egg_point);

            rim_sections[i] = rim_section;
        }

        Mesh rim_mesh = MeshCreator.createFromPoints3D(rim_sections);

        Quaternion wheel_rotation = Quaternion.identity;

        if (m_wheel_GO != null)
        {
            wheel_rotation = m_wheel_GO.transform.rotation;
            Destroy(m_wheel_GO);
            m_wheel_GO = null;
        }

        if (m_wheel_spoke_wrench_GO != null)
        {
            Destroy(m_wheel_spoke_wrench_GO);
            m_wheel_spoke_wrench_GO = null;
        }

        m_wheel_GO       = new GameObject("wheel");
        m_wheel_GO.layer = layer_wheel;

        m_wheel_spoke_wrench_GO = Instantiate(m_spoke_wrench_prefab, m_wheel_GO.transform);

        MeshFilter mf = m_wheel_GO.AddComponent <MeshFilter>();

        mf.mesh = rim_mesh;
        MeshRenderer mr = m_wheel_GO.AddComponent <MeshRenderer>();

        mr.material = m_rim_mat;
        MeshCollider mc = m_wheel_GO.AddComponent <MeshCollider>();

        mc.sharedMesh = rim_mesh;

        if (m_wheel_box_GO != null)
        {
            Destroy(m_wheel_box_GO);
            m_wheel_box_GO = null;
        }
        m_wheel_box_GO       = new GameObject("wheel_box");
        m_wheel_box_GO.layer = layer_wheel_box;
        BoxCollider wheel_box_GO_BoxCollider = m_wheel_box_GO.AddComponent <BoxCollider>();

        wheel_box_GO_BoxCollider.center = mc.bounds.center;
        wheel_box_GO_BoxCollider.size   = mc.bounds.size;

        //hub
        Vector3D hub_l  = m_WheelModel.get_hub_pos() + new Vector3D(0, 0, 1) * m_WheelModel.axle_length / 2;
        Vector3D hub_r  = m_WheelModel.get_hub_pos() + new Vector3D(0, 0, -1) * m_WheelModel.axle_length / 2;
        Vector3D hub_lr = hub_r - hub_l;

        Mesh       hub_mesh = MeshCreator.createHub(hub_l, hub_lr.normalized(), 40, 0.005, 0.002 + m_WheelModel.hub_d / 2, m_WheelModel.axle_length, m_WheelModel.l_dish, m_WheelModel.r_dish, 0.005);
        GameObject hub_GO   = new GameObject("hub");

        hub_GO.transform.parent = m_wheel_GO.transform;
        hub_GO.AddComponent <MeshFilter>().mesh       = hub_mesh;
        hub_GO.AddComponent <MeshRenderer>().material = m_hub_mat;

        m_wheel_nipples_GO = new GameObject[m_WheelModel.spokes_count];

        for (int i = 0; i < m_WheelModel.spokes_count; ++i)
        {
            Vector3D hub_point  = m_WheelModel.get_hub_point(i);
            Vector3D nip_point  = m_WheelModel.getRimPointBySpoke(i, m_bent_on_every_100kgf, m_egg_on_every_100kgf);
            Vector3D rim_center = m_WheelModel.get_rim_center();
            Vector3D nip_hub    = hub_point - nip_point;

            // spokes
            Mesh spoke_mesh = MeshCreator.createCylinder(0.001, nip_hub.length(), 8, nip_point, nip_hub.normalized(), 0.0);

            GameObject spoke_GO = new GameObject("spoke");
            spoke_GO.transform.parent = m_wheel_GO.transform;
            spoke_GO.AddComponent <MeshFilter>().mesh       = spoke_mesh;
            spoke_GO.AddComponent <MeshRenderer>().material = m_spoke_mat;

            //nipple
            float nipple_rev_deg = (float)m_WheelModel.getNippleRotate(i) * m_WheelModel_force_modifier * Mathf.PI * 2 * Mathf.Rad2Deg;

            GameObject nipple_GO = Instantiate(m_nipple_prefab);
            nipple_GO.transform.parent        = spoke_GO.transform;
            nipple_GO.transform.localPosition = nip_point.toVector3();
            nipple_GO.transform.localRotation = Quaternion.LookRotation((hub_point - nip_point).normalized().toVector3(),
                                                                        m_WheelModel.get_rim_cross_axis().toVector3())
                                                *
                                                Quaternion.AngleAxis(nipple_rev_deg + m_WheelModel_spokes_rev90_offset[i] * 90, -Vector3.forward);
            m_wheel_nipples_GO[i] = nipple_GO;

            // eyelets
            Vector3D eyelet_center = nip_point;
            Vector3D eyelet_vector = m_WheelModel.get_rim_center() - eyelet_center;

            double eyelet_inner_dia               = 0.0038;
            double eyelet_outter_dia              = 0.0075;
            double eyelet_torus_circle_radius     = (eyelet_outter_dia - eyelet_inner_dia) / 4;
            int    eyelet_half_torus_points_count = 3;
            int    eyelet_section_count           = 12;

            Points3D[] eyelet_sections = new Points3D[eyelet_section_count];

            double torus_rad_per_section = 2 * Math.PI / (eyelet_section_count);

            for (int n_section = 0; n_section < eyelet_section_count; ++n_section)
            {
                Points3D eyelet_section      = new Points3D();
                double   torus_rad_per_point = Math.PI / (eyelet_half_torus_points_count - 1);
                for (int n_point = 0; n_point < eyelet_half_torus_points_count; ++n_point)
                {
                    eyelet_section.addPoint(
                        new Vector3D(Math.Cos(n_point * torus_rad_per_point) * eyelet_torus_circle_radius, Math.Sin(n_point * torus_rad_per_point) * eyelet_torus_circle_radius, 0)
                        );
                }
                eyelet_section.move(new Vector3D(-(eyelet_inner_dia / 2 + eyelet_torus_circle_radius), 0, 0));
                eyelet_section.rotate(new Vector3D(0, 1, 0), n_section * torus_rad_per_section, Vector3D.zero);
                eyelet_section.rotate(Matrix3x3.getRotationMatrixLookAtYAxis(new Vector3D(0, 0, 1), eyelet_vector.normalized()), Vector3D.zero);
                eyelet_section.move(eyelet_center);

                eyelet_sections[n_section] = eyelet_section;
            }
            Mesh eyelet_mesh = MeshCreator.createFromLoopPoints3D(eyelet_sections);

            GameObject eyelet_GO = new GameObject("eyelet");
            eyelet_GO.transform.parent = spoke_GO.transform;
            eyelet_GO.AddComponent <MeshFilter>().mesh       = eyelet_mesh;
            eyelet_GO.AddComponent <MeshRenderer>().material = m_eyelet_mat;

            Mesh       eyelet_low_circle_mesh = MeshCreator.createCircle(eyelet_inner_dia / 2 + eyelet_torus_circle_radius, eyelet_section_count, eyelet_center + eyelet_vector.normalized() * eyelet_torus_circle_radius / 2, eyelet_vector.normalized(), false);
            GameObject eyelet_low_circle_GO   = new GameObject("eyelet_low_circle");
            eyelet_low_circle_GO.transform.parent = eyelet_GO.transform;
            eyelet_low_circle_GO.AddComponent <MeshFilter>().mesh       = eyelet_low_circle_mesh;
            eyelet_low_circle_GO.AddComponent <MeshRenderer>().material = m_eyelet_circle_mat;
        }

        m_wheel_GO.transform.rotation = wheel_rotation;
        m_wheel_spoke_wrench_GO_updateTransformByCurrentSpoke();
    }