const float jointsDistance          = 0.25f; //distance between two standard joints in brick (scale 1)

        public override ProposedPosition GetPosition(Vector3 mousePosition, bool snapToGrid, float gridSize)
        {
            var simplePosition = base.GetPosition(mousePosition, false, gridSize);

            brick.transform.position = simplePosition.position;

            if (!(brick is AgaQBrick))
            {
                return(simplePosition);
            }

            //calculate distance betweeen two standard joints in screen space.
            var joint1Pos            = simplePosition.position + cam.transform.right * jointsDistance * brick.transform.localScale.x;
            var joint2Pos            = simplePosition.position - cam.transform.right * jointsDistance * brick.transform.localScale.x;
            var jointsScreenDistance = (cam.WorldToScreenPoint(joint1Pos) - cam.WorldToScreenPoint(joint2Pos)).magnitude * 0.5f;

            //transform our moving brick joints postions to screen space
            var brickJoints = ProjectionTool.ProjectJoints(brick as AgaQBrick);

            //get possible joints
            var gameObjectsBehind = GetOtherBricks(mousePosition);
            var possibleJoints    = GetClosetsJoins(brickJoints, gameObjectsBehind, jointsScreenDistance);

            //iterate over possible joints
            foreach (var possibleJoint in possibleJoints)
            {
                if (CheckJoint(possibleJoint, snapToGrid))
                {
                    return(new ProposedPosition(brick.transform, true, true));
                }
            }

            if (!snapToGrid)
            {
                return(simplePosition);
            }

            return(base.GetPosition(mousePosition, snapToGrid, gridSize));
        }
        /// <summary>
        /// Get joints from other brics that are close enouth to try join brick with.
        /// List is sorted by distance after projeting to the plane.
        /// </summary>
        /// <param name="projectedDragingBrickJoints"></param>
        /// <param name="positionTolerance">Position tolerance.</param>
        /// <returns>The closets joins.</returns>
        PossibleJoint[] GetClosetsJoins(ProjectedJoint[] projectedDragingBrickJoints, GameObject[] gameObjects, float positionTolerance)
        {
            List <PossibleJoint> possibleJoints = new List <PossibleJoint> ();

            //iterate over all colliders
            foreach (var otherGameObject in gameObjects)
            {
                //skip grid and itself
                if (otherGameObject.tag == "background" || otherGameObject == this.brick.gameObject)
                {
                    continue;
                }

                //check if collider is AgaQ brick
                var otherBrick = otherGameObject.GetComponent <AgaQBrick> ();
                if (otherBrick == null)
                {
                    //try to get AgaQScript from parent
                    otherBrick = otherGameObject.GetComponentInParent <AgaQBrick>();
                    if (otherBrick == null)
                    {
                        continue;
                    }
                }

                //iterate over all brick joints
                foreach (var otherBrickJoint in otherBrick.joints)
                {
                    if (otherBrickJoint.other == null)
                    {
                        foreach (var projectedDragingBrickJoint in projectedDragingBrickJoints)
                        {
                            var projectedJoint = ProjectionTool.ProjectJoint(otherBrickJoint);
                            if (projectedDragingBrickJoint.Compare(projectedJoint, positionTolerance))
                            {
                                possibleJoints.Add(new PossibleJoint(projectedDragingBrickJoint, projectedJoint));
                            }
                        }
                    }
                }
            }

            //draw possible joints in editor for debuging purpose
            #if UNITY_EDITOR
            foreach (var j in possibleJoints)
            {
                DebugExtension.DebugCircle(
                    j.projectedOtherJoint.joint.transform.position,
                    Color.red,
                    0.1f,
                    02.2f,
                    false
                    );
                //Debug.DrawLine(
                //    j.projectedBrickJoint.joint.transform.position,
                //    j.projectedOtherJoint.joint.transform.position,
                //    Color.red,
                //    0.2f,
                //    false
                //);
            }
            #endif

            //possibleJoints.OrderBy (x => x.cameraVectorDistance); // order joints by distance to camera
            //possibleJoints.OrderBy (x => x.projectedDistance); // order joints by distance after project

            //sort by brick to camera distance than by projected distance
            possibleJoints.Sort((x, y) => {
                if (x.projectedOtherJoint.joint.parentBrick != y.projectedOtherJoint.joint.parentBrick)
                {
                    return(x.cameraVectorDistance.CompareTo(y.cameraVectorDistance));
                }
                return(x.projectedDistance.CompareTo(y.projectedDistance));
            });



            return(possibleJoints.ToArray());
        }