`
wsliujian
  • 浏览: 95111 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

Flash中的深度排序

阅读更多
As for Multiplayer Games and Virtual Worlds

202
排序算法

……在世界里将对象放在正确的位置不是件难事,但是长期以来让开发者们发晕的是如何在以恶搞等角视觉里适当的将那些对象排序。“排序”这个词在这篇文章里的意思是指基于对象的3D位置将它们分在不同的图层。

图例中灌木应该在树的前面显示,而树则应显示在灌木后面(基于他们的坐标)。
在google上转了一圈,我没有发现太多在如何适当地处理等角视野的排序方面有价值的信息,却在论坛上发现一堆开发者寻找答案的帖子。我自创了一个解决排序难题的解决方案,并且依照它弄了个范例。

逻辑

我们实现排序算法取决于我们能分析所有对象的位置、所在的列数和行数,并且像我们现实生活中看到的一样去适当地排序,在这里,必须做两个假定:
所有的物件都被放在一个由砖块拼凑成的长方体里。它可以是单个方块那么小(1×1),也可以是类似餐桌的形状(比如2×4),我们不允许有其他形状的物件,比如L型的沙发——那样的对象需要被打散成两个长方体对象。
对象不能相互重叠,就像真实世界里你不能将一个沙发和一个餐桌放到同一个物理空间,这里我们也不允许那么做。
现在介绍算法如何工作。一开始,我们需要一个包括所有对象的原始列表。再创建一个空的列表用来存放排序之后的对象。我们将循环整个原始对象列表,并将其中的对象与已排列表中的对象比较,当比较结果显示当前的对象(来自原始列表中的)应该被排到某个已排对象的下面(也可说后面),那么在已排列表中它就会被插入到那个已排对象前面。这会持续到原始列表中的所有对象都被放到了已排列表中。如果一个物件没有被排到任何东西的后面,那么它会被放在已排列表的末端。最终,我们得到的结果就是一个已经将所有东西都排序妥当的列表。
问题的重点在这里:决定两个对象谁先谁后的比较是怎么做的?这才是使整个流程运转起来的关键。请观察下面几幅图并思考。



当我们在做比较,并假设如果Object B应该在Object A后面时,我们会问两个问题:
Object B的起始列是否小于等于Object A延伸到的最大列?
Object B的起始行是否小于等于Object A延伸到的最大行?
如果上述两者的答案均是YES,那么Object B应该排在Object A之后。你最好花些时间看着上面的图,并且尝试问自己这两个问题,以核实这个逻辑思路。

排序示例

此例中,我们会在屏幕上放满东西,并且将它们合理排序。下图就是我们这个例子没排序时的样子:
这是排序后的:

这个例子是利用以前章节中提到的网格示例建立起来的,而我们只需把注意力放在与今天主题有关的代码上。所有放在屏幕上的物件都会被放到一个叫做_itemHolder的影片剪辑里。在网格创建之后,这个影片剪辑会被intialize方法添加到舞台上:


_itemHolder = new MovieClip();
addChild(_itemHolder);

在intialize的底部加入以下代码:

for( var i:int = 0; i < 50; ++ i) {
var col:int = Math.floor(_cols * Math.random());
var row:int = Math.floor(_rows * Math.random());

var item:Item = new Item();
item.type = Math.floor(3 * Math.random());

if(testItemPlacement(item, col, row)) {
addItem(item, col, row);
}
}

SortAllItems();

这段代码用了50次迭代把物件放在任意位置。物件的行和列是随机的,同时物件的样式也是随机的。物件有三种样式,0,1或2。Item类根据type值来决定这个东西显示什么图片,并且占用多少行和列。接着是一个条件语句来检测预期的摆放位置,在摆放位置超出地图边界或者覆盖其他物件的情况下,都将是无效的。如果位置有效,那么我们用addItem方法将它加到屏幕上。随后调用SortAllItems方法。

这是addItem方法的具体代码:

private function addItem(itm:Item, col:int, row:int):void {
for(var i:int = col; i< col + itm.cols; ++i) {
for(var j:int = row; j < row + itm.rows; ++j) {
var tile:Tile = getTile(i,j);
if(tile != null) {
tile.addItem(itm);
}
}
}


var tx:Number = _tileWidth * col + _tileWidth/2;
var tz:Number = - (_tileHeight * row + _tileHeight/2);

var coord:Coordinate = iso.mapToScreen(tx, 0, tz);
itm.x = coord.x;
itm.y = coord.y;

itm.col = col;
itm.row = row;

_itemHolder.addChild(itm);

_sortedItems.push(itm);

}
这个方法做的第一件事是遍历所有物件将会放诸其上的砖块并将物件放置上去。因为之前提到的检测放置可行性的方法testItemPlacement是检测砖块是否包含物件,所以这里我们要把物件加到砖块里。之后,我们指定物件的3D坐标位置,这和指定砖块位置用的是相类似的技术,唯一的区别是,在放物件的情况下,在坐标的x和z方向上都会给一个增量,以便于物件能放在砖块中间。之后用mapToScreen方法确定屏幕上的投影位置。一个物件在确定了摆放的行列位置,并放入了_itemHolder之后,在它身上将要发生的最后一件事就是被放进_sortedItems数组中(虽然它仍没被排序)。

在继续下去之前,你要知道所有的Item实例都实现了ISortableItem接口。这很重要,因为你很可能会添加一些非物件的东西到屏幕上,但是它们需要遵循同样的排序逻辑,比如Avatar。一个avatar也可以实现这个接口,只要你希望它像其他东西一样的排序。ISortableItem接口的最小化子类需要实现以下方法:
function get col():int;
function get row():int;
function get cols():int;
function get rows():int;

现在来看SortAllItems方法:
private function sortAllItems():void {
var list:Array = _sortedItems.slice(0);

_sortedItems = [];

for(var i:int = 0; i < list.length; ++i) {
var nsi:IsortableItem = list[i];

var added:Boolean = false;
for(var j:int = 0; j < _sortedItems.length; ++j) {
var si:IsortableItem = _sortedItems[j];

if(nsi.col <= si.col + si.cols - 1 && nsi.row <= si.row + si.rows - 1) {
_sortedItems.splice(j, 0, nsi);
added = true;
break;
}
}
if(!added) {
_sortedItems.push(nsi);
}
}

for(i = 0; i< _sortedItems.length; ++i) {
var disp:DisplayObject = _sortedItems[i] as DisplayObject;
_itemHolder.addChildAt(disp, i);
}

}

此方法中,我们依照早先给出的算法。首先创建一个称之为list的数组用来复制_sortedItems。之后,置空_sortedItems数组。然后遍历list里的每一项,命名为nsi,让它和_sortedItems里的每一项si比。每个nsi都有个added属性,如果排序后它不在任何东西后面,则为flase。随后的条件语句包含了两个比较nsi和si先后位置的条件,如果都满足,那么把nsi插到_sortedItems数组中si的前面,added属性置为true,并跳出内部循环。
最后的事就是将_sortedItems中刚排序完成的物件加到屏幕上相应的深度。你的排序事业就大功告成!

分享到:
评论

相关推荐

    精心整理史上最全的数据结构flash演示动画,共5个版本,祝大家考研成功!

    \数据结构flash演示\版本1\7-3-2图的深度优先搜索.swf \数据结构flash演示\版本1\7-3-3图的广度优先搜索.swf \数据结构flash演示\版本1\7-3-4图的广度优先搜索-树的层次遍历.swf \数据结构flash演示\版本1\7-4-1...

    原创数据结构Flash演示动画(46个算法演示)

    串的顺序存储、单链表结点的插入、单链表结点的删除、堆排序、二叉排序树的删除、二叉排序树的生成、二叉树的建立、二分查找、归并排序、基数排序、快速排序、邻接表表示的图的广度优先遍历、邻接表表示的图的深度...

    常见程序算法原理过程flash演示

    排序是计算机科学中最基本的问题之一,它涉及到将一组数据按照特定的顺序进行排列。这个资源可能包括了常见的排序算法,如冒泡排序、插入排序、选择排序、快速排序、归并排序和堆排序。每种排序算法都有其独特的思想...

    算法演示flash,很多算法题,都是有flash版的

    Flash动画可以演示各种排序算法的运作,如冒泡排序、插入排序、选择排序、快速排序、归并排序和堆排序等。这些动画会清晰地展示元素如何交换位置,帮助理解每种排序方法的时间复杂度和稳定性。 3. **图算法**:图论...

    flash/as3 3D 版 SNS社交游戏源码

    总结来说,这个"flash/as3 3D SNS社交游戏源码"是一个综合了3D图形、寻路算法、深度排序、光照效果以及社交功能的实例。对于想深入学习AS3游戏开发,尤其是3D社交游戏的开发者而言,这是一个宝贵的资源,可以从中...

    数据结构和算法的FLASH演示

    本资料集合提供了一系列的FLASH演示,生动地展示了这些核心概念。以下是对每个文件名称所对应的知识点的详细解释: 1. **构造哈夫曼树的算法模拟.swf**: 哈夫曼树,也称为最优二叉树,是一种带权路径长度最短的...

    所有数据结构flash演示动画

    通过“所有数据结构flash演示动画”,你可以动态观察这些数据结构的操作,加深理解,并掌握它们在实际问题中的应用。例如,你可以看到链表的插入和删除是如何进行的,栈和队列如何影响元素的进出,二叉搜索树如何...

    数据结构和算法Flash动画演示.rar

    常见的算法包括排序算法(如冒泡排序、选择排序、插入排序、快速排序、归并排序、堆排序)、查找算法(如线性查找、二分查找、哈希查找)、图算法(如深度优先搜索、广度优先搜索)和动态规划等。排序算法中,冒泡...

    经典算法Flash演示

    这个资源可能包含了一系列的Flash动画,每个动画都详细解释了一个特定的经典算法,如排序、查找、图论或动态规划等。以下是可能涵盖的一些重要算法及其核心概念: 1. **排序算法**:包括快速排序(Quick Sort)、...

    3D空间感的粒子旋转动态效果-Flash源文件.rar

    在Flash中,虽然它主要处理二维图形,但通过使用特定的编程技巧,如透视、深度排序和运动模糊,可以创造出3D的错觉。开发者可能利用ActionScript(Flash的编程语言)编写了粒子的位置、速度、旋转角度以及透明度等...

    数据结构算法Flash演示

    例如,排序算法(冒泡排序、选择排序、插入排序、快速排序、归并排序等)、查找算法(线性查找、二分查找)、图算法(深度优先搜索、广度优先搜索)和树算法(前序遍历、中序遍历、后序遍历)等。Flash演示会通过...

    数据结构和算法Flash动画演示

    动画可能演示了在非排序数组中进行顺序查找的过程和效率。 3. **归并排序.swf**:归并排序是一种分治算法,将大问题分解为小问题来解决。它将数组分为两半,分别排序,然后合并成一个有序数组。动画可能展示了...

    flash数据结构算法演示

    《Flash数据结构算法演示》是基于Flash技术制作的一系列SWF动画,旨在通过生动的动态效果展示各种数据结构和算法的运作过程。这些文件涵盖了多种基础且重要的算法,包括搜索、排序、树结构以及图的遍历等核心概念。...

    数据结构Flash演示动画.rar

    图遍历算法如深度优先搜索(DFS)和广度优先搜索(BFS)是图论中的基础内容。 7. **哈希表**:通过哈希函数将键映射到数组的特定位置,实现快速查找。哈希冲突的解决方法有开放寻址法和链地址法。 8. **堆**:一种...

    拓扑排序.zip

    在给定的压缩包文件“拓扑排序.zip”中,包含了名为“拓扑排序.swf”的文件,这很可能是演示拓扑排序过程的Flash动画或交互式教程。通过查看这个文件,用户可以更直观地理解拓扑排序的概念和步骤,加深对这一图论...

    数据结构flash算法演示

    - **遍历算法**:如深度优先搜索(DFS)和广度优先搜索(BFS),在树和图中遍历所有节点。 - **最短路径算法**:如Dijkstra算法和Floyd算法,用于寻找图中两点间的最短路径。 - **贪心算法**:通过局部最优解逐步...

    用Flash做的数据结构教程

    特别是二叉搜索树,其左子节点小于父节点,右子节点大于父节点,这样的特性在查找和排序中有着优异性能。 然后,图是由顶点和边组成的,用于表示对象之间的关系。在Flash动画中,可以生动地展示图的邻接矩阵或邻接...

    数据结构相关的算法FLASH演示

    文件列表中的“演示”可能包含一系列针对不同数据结构和算法的FLASH动画,如排序算法的比较过程、栈的压栈和弹栈操作、树的构建和遍历等。通过观看这些演示,学习者能够看到每个步骤的动态变化,加深对数据结构和...

    数据结构flash课件

    10. **查找算法**:如二分查找、广度优先搜索(BFS)、深度优先搜索(DFS)等,这些算法用于在数据结构中寻找目标元素。 这个“数据结构FLASH课件”利用动画的形式,将这些复杂的概念可视化,使得学习者能够更好地...

Global site tag (gtag.js) - Google Analytics