Ejemplo n.º 1
0
        /// <summary>
        /// Shift given shiftedBlock behind target, if possible
        /// </summary>
        /// <param name="shiftedBlock"></param>
        /// <param name="target"></param>
        /// <param name="view"></param>
        private bool shiftBehind(ExecutedBlock shiftedBlock, ExecutedBlock target, ExecutionView view)
        {
            //cumulative list of blocks that has to be shifted
            //It has reverse ordering of transformations that will be generated
            var shiftedBlocks = new List <ExecutedBlock>();

            shiftedBlocks.Add(shiftedBlock);

            var borderInstances = new HashSet <Instance>();

            borderInstances.UnionWith(view.AffectedInstances(shiftedBlock));

            //find all colliding blocks, so we can move them with shifted block if possible
            var currentBlock = shiftedBlock;

            while (currentBlock != target)
            {
                currentBlock = view.NextBlock(currentBlock);

                if (!canCross(currentBlock, borderInstances, view))
                {
                    //this block cannot be crossed
                    borderInstances.UnionWith(view.AffectedInstances(currentBlock));
                    shiftedBlocks.Add(currentBlock);
                }
            }

            //shifting is not possible, due to collisions between blocks
            if (!canCross(target, borderInstances, view))
            {
                return(false);
            }

            shiftedBlocks.Reverse();
            foreach (var block in shiftedBlocks)
            {
                view.ShiftBehind(block, target);
            }

            return(true);
        }
Ejemplo n.º 2
0
        private bool canCross(ExecutedBlock shiftedBlock, HashSet <Instance> borderInstances, ExecutionView view)
        {
            foreach (var instance in view.AffectedInstances(shiftedBlock))
            {
                if (borderInstances.Contains(instance))
                {
                    //there is collision with border
                    return(false);
                }
            }

            return(true);
        }