[猫儿的RMXP工具箱第七弹]自动绘制迷宫墙壁
有没有很眼馋RMVA、RMMV的“自动元件绘制迷宫”功能?有没有很苦手RMXP绘制迷宫没有自动元件的墙壁用?(XXX图块为什么没有自动元件屋顶?抓狂!!)
有没有很纠结大量的无意义体力活浪费在填涂迷宫墙壁上?
这一切都结束了!
有了这个工具脚本, 所有迷宫的绘制过程,将从
铺地板>>涂墙壁>>局部修改>>装饰
简化为
铺地板>>运行脚本>>局部修改>>装饰
脚本如下:
RUBY 代码
#==============================================================================
# ■ Auto_MazeWalls
#------------------------------------------------------------------------------
# 自动生成迷宫的墙壁,默认支持的迷宫种类有:
# 农村内部(24)、教会内部(29)、城寨内部(38)、塔内部(40)、魔物城堡内部
# (42)、土之洞窟(43)、炎之洞窟(44)、冰之洞窟(45)、水之洞窟(46)、矿山
# (47)、体内(49),也就是不能用自动元件画墙壁的所有图块。
# 使用方法:
# 绘制一张只有一层(F5)层的地图,并只绘制地面的部分(即人可以走到的部分),
# 其他位置全部留空——注意是留空,不要用别的东西填充了
# 插入本脚本到Game_Temp(注意不是Main)之前,然后在末尾添加
#
# $auto_fill = Auto_MazeWalls.new(地图编号)
# $auto_fill = fill_wall(墙壁高度)
# $auto_fill.save
# exit
#
# 运行完毕后请重新打开工程或相关地图。
# 注释掉本脚本末尾的四行可以屏蔽该功能正常测试游戏。
# 注:
# 1) 地图编号不存在的话,脚本将无效直接关闭
# 2) 部分图块锁定了墙高(24、29、38),墙壁高度填写任何值都是无效的
# 3) 墙壁高度如填写为负数,则会生成悬空式迷宫,但前提是图块支持这种迷宫
# 4) 如果有多张地图需要生成墙壁,请分别执行
# 5) 如果地形有冲突(如墙高度不够),图块会重叠或空白,请手工修改冲突的地方
#==============================================================================
class Auto_MazeWalls
#--------------------------------------------------------------------------
# ● 初始化对像
#--------------------------------------------------------------------------
def initialize(map_id)
@filename = sprintf("Data/Map%03d.rxdata", map_id)
ifFileTest.exist?(@filename)
@map = load_data(@filename)
@width = @map.width
@height = @map.height
setup(@map.tileset_id)
else
exit
end
end
#--------------------------------------------------------------------------
# ● 保存地图
#--------------------------------------------------------------------------
def save
save_data(@map, @filename)
end
#--------------------------------------------------------------------------
# ● 根据图块ID获得填涂ID表
#--------------------------------------------------------------------------
def setup(tileset_id)
case tileset_id
when24# 农村 内部
@force_height = 2
@floor = 384
@dark = 396
@covers =
@walls_low = [-419, 420, -421]
@walls_med =
@walls_top =
@line_l = 395
@line_r = 397
@corner_lu = 390
@corner_ru = 391
@corner_lb = 398
@corner_rb = 399
@d_corner1 = 0
@d_corner2 = 0
@allow_deep = false
@shades = {384 => 385, 404 => 404, 412 => 401, 420 => 409}
when29# 教会 内部
@force_height = 3
@floor = 384
@dark = 409
@covers =
@walls_low =
@walls_med =
@walls_rim =
@walls_top =
@line_l = 408
@line_r = 410
@corner_lu = 403
@corner_ru = 404
@corner_lb = 411
@corner_rb = 412
@d_corner1 = 0
@d_corner2 = 0
@allow_deep = false
@shades = {384 => 385, 417 => 417, 425 => 427, 433 => 435, 441 => 443}
when38# 城寨 内部
@force_height = 2
@floor = 384
@dark = 409
@covers =
@walls_low = [-432, 433, -434]
@walls_med =
@walls_top =
@line_l = 408
@line_r = 410
@corner_lu = 403
@corner_ru = 404
@corner_lb = 411
@corner_rb = 412
@d_corner1 = 0
@d_corner2 = 0
@allow_deep = false
@shades = {384 => 386, 417 => 417, 425 => 419, 433 => 427}
when40# 塔 内部
@force_height = 0
@floor = 384
@dark = 409
@covers =
@walls_low =
@walls_med =
@walls_top =
@line_l = 408
@line_r = 410
@corner_lu = 403
@corner_ru = 404
@corner_lb = 411
@corner_rb = 412
@d_corner1 = 0
@d_corner2 = 0
@allow_deep = false
@shades = {384 => 385, 417 => 417, 425 => 427, 433 => 435}
when42# 魔物城堡 内部
@force_height = 0
@floor = 384
@dark = 409
@covers =
@walls_low =
@walls_med =
@walls_top =
@line_l = 408
@line_r = 410
@corner_lu = 403
@corner_ru = 404
@corner_lb = 411
@corner_rb = 412
@d_corner1 = 0
@d_corner2 = 0
@allow_deep = true
@depths =
@void = 393
@flat_top =
@flat_l = 413
@flat_r = 415
@flat_bottom =
@d_flat1 = 0
@d_flat2 = 0
@flat_lu = 419
@flat_ru = 420
@flat_lb = 427
@flat_rb = 428
@shades = {384 => 385, 417 => 440, 425 => 448, 433 => 456}
when43..46# 属性洞穴
@force_height = 0
@floor = 384
@dark = 425
@covers =
@walls_low =
@walls_med =
@walls_top =
@line_l = 424
@line_r = 426
@corner_lu = 419
@corner_ru = 420
@corner_lb = 427
@corner_rb = 428
@d_corner1 = 435
@d_corner2 = 436
@allow_deep = true
@depths = [488, 489, 490, 496, 497, 498, 504, 505, 506,
512, 513, 514, 520, 521, 522, 528, 529, 530]
@void = 425
@flat_top =
@flat_l = 429
@flat_r = 431
@flat_bottom =
@d_flat1 = 443
@d_flat2 = 444
@flat_lu = 451
@flat_ru = 452
@flat_lb = 459
@flat_rb = 460
@shades = {384 => 96, 433 => 445, 441 => 453, 449 => 461}
when47# 矿山
@force_height = 0
@floor = 384
@dark = 409
@covers =
@walls_low = [-432, -433, -434]
@walls_med =
@walls_top =
@line_l = 408
@line_r = 410
@corner_lu = 403
@corner_ru = 404
@corner_lb = 411
@corner_rb = 412
@d_corner1 = 0
@d_corner2 = 0
@allow_deep = true
@depths = [429, 430, 431, 437, 438, 439, 445, 446, 447,
453, 454, 455, 461, 462, 463, 469, 470, 471]
@void = 409
@flat_top =
@flat_l = 413
@flat_r = 415
@flat_bottom =
@d_flat1 = 0
@d_flat2 = 0
@flat_lu = 419
@flat_ru = 420
@flat_lb = 427
@flat_rb = 428
@shades = {384 => 385, 417 => 464, 425 => 472, 433 => 480}
when49# 体内
@force_height = 0
@floor = 384
@dark = 433
@covers =
@walls_low = [-456, -457, -458]
@walls_med =
@walls_top =
@line_l = 432
@line_r = 434
@corner_lu = 435
@corner_ru = 436
@corner_lb = 443
@corner_rb = 444
@d_corner1 = 0
@d_corner2 = 0
@allow_deep = true
@depths =
@void = 433
@flat_top =
@flat_l = 437
@flat_r = 439
@flat_bottom =
@d_flat1 = 0
@d_flat2 = 0
@flat_lu = 451
@flat_ru = 452
@flat_lb = 459
@flat_rb = 460
@shades = {384 => 385, 441 => 464, 449 => 472, 457 => 480}
end
end
#--------------------------------------------------------------------------
# ● 填涂墙壁
# wall_height: 墙壁高度(负值为悬空式,可能会被图块锁定)
#--------------------------------------------------------------------------
def fill_wall(wall_height = 2)
# 检查深渊地形
if wall_height < 0
if@allow_deep
fill_depth
return
else# 图块没有深渊地形的情况下,按2格默认高度填涂墙壁
wall_height = .max
end
end
# 强制墙高生效
wall_height = @force_heightif@force_height != 0
# 勾勒地板边缘
tile_data = Table.new(@width, @height)
for i in0...@width
for j in0...@height
tile_data = get_border_tile(i, j)
end
end
# 填涂地板边缘和F5层(背板遮挡填在F6层)
for i in0...@width
for j in0...@height
unless@covers.include?(tile_data)
if tile_data > 0
@map.data = tile_data
else
@map.data = @floor
@map.data = -tile_data
end
else
@map.data = tile_dataif j > 0
case tile_data
when@covers
if j < @height - 1and tile_data == @dark
@map.data = @corner_lu
else
@map.data = @line_l
end
when@covers
@map.data = @dark
when@covers
if j < @height - 1and tile_data == @dark
@map.data = @corner_ru
else
@map.data = @line_r
end
end
end
end
end
# 墙高及纵向墙线的增长
wall_data = {}
for i in0...@width
for j in0...@height
index = @walls_low.index(@map.data)
index = @walls_low.index(-@map.data)if index == nil
if index != nil
# 不是固定墙高3的情况下
unless@force_height == 3
(wall_height - 1).timesdo |n|
wall_data[] = @walls_medif j > n
end
else
wall_data[] = @walls_medif j > 0
wall_data[] = @walls_rimif j > 1
end
wall_data[] = @walls_topif j >= wall_height
elsif@map.data == @line_land@map.data == @dark
(wall_height - 1).timesdo |n|
wall_data[] = @line_lif j > n
end
# 交角处理
if j >= wall_height
if@map.data == @corner_ru
wall_data[] = @d_corner2
else
wall_data[] = @corner_lb
end
end
elsif@map.data == @line_rand@map.data == @dark
(wall_height - 1).timesdo |n|
wall_data[] = @line_rif j > n
end
# 交角处理
if j >= wall_height
if@map.data == @corner_lu
wall_data[] = @d_corner1
else
wall_data[] = @corner_rb
end
end
end
end
end
# 填涂墙壁
wall_data.eachdo |k, v|
@map.data, k, 0] = v
end
# 末行处理
for i in0...@width
if@map.data == @floor
@map.data = @covers
end
end
# 阴影处理
@width.timesdo |n|
i = @width - n
for j in0...@height
# 地板的阴影
if@map.data == @floor
unless@map.data == @flooror
@map.data == @flooror
(@map.data == @floorand
@map.data != -@walls_low)
@map.data = @shades[@floor]
end
end
# 墙壁的阴影
if@map.data == @walls_top
if@map.data == @line_r
for k in0..wall_height
if j + k < @height
@map.data = @shades[@map.data]
if@map.data == -@walls_low
@map.data = @shades[@map.data]
end
end
end
end
end
end
end
end
#--------------------------------------------------------------------------
# ● 获得勾勒墙壁图块
# x: 地图的 x 坐标
# y: 地图的 y 坐标
#--------------------------------------------------------------------------
def get_border_tile(x, y)
s = @map.data
return s if s != 0
case neighbor_data(x, y)
when0, 2, 128
return@dark
when1, 3, 129, 131
return@covers
when16, 24, 48, 56
return@walls_low
when4, 6
return@corner_ru
when64, 192
return@corner_lu
when8, 12, 14
return@line_r
when32, 96, 224
return@line_l
when80, 88, 112, 120, 208, 216, 240, 248
return@walls_low
when20, 22, 28, 30, 52, 54, 60, 62
return@walls_low
when65, 67, 97, 99, 193, 195, 225, 227
return@covers
when5, 7, 13, 15, 133, 135, 141, 143
return@covers
else
return0
end
end
#--------------------------------------------------------------------------
# ● 填涂深渊
#--------------------------------------------------------------------------
def fill_depth
# 勾勒地板边缘
tile_data = Table.new(@width, @height)
for i in0...@width
for j in0...@height
tile_data = get_depth_tile(i, j)
end
end
# 填涂地板边缘和F5层(高台遮挡填在F6层)
for i in0...@width
for j in0...@height
unless@flat_top.include?(tile_data)
@map.data = tile_data
else
@map.data = tile_data
@map.data = @void
end
end
end
# 深渊的增长
for i in0...@width
for j in0...@height
index = @flat_bottom.index(@map.data)
if index != nil
for k in0...@depths.length / 3
breakif@map.data != @voidor j + k + 1 >= @height
@map.data = @depths
end
end
end
end
end
#--------------------------------------------------------------------------
# ● 获得勾勒深渊图块
# x: 地图的 x 坐标
# y: 地图的 y 坐标
#--------------------------------------------------------------------------
def get_depth_tile(x, y)
s = @map.data
return s if s != 0
case neighbor_data(x, y)
when0
return@void
when2
return@flat_bottom
when1, 3, 129, 131
return@flat_bottom
when128
return@flat_bottom
when8
return@flat_top
when16, 24, 48, 56
return@flat_top
when32
return@flat_top
when4, 6, 12, 14
return@flat_l
when64, 96, 192, 224
return@flat_r
when65, 67, 97, 99, 193, 195, 225, 227
return@flat_rb
when5, 7, 13, 15, 133, 135, 141, 143
return@flat_lb
when80, 88, 112, 120, 208, 216, 240, 248
return@flat_ru
when20, 22, 28, 30, 52, 54, 60, 62
return@flat_lu
else
return0
end
end
#--------------------------------------------------------------------------
# ● 获得图块的邻近值
# x: 地图的 x 坐标
# y: 地图的 y 坐标
#--------------------------------------------------------------------------
def neighbor_data(x, y)
neighbor =
neighbor = @map.dataif x > 0and y > 0
neighbor = @map.dataif x > 0
neighbor = @map.dataif x > 0and y < @height - 1
neighbor = @map.dataif y < @height - 1
neighbor = @map.dataif x < @width - 1and y < @height - 1
neighbor = @map.dataif x < @width - 1
neighbor = @map.dataif x < @width - 1and y > 0
neighbor = @map.dataif y > 0
neighbor.collect!{|n| n > 0 ? 1 : 0}
return neighbor.inject(0){|v, n| v = v * 2 + n}
end
end
# 以下为使用脚本,发布前请删除或注释
$auto_fill = Auto_MazeWalls.new(1)
$auto_fill.fill_wall
$auto_fill.save
exit
效果如下:
Before
After
After-2
范例工程:
本帖来自P1论坛作者yang1zhi,因Project1站服务器在国外有时候访问缓慢不方便作者交流学习,经联系P1站长fux2同意署名转载一起分享游戏制作经验,共同为国内独立游戏作者共同创造良好交流环境,原文地址:https://rpg.blue/forum.php?mod=viewthread&tid=388732若有侵权,发帖作者可联系底部站长QQ在线咨询功能删除,谢谢。
页:
[1]