Fixture:rayCast (日本語)

LÖVE 0.8.0 から使用可能
このメソッドは以前のバージョンでは非対応です。

取付具の形状に対する斜線計算および表面法線のベクトル、さらに斜線により線が当たった位置を返します。斜線が形状を外れている場合は nil を返します。

斜線は入力線の第一地点を出発して線のある第二地点へ移動します。第五引数は入力線の長さであり尺度変更係数として斜線が移動する最大距離です。

引数 childIndex は ChainShape といった親形状に対して、どの子が斜線計算されるか指定するために使用されます。ChainShapes において、索引 1 が鎖においての最初の角です。親形状の斜線計算では指定された子に対してのみ検査されるために、すべての親形状を調査したいのであれば、その子ら全てに対して反復する必要があります。

力積における世界位置は行ベクトルへ第三引数の返値を乗算して行の始点へ加算をすることで計算できます。

hitx, hity = x1 + (x2 - x1) * fraction, y1 + (y2 - y1) * fraction


O.png 0.8.0 において、この関数により返された通常ベクトルが love.physics.getMeter により規模変更されてしまう不具合があります。  


関数

概要

xn, yn, fraction = Fixture:rayCast( x1, y1, x2, y2, maxFraction, childIndex )

引数

number x1
入力線の始点として x 位置。
number y1
入力線の始点として y 位置。
number x2
入力線の終点として x 位置。
number y2
入力線の終点として y 位置。
number maxFraction
斜線の長さにおける引数。
number childIndex (1)
斜線計算が行われる子の索引。

返値

number xn
斜線が形状に当たった場所での角の通常ベクトルにおける x 要素。
number yn
斜線が形状に当たった場所での角の通常ベクトルにおける y 要素。
number fraction
線の長さを係数として公差が発生した入力線上の位置。

用例

二つの異なる箱に対して斜線計算します。

function love.load()
	-- ここで現在の規模に対する不具合を回避するために 1 を設定します。
	love.physics.setMeter(1)

	World = love.physics.newWorld()

	Box = {}
	Box.Body = love.physics.newBody(World, 400, 300, "dynamic")
	Box.Shape = love.physics.newRectangleShape(150, 150)
	Box.Fixture = love.physics.newFixture(Box.Body, Box.Shape)

	-- 箱を優しく回転させます。
	Box.Body:setAngularVelocity(0.5)

	Ray1 = {
		point1 = {},
		point2 = {},
	}
	Ray1.point1.x, Ray1.point1.y = 50, 50
	Ray1.point2.x, Ray1.point2.y = 400, 300
	Ray1.scale = 1

	Ray2 = {
		point1 = {},
		point2 = {},
	}
	Ray2.point1.x, Ray2.point1.y = 500, 400
	Ray2.point2.x, Ray2.point2.y = Ray2.point1.x + math.cos(math.pi*1.45), Ray2.point1.y + math.sin(math.pi*1.45)
	Ray2.scale = 150
end

function love.update(dt)
	World:update(dt)
end

function love.draw()
	-- 箱を描画します。
	love.graphics.setColor(255, 255, 255)
	love.graphics.polygon("line", Box.Body:getWorldPoints( Box.Shape:getPoints() ))

	-- 斜線の入力線および到達する灰色の斜線 2 を描画します。
	love.graphics.setLineWidth(3)
	love.graphics.setColor(50, 50, 50)
	love.graphics.line(Ray2.point1.x, Ray2.point1.y, Ray2.point1.x + (Ray2.point2.x - Ray2.point1.x) * Ray2.scale, Ray2.point1.y + (Ray2.point2.y - Ray2.point1.y) * Ray2.scale)
	love.graphics.setColor(255, 255, 255)
	love.graphics.line(Ray1.point1.x, Ray1.point1.y, Ray1.point2.x, Ray1.point2.y)
	love.graphics.line(Ray2.point1.x, Ray2.point1.y, Ray2.point2.x, Ray2.point2.y)
	love.graphics.setLineWidth(1)

	-- 何にも当たらない場合は斜線計算で nil が返されることを覚えておいてください。
	local r1nx, r1ny, r1f = Box.Fixture:rayCast(Ray1.point1.x, Ray1.point1.y, Ray1.point2.x, Ray1.point2.y, Ray1.scale)
	local r2nx, r2ny, r2f = Box.Fixture:rayCast(Ray2.point1.x, Ray2.point1.y, Ray2.point2.x, Ray2.point2.y, Ray2.scale)

	if r1nx then
		-- 世界において斜線が当たった位置の計算。
		local r1HitX = Ray1.point1.x + (Ray1.point2.x - Ray1.point1.x) * r1f
		local r1HitY = Ray1.point1.y + (Ray1.point2.y - Ray1.point1.y) * r1f

		-- 形状の始点から位置へ射線を描画します。
		love.graphics.setColor(255, 0, 0)
		love.graphics.line(Ray1.point1.x, Ray1.point1.y, r1HitX, r1HitY)

		-- 斜線が当たった角の表面法線についても取得します。ここでは緑色で描画されます。
		love.graphics.setColor(0, 255, 0)
		love.graphics.line(r1HitX, r1HitY, r1HitX + r1nx * 25, r1HitY + r1ny * 25)
	end

	if r2nx then
		-- 世界において射線が当たった位置の計算。
		local r2HitX = Ray2.point1.x + (Ray2.point2.x - Ray2.point1.x) * r2f
		local r2HitY = Ray2.point1.y + (Ray2.point2.y - Ray2.point1.y) * r2f

		-- 形状の始点から位置へ射線を描画します。
		love.graphics.setColor(255, 0, 0)
		love.graphics.line(Ray2.point1.x, Ray2.point1.y, r2HitX, r2HitY)

		-- 斜線が当たった角の表面法線についても取得します。ここでは緑色で描画されます。
		love.graphics.setColor(0, 255, 0)
		love.graphics.line(r2HitX, r2HitY, r2HitX + r2nx * 25, r2HitY + r2ny * 25)
	end
end
この用例の画面撮影。

関連


そのほかの言語