Exemple #1
0
    public void OnSceneGUI()
    {
        VolumeGrass _target = (VolumeGrass)target;

        int          i;
        EditorWindow currentWindow = EditorWindow.mouseOverWindow;

        if (currentWindow)
        {
            //Rect winRect = currentWindow.position;
            Event current = Event.current;

            switch (current.type)
            {
            case EventType.keyDown:
                if (current.keyCode == KeyCode.M)
                {
                    _target.paint_height = !_target.paint_height;
                    EditorUtility.SetDirty(_target);
                }
                break;
            }

            if (_target.state == 1)
            {
                if (_target.paint_height)
                {
                    if (current.alt)
                    {
                        return;
                    }
                    if (current.control)
                    {
                        if (current.type == EventType.mouseMove)
                        {
                            if (control_down_flag)
                            {
                                control_down_flag = false;
                                EditorUtility.SetDirty(_target);
                            }
                        }
                        return;
                    }
                    control_down_flag = true;
                    switch (current.type)
                    {
                    case EventType.mouseDown:
                        get_paint_coverage();
                        cover_verts_num_start_drag = cover_verts_num;
                        if (cover_verts_num > 0)
                        {
                            Undo.RegisterSceneUndo("grass edit (height)");
                            _target.modify_height(cover_verts_num, cover_indices, cover_strength, current.shift);
                            current.Use();
                        }
                        else
                        {
                            _target.undo_flag = true;
                        }
                        break;

                    case EventType.mouseDrag:
                        get_paint_coverage();
                        if (cover_verts_num > 0)
                        {
                            if (_target.undo_flag)
                            {
                                Undo.RegisterSceneUndo("grass edit (height)");
                                _target.undo_flag = false;
                            }
                        }
                        if (cover_verts_num_start_drag > 0)
                        {
                            _target.modify_height(cover_verts_num, cover_indices, cover_strength, current.shift);
                            current.Use();
                        }
                        break;

                    case EventType.mouseMove:
                        get_paint_coverage();
                        break;
                    }

                    if (current.shift)
                    {
                        for (i = 0; i < cover_verts_num; i++)
                        {
                            Handles.color = new Color(0, 1, 0, cover_strength[i]);
                            //Handles.ArrowCap(0, cover_verts[i], cover_norms[i], 5*cover_strength[i]);
                            Handles.DrawSolidDisc(cover_verts[i], Camera.current.transform.position - cover_verts[i], HandleUtility.GetHandleSize(cover_verts[i]) * 0.03f);
                        }
                    }
                    else
                    {
                        Handles.color = Color.red;
                        for (i = 0; i < cover_verts_num; i++)
                        {
                            Handles.color = new Color(1, 0, 0, cover_strength[i]);
                            //Handles.ArrowCap(0, cover_verts[i], cover_norms_flip[i], 5*cover_strength[i]);
                            Handles.DrawSolidDisc(cover_verts[i], Camera.current.transform.position - cover_verts[i], HandleUtility.GetHandleSize(cover_verts[i]) * 0.03f);
                        }
                    }

                    return;
                }
            }

            switch (current.type)
            {
            case EventType.keyDown:
                if (current.keyCode == KeyCode.Delete)
                {
                    if ((_target.state == 0) || (_target.which_active == 3))
                    {
                        if (_target.active_idx >= 0)
                        {
                            Undo.RegisterUndo(new Object[2] {
                                _target, _target.transform
                            }, "grass edit");
                            _target.DeleteActiveControlPoint();
                            current.Use();
                        }
                    }
                    else
                    {
                        if (_target.active_idx >= 0)
                        {
                            current.Use();
                            if (_target.which_active == 0)
                            {
                                EditorUtility.DisplayDialog("Info", "Deleting nodes in Edit mode only   ", "Proceed", "");
                            }
                        }
                    }
                }
                else if (current.keyCode == KeyCode.Return)
                {
                    if (_target.state == 1)
                    {
                        // rebuild
                        current.Use();
                        if (!_target.BuildMesh())
                        {
                            EditorUtility.DisplayDialog("Error...", "Can't build mesh   ", "Proceed", "");
                        }
                    }
                }
                break;

            case EventType.keyUp:
//					current.Use();
                break;

            case EventType.mouseDown:
                //Debug.Log(current +"     "+controlID);
                float dist;
                float min_dist;

                _target.active_idx   = -1;
                _target.which_active = 0;
                // pressing control points
                min_dist = 12f;                       // promień kliku w obrębie którego "łapiemy" pkt kontrolny
                for (i = 0; i < _target.control_points.Count; i++)
                {
                    dist = Vector2.Distance(current.mousePosition, HandleUtility.WorldToGUIPoint(T_lw(_target.control_points[i])));
                    if (dist < min_dist)
                    {
                        min_dist           = dist;
                        _target.active_idx = i;
                    }
                }
                if (_target.state == 0)                         // zaznaczanie pktów beziera tylko w trybie edycji (w rybie build i tak są niewidoczne)
                // pressing bezierA points
                {
                    min_dist = 5f;                           // kółko bezier handla jest mniejsze niż control point
                    for (i = 0; i < _target.control_points.Count; i++)
                    {
                        // pkt beziera traktujemy jako "aktywny" jeśli jest choć trochę oddalony od control_pointa
                        if (Vector2.Distance(HandleUtility.WorldToGUIPoint(T_lw(_target.control_points[i])), HandleUtility.WorldToGUIPoint(T_lw(_target.bezier_pointsA[i]))) > 0.01f)
                        {
                            dist = Vector2.Distance(current.mousePosition, HandleUtility.WorldToGUIPoint(T_lw(_target.bezier_pointsA[i])));
                            if (dist < min_dist)
                            {
                                min_dist             = dist;
                                _target.which_active = 1;
                                _target.active_idx   = i;
                            }
                        }
                    }
                    // pressing bezierB points
                    min_dist = 5f;                           // kółko bezier handla jest mniejsze niż control point
                    for (i = 0; i < _target.control_points.Count; i++)
                    {
                        // pkt beziera traktujemy jako "aktywny" jeśli jest choć trochę oddalony od control_pointa
                        if (Vector2.Distance(HandleUtility.WorldToGUIPoint(T_lw(_target.control_points[i])), HandleUtility.WorldToGUIPoint(T_lw(_target.bezier_pointsB[i]))) > 0.01f)
                        {
                            dist = Vector2.Distance(current.mousePosition, HandleUtility.WorldToGUIPoint(T_lw(_target.bezier_pointsB[i])));
                            if (dist < min_dist)
                            {
                                min_dist             = dist;
                                _target.which_active = 2;
                                _target.active_idx   = i;
                            }
                        }
                    }
                }
                // pressing tesselation points
                if ((_target.state == 0) || (_target.show_tesselation_points))
                {
                    min_dist = 8f;                           // kółko tesselation handla jest mniejsze niż control point
                    for (i = 0; i < _target.tesselation_points.Count; i++)
                    {
                        dist = Vector2.Distance(current.mousePosition, HandleUtility.WorldToGUIPoint(T_lw(_target.tesselation_points[i])));
                        if (dist < min_dist)
                        {
                            min_dist             = dist;
                            _target.which_active = 3;
                            _target.active_idx   = i;
                        }
                    }
                }
                if ((_target.state == 0) && current.shift && (!current.alt) && (_target.active_idx == -1) && (_target.which_active == 0))
                {
                    // dodawanie pktów kontrolnych
                    Vector3 insert_pos = new Vector3(0, 0, 0);
                    int     insert_idx = -1;
                    _target.GetInsertPos(current.mousePosition, ref insert_pos, ref insert_idx);
                    if (insert_idx < 0)
                    {
                        // add point
                        Undo.RegisterUndo(new Object[2] {
                            _target, _target.transform
                        }, "grass edit");
                        _target.AddControlPoint(GetWorldPointFromMouse(_target.ground_layerMask), -1);
                    }
                    else
                    {
                        // insert point
                        Undo.RegisterUndo(new Object[2] {
                            _target, _target.transform
                        }, "grass edit");
                        _target.AddControlPoint(insert_pos, insert_idx);
                    }
                    current.Use();
                }
                else if (current.shift && current.alt && (_target.active_idx == -1) && (_target.which_active == 0) && ((_target.state == 0) || (_target.show_tesselation_points)))
                {
                    // dodawanie pktów tesselacji
                    Undo.RegisterUndo(new Object[2] {
                        _target, _target.transform
                    }, "grass edit");
                    _target.AddTesselationPoint(GetWorldPointFromMouse(_target.ground_layerMask));
                    current.Use();
                }
                else if ((_target.state == 0) && (_target.active_idx >= 0) && (_target.which_active == 0) && (current.alt))
                {
                    // dodawanie pktów beziera
                    if (Vector2.Distance(HandleUtility.WorldToGUIPoint(T_lw(_target.control_points[_target.active_idx])), HandleUtility.WorldToGUIPoint(T_lw(_target.bezier_pointsA[_target.active_idx]))) < 0.01f)
                    {
                        // wstawienie bezier_pointA
                        //_target.which_active=1;
                        Vector3 dir_vec = _target.control_points[(_target.active_idx + 1) % _target.control_points.Count] - _target.control_points[_target.active_idx];
                        dir_vec += 1.5f * (_target.control_points[(_target.active_idx + _target.control_points.Count - 1) % _target.control_points.Count] - _target.control_points[_target.active_idx]);
                        if (dir_vec.magnitude < 0.01f)
                        {
                            dir_vec = Vector3.right;
                        }
                        else if (dir_vec.magnitude > 5)
                        {
                            dir_vec.Normalize();
                            dir_vec *= 5;
                        }
                        _target.bezier_pointsA[_target.active_idx] -= dir_vec;
                    }
                    else if (Vector2.Distance(HandleUtility.WorldToGUIPoint(T_lw(_target.control_points[_target.active_idx])), HandleUtility.WorldToGUIPoint(T_lw(_target.bezier_pointsB[_target.active_idx]))) < 0.01f)
                    {
                        // wstawienie bezier_pointB
                        //_target.which_active=2;
                        Vector3 dir_vec = _target.control_points[(_target.active_idx + _target.control_points.Count - 1) % _target.control_points.Count] - _target.control_points[_target.active_idx];
                        dir_vec += 1.5f * (_target.control_points[(_target.active_idx + 1) % _target.control_points.Count] - _target.control_points[_target.active_idx]);
                        if (dir_vec.magnitude < 0.01f)
                        {
                            dir_vec = Vector3.right;
                        }
                        else if (dir_vec.magnitude > 5)
                        {
                            dir_vec.Normalize();
                            dir_vec *= 5;
                        }
                        _target.bezier_pointsB[_target.active_idx] -= dir_vec;
                    }
                    //current.Use();
                }
//					if ((prev_target_active_idx!=_target.active_idx) || (prev_target_which_active!=_target.which_active)) {
//						Undo.RegisterUndo(new Object[2]{_target, _target.transform}, "grass edit");
//					}
                _target.undo_flag = false;
                //current.Use();
                break;

//				case EventType.mouseMove:
//				break;
            case EventType.mouseDrag:
                //current.Use();
                break;

            case EventType.mouseUp:
                //current.Use();
                break;

            case EventType.layout:
                // HandleUtility.AddDefaultControl(controlID);
                break;
            }
        }

        // Node Numbers
        if (_target.showNodeNumbers)
        {
            for (i = 0; i < _target.control_points.Count; i++)
            {
                Handles.Label(T_lw(_target.control_points[i]), "  " + i);
            }
        }

        // tesselation points labels
        if ((_target.state == 0) || (_target.show_tesselation_points))
        {
            for (i = 0; i < _target.tesselation_points.Count; i++)
            {
                Handles.Label(T_lw(_target.tesselation_points[i]), " tp");
            }
        }

        // control_points
        for (i = 0; i < _target.control_points.Count; i++)
        {
            Vector3 vec =
                Handles.FreeMoveHandle(T_lw(_target.control_points[i]),
                                       Quaternion.identity, HandleUtility.GetHandleSize(T_lw(_target.control_points[i])) * 0.08f, Vector3.one,
                                       Handles.RectangleCap);
            if ((_target.state == 0) && (Vector3.Distance(vec, T_lw(_target.control_points[i])) > 0))
            {
                if (!_target.undo_flag)
                {
                    Undo.RegisterUndo(new Object[2] {
                        _target, _target.transform
                    }, "grass edit");
                    _target.undo_flag = true;
                }
                Vector3 delta_bezierA = T_lw(_target.bezier_pointsA[i]) - T_lw(_target.control_points[i]);
                Vector3 delta_bezierB = T_lw(_target.bezier_pointsB[i]) - T_lw(_target.control_points[i]);
                if (_target.snap_on_move)
                {
                    _target.control_points[i] = T_wl(GetWorldPointFromMouse(_target.ground_layerMask));
                }
                else
                {
                    _target.control_points[i] = T_wl(vec);
                }
                _target.bezier_pointsA[i] = T_wl(T_lw(_target.control_points[i]) + delta_bezierA);
                _target.bezier_pointsB[i] = T_wl(T_lw(_target.control_points[i]) + delta_bezierB);
            }
        }
        Handles.color = Color.gray;
        // tesselation point handles
        if ((_target.state == 0) || (_target.show_tesselation_points))
        {
            for (i = 0; i < _target.tesselation_points.Count; i++)
            {
                Vector3 vec =
                    Handles.FreeMoveHandle(T_lw(_target.tesselation_points[i]),
                                           Quaternion.identity, HandleUtility.GetHandleSize(T_lw(_target.tesselation_points[i])) * 0.06f, Vector3.one,
                                           Handles.CircleCap);
                if (Vector3.Distance(vec, T_lw(_target.tesselation_points[i])) > 0)
                {
                    if (!_target.undo_flag)
                    {
                        Undo.RegisterUndo(new Object[2] {
                            _target, _target.transform
                        }, "grass edit");
                        _target.undo_flag = true;
                    }
                    if (_target.snap_on_move)
                    {
                        _target.tesselation_points[i] = T_wl(GetWorldPointFromMouse(_target.ground_layerMask));
                    }
                    else
                    {
                        _target.tesselation_points[i] = T_wl(vec);
                    }
                }
            }
        }
        // custom UV grid bounds handles
        if (_target.custom_UV_bounds)
        {
            Vector3 handle_pos, vec;
            // minx
            handle_pos = new Vector3(_target.custom_minx, _target.transform.position.y, 0.5f * (_target.custom_minz + _target.custom_maxz));
            vec        = Handles.FreeMoveHandle(handle_pos, Quaternion.identity, HandleUtility.GetHandleSize(handle_pos) * 0.04f, Vector3.one, Handles.DotCap);
            if (Mathf.Abs(vec.x - handle_pos.x) > 0)
            {
                if (!_target.undo_flag)
                {
                    Undo.RegisterUndo(_target, "grass edit");
                    _target.undo_flag = true;
                }
                if (vec.x > _target.minx)
                {
                    vec.x = _target.minx;
                }
                _target.custom_minx = vec.x;
            }
            // maxx
            handle_pos = new Vector3(_target.custom_maxx, _target.transform.position.y, 0.5f * (_target.custom_minz + _target.custom_maxz));
            vec        = Handles.FreeMoveHandle(handle_pos, Quaternion.identity, HandleUtility.GetHandleSize(handle_pos) * 0.04f, Vector3.one, Handles.DotCap);
            if (Mathf.Abs(vec.x - handle_pos.x) > 0)
            {
                if (!_target.undo_flag)
                {
                    Undo.RegisterUndo(_target, "grass edit");
                    _target.undo_flag = true;
                }
                if (vec.x < _target.maxx + 0.1f)
                {
                    vec.x = _target.maxx + 0.1f;
                }
                _target.custom_maxx = vec.x;
            }
            // minz
            handle_pos = new Vector3(0.5f * (_target.custom_minx + _target.custom_maxx), _target.transform.position.y, _target.custom_minz);
            vec        = Handles.FreeMoveHandle(handle_pos, Quaternion.identity, HandleUtility.GetHandleSize(handle_pos) * 0.04f, Vector3.one, Handles.DotCap);
            if (Mathf.Abs(vec.z - handle_pos.z) > 0)
            {
                if (!_target.undo_flag)
                {
                    Undo.RegisterUndo(_target, "grass edit");
                    _target.undo_flag = true;
                }
                if (vec.z > _target.minz)
                {
                    vec.z = _target.minz;
                }
                _target.custom_minz = vec.z;
            }
            // maxz
            handle_pos = new Vector3(0.5f * (_target.custom_minx + _target.custom_maxx), _target.transform.position.y, _target.custom_maxz);
            vec        = Handles.FreeMoveHandle(handle_pos, Quaternion.identity, HandleUtility.GetHandleSize(handle_pos) * 0.04f, Vector3.one, Handles.DotCap);
            if (Mathf.Abs(vec.z - handle_pos.z) > 0)
            {
                if (!_target.undo_flag)
                {
                    Undo.RegisterUndo(_target, "grass edit");
                    _target.undo_flag = true;
                }
                if (vec.z < _target.maxz + 0.1f)
                {
                    vec.z = _target.maxz + 0.1f;
                }
                _target.custom_maxz = vec.z;
            }
        }

        if (_target.state == 0)
        {
            if (_target.which_active != 3)
            {
                // bezier handle A
                for (i = 0; i < _target.control_points.Count; i++)
                {
                    if ((_target.active_idx == i) && ((_target.which_active == 1) || (Vector3.Distance(T_lw(_target.control_points[i]), T_lw(_target.bezier_pointsA[i])) > 0.01f)))
                    {
                        Vector3 vec =
                            Handles.FreeMoveHandle(T_lw(_target.bezier_pointsA[i]),
                                                   Quaternion.identity, HandleUtility.GetHandleSize(T_lw(_target.bezier_pointsA[i])) * 0.05f, Vector3.one,
                                                   Handles.CircleCap);
                        if (Vector3.Distance(vec, T_lw(_target.bezier_pointsA[i])) > 0)
                        {
                            if (!_target.undo_flag)
                            {
                                Undo.RegisterUndo(new Object[2] {
                                    _target, _target.transform
                                }, "grass edit");
                                _target.undo_flag = true;
                            }
                            if (_target.snap_on_move)
                            {
                                _target.bezier_pointsA[i] = T_wl(GetWorldPointFromMouse(_target.ground_layerMask));
                            }
                            else
                            {
                                _target.bezier_pointsA[i] = T_wl(vec);
                            }
                        }
                        Handles.DrawLine(T_lw(_target.control_points[i]), T_lw(_target.bezier_pointsA[i]));
                    }
                }
                // bezier handle B
                for (i = 0; i < _target.control_points.Count; i++)
                {
                    if ((_target.active_idx == i) && ((_target.which_active == 2) || (Vector3.Distance(T_lw(_target.control_points[i]), T_lw(_target.bezier_pointsB[i])) > 0.01f)))
                    {
                        Vector3 vec =
                            Handles.FreeMoveHandle(T_lw(_target.bezier_pointsB[i]),
                                                   Quaternion.identity, HandleUtility.GetHandleSize(T_lw(_target.bezier_pointsB[i])) * 0.05f, Vector3.one,
                                                   Handles.CircleCap);
                        if (Vector3.Distance(vec, T_lw(_target.bezier_pointsB[i])) > 0)
                        {
                            if (!_target.undo_flag)
                            {
                                Undo.RegisterUndo(new Object[2] {
                                    _target, _target.transform
                                }, "grass edit");
                                _target.undo_flag = true;
                            }
                            if (_target.snap_on_move)
                            {
                                _target.bezier_pointsB[i] = T_wl(GetWorldPointFromMouse(_target.ground_layerMask));
                            }
                            else
                            {
                                _target.bezier_pointsB[i] = T_wl(vec);
                            }
                        }
                        Handles.DrawLine(T_lw(_target.control_points[i]), T_lw(_target.bezier_pointsB[i]));
                    }
                }
            }
        }
    }