Jump to content

Hybrid fpscontroller.lua


Canardia
 Share

Recommended Posts

You can use this fpscontroller2.lua from Editor or by dragging it over Engine.exe.

--stuff which should be part of LE

--the best working round function, works also for negative idp (written by Robert Jay Gould)
function round(num, idp)
return tonumber(string.format("%." .. (idp or 0) .. "f", num))
end

BLEND_NONE=0
BLEND_ALPHA=1

--end of stuff which should be part of LE

if fw==nil then --we are not in Editor
RegisterAbstractPath("")
Graphics(800,600)
fw=CreateFramework()
scene=LoadScene("abstract::tunnels.sbx")
scene:SetCollisionType(COLLISION_SCENE)
TFilter(1)
AFilter(4)
standalone=1
end

require("Scripts/constants/collision_const")
require("Scripts/constants/engine_const")
require("Scripts/LinkedList")
require("Scripts/filesystem")
require("Scripts/math/math")
require("scripts/classes/bullet")

--Variables
dx=0.0
dy=0.0
camerapitch=0.0
camerayaw=0.0
move=0.0
strafe=0.0

--Create a player controller
controller=CreateController(1.8,0.45,0.25,45)
controller:SetCollisionType(COLLISION_CHARACTER,0)
controller:SetMass(10)
if standalone==1 then
controller:SetPosition(Vec3(38.8,5.7,7))
else
controller:SetPosition(fw.main.camera.position)
end
camerapitch=fw.main.camera.rotation.x
camerayaw=fw.main.camera.rotation.y+180

local gunscale=0.6
local vwep = LoadMesh("abstract::vwep_hands.gmf")
LoadMesh("abstract::vwep_gun.gmf",vwep)
vwep:SetParent(fw.main.camera,0)
vwep:SetPosition(Vec3(-0.18*gunscale,-0.03*gunscale,0.37*gunscale),0)
vwep:SetScale(Vec3(0.04*gunscale,0.04*gunscale,0.04*gunscale))
local gundisplayposition = vwep:GetPosition()
sound_gunshot = LoadSound("abstract::gunshot.ogg")
source_gunshot = CreateSource(sound_gunshot)
source_gunshot:SetVolume(0.5)
vwep :SetShadowMode(0,1)
local displayposition=Vec3(-0.26/2.0,-0.03,0.19)
local muzzleflash = CreatePointLight(3)
muzzleflash:SetParent( vwep )
muzzleflash:SetColor(Vec4(1,0.6,0.0,1.0))
muzzleflash:SetPosition( displayposition )
muzzleflash:SetShadowMode(0)

HideMouse()
MoveMouse(GraphicsWidth()/2,GraphicsHeight()/2)
FlushKeys()
FlushMouse()

local pick
local camera = fw.main.camera
local remainingtime
local starttime=AppTime()
local gameduration=2--length of game in minutes
local gamemode=0

gunpos = vwep.position:Copy()

local smoothedgunswayamplitude=0.0
local smoothedgunswayspeed	=0.0
local guntime = 0.0
local recoil = 0.0
local lastfiretime=0.0
local smoothrecoil=0.0
local swaydamping=0.0
local smoothswaydamping=0.0
local lightsmoothing =0.0
local gunlight = 0.0

--Flashlight
flashlight = {}
flashlight.light = CreateSpotLight(8)
flashlight.light:Hide()
flashlight.sound_switch = LoadSound("abstract::switch.wav")
flashlight.state=0
flashlight.light:SetConeAngles(30,35)
flashlight.light:SetRotation(Vec3(5,0,0))
flashlight.light:SetShadowmapSize(512)
flashlight.light:Paint(LoadMaterial("abstract::flashlight.mat"))

function flashlight:SetState( state )
if state~=self.state then
	self.state=state
	if state==0 then
		self.light:Hide()
	else
		self.light:Show()
	end
	if self.sound_switch~=nil then
		self.sound_switch:Play()
	end
end
end


function ShootBullet( position, direction )
--	local speed=100.0
--	local pick = LinePick( position, Vec3(position.x+direction.x * speed) )
end


function DrawHUD(contr)
SetBlend(BLEND_ALPHA)
DrawText("pos: "..round(contr.position.x,3)..","..round(contr.position.y,3)..","..round(contr.position.z,3),1,FontHeight()*5)
DrawText("rot: "..round(contr.rotation.x,3)..","..round(contr.rotation.y,3)..","..round(contr.rotation.z,3),1,FontHeight()*6)
SetBlend(BLEND_NONE)
end


--main function
while KeyHit(KEY_ESCAPE)==0 do
jump=KeyHit(KEY_SPACE)*6.0
if controller:IsAirborne()==1 then jump=0 end


local time = AppTime()/3200.0
local frame = time*(179.0-96.0)+96.0
frame=Clamp( frame, 96, 179 )
vwep:Animate(96,1,0,1)


--Camera look
gx=Round(GraphicsWidth()/2)
gy=Round(GraphicsHeight()/2)
dx=Curve((MouseX()-gx)/4.0,dx,3.0/AppSpeed())
dy=Curve((MouseY()-gy)/4.0,dy,3.0/AppSpeed())
MoveMouse(gx,gy)
camerapitch=camerapitch+dy
camerayaw=camerayaw-dx
camerapitch=math.min(camerapitch,90)
camerapitch=math.max(camerapitch,-90)
fw.main.camera:SetRotationf(camerapitch,camerayaw,0,1)

movespeed=6
movesmoothing=10
if controller:IsAirborne()==1 then
	movesmoothing=200
end

--Player movement
move=Curve( (KeyDown(KEY_W)-KeyDown(KEY_S))*movespeed,move,movesmoothing)
strafe=Curve( (KeyDown(KEY_D)-KeyDown(KEY_A))*movespeed,strafe,movesmoothing)

--Use objects
if KeyHit(KEY_E)==1 then
	pick=CameraPick(camera,Vec3(GraphicsWidth()/2,GraphicsHeight()/2,2.0),0,0)
	if pick~=nil then
		repeat
			if pick.entity:GetClass()==ENTITY_MODEL then
				break
			end
			pick.entity=pick.entity.parent
		until pick.entity==nil
		if pick.entity~=nil then
			pick.entity:SendMessage("use",controller,0)
		end
	end
end

--Update controller
controller:Update(camerayaw,move,strafe,jump,40,10)

fw:Update()

if KeyHit(KEY_F)==1 then
	flashlight:SetState(1-flashlight.state)
end

--Position camera
camera:SetPositionf(controller.position.x,controller.position.y+0.8,controller.position.z,1)

time=AppTime()
gunfirefrequency=80
gunswayspeed=0.001*20.0
gunoffset = gunpos:Copy()
gunswayamplitude = 0.02
if KeyDown(KEY_W)==1 or KeyDown(KEY_D)==1 or KeyDown(KEY_A)==1 or KeyDown(KEY_S)==1 then
	gunswayamplitude = 0.03
	gunswayspeed=0.005*20.0
end
smoothedgunswayamplitude = Curve( gunswayamplitude, smoothedgunswayamplitude,8.0  )
smoothedgunswayspeed = Curve( gunswayspeed, smoothedgunswayspeed,8.0 )
if smoothrecoil<0.001 then
	guntime = guntime + AppSpeed() * smoothedgunswayspeed * math.max(0.0,1.0 - smoothswaydamping)
end
gunoffset.z = gunoffset.z - smoothrecoil * 0.05
--smoothedgunswayamplitude = smoothedgunswayamplitude * (1.0 - smoothswaydamping)
gunoffset.x = gunoffset.x + math.sin( guntime ) * smoothedgunswayamplitude * gunscale
gunoffset.y = gunoffset.y + (1.0-math.cos( guntime*2.0 )) * 0.005 * gunscale-- * math.min(1.0,1.0 - smoothswaydamping))
vwep:SetPosition( gunoffset )
recoil = recoil-0.1
swaydamping = math.max( swaydamping - 0.05, 0.0 )
recoil = math.max(recoil,0.0)
smoothrecoil=Curve(recoil,smoothrecoil,3.0)
smoothswaydamping = Inc( swaydamping ,smoothswaydamping,0.01 )
gunlight = math.max( gunlight- 0.2, 0.0 )
lightsmoothing =gunlight-- Curve(gunlight,lightsmoothing,8.0)
muzzleflash:SetColor(Vec4(1.0*lightsmoothing,0.6*lightsmoothing,0.0,1.0))
if lightsmoothing <0.01 then
	muzzleflash:Hide()
end
if MouseDown(1)==1 then
	if AppTime()-lastfiretime>gunfirefrequency then
		recoil = 1.0
		lastfiretime=AppTime()+math.random(0,20)
		gunswayspeed=0.0
		gunlight = 1.0
		source_gunshot:Play()
		source_gunshot:SetPitch(1.0 + (math.random()-0.5)*0.05 )
		swaydamping = 1.0
		muzzleflash:Show()

		CreateBullet(vwep:GetPosition(1) , fw.main.camera.mat:K():Scale(300))

	end
end

UpdateBullets()

flashlight.light:SetPosition(fw.main.camera:GetPosition(1))
flashlight.light:SetRotationf( CurveAngle( fw.main.camera.rotation.x, flashlight.light.rotation.x, 3.0/AppSpeed() ), CurveAngle( fw.main.camera.rotation.y, flashlight.light.rotation.y, 3.0/AppSpeed() ) )
flashlight.light:Movef(-0.07,-0.04,0.02)

fw:Render()
DrawHUD(controller)
Flip(0)
end

controller:Free()
vwep:Free()

ShowMouse()

Ryzen 9 RX 6800M ■ 16GB XF8 Windows 11 ■
Ultra ■ LE 2.53DWS 5.6  Reaper ■ C/C++ C# ■ Fortran 2008 ■ Story ■
■ Homepage: https://canardia.com ■

Link to comment
Share on other sites

Yeah, I though also of making fpscontroller using some classes, but this is just the first working version with Engine.exe.

I noticed that emitters don't work, and that the skybox is loaded although it should not. Must be a bug in Engine.exe :lol:

Ryzen 9 RX 6800M ■ 16GB XF8 Windows 11 ■
Ultra ■ LE 2.53DWS 5.6  Reaper ■ C/C++ C# ■ Fortran 2008 ■ Story ■
■ Homepage: https://canardia.com ■

Link to comment
Share on other sites

Yeah, I though also of making fpscontroller using some classes, but this is just the first working version with Engine.exe.

I noticed that emitters don't work, and that the skybox is loaded although it should not. Must be a bug in Engine.exe :lol:

 

 

Sorry, when I say objects I mean the kind of objects you drag into the scene from the tree view of the editor and not classes in the fpscontroller.lua. I thought I remember Josh saying he wanted to change the name of those. I still don't think object is a very good name also. I don't like model either because we can have logical "things" and not just models. There must be a better name for the "things" we are dragging into the scene. Can't be entities because it's confusing with the LE TEntity type.

 

Anyway I think the best game script lua file would be something more like:

 

require("Scripts/constants/collision_const")
require("Scripts/constants/engine_const")
require("Scripts/LinkedList")
require("Scripts/filesystem")
require("Scripts/math/math")



if fw==nil then --we are not in Editor
       RegisterAbstractPath("")
       Graphics(800,600)		-- need a better way to get screen res
       fw=CreateFramework()
       scene=LoadScene("")		-- need a way to get a scene to load
       scene:SetCollisionType(COLLISION_SCENE)
       TFilter(1)
       AFilter(4)
end


SetGlobalString("mode", "GAME_MODE")

FlushKeys()
FlushMouse()


--main function
while KeyHit(KEY_ESCAPE)==0 do
       fw:Update()
       fw:Render()
       Flip(0)
end

SetGlobalString("mode", "DESIGN_MODE")

Link to comment
Share on other sites

Let's start improving this with the options like screen resolution and which map to load.

The first thing which comes to my mind would be reading a fpscontroller2.ini file from disk with LUA.

Then there could be a fpscontroller2config.lua which would launch an UI where the user can select the options.

It could be also part of fpscontroller2.lua, but then there would need to be a title screen where you can choose to play the game or to configure the settings.

 

I'm not sure how your GAME_MODE idea works, because then it should support all kind of game types. I think it's easier to make a seperate lua file for each game type (at least in the beginning).

Ryzen 9 RX 6800M ■ 16GB XF8 Windows 11 ■
Ultra ■ LE 2.53DWS 5.6  Reaper ■ C/C++ C# ■ Fortran 2008 ■ Story ■
■ Homepage: https://canardia.com ■

Link to comment
Share on other sites

Your gfx mode was done by AndfGFX. of course his is still in a lua file, its just in a different lua file, but still hard coded. It really needs to be set at the first load, then written to a CFG file for storage, then if you crash while trying to load the mode you set, you can always manually edit the CFG file, and turn the settings back down again.

AMD Phenom II x6 1100T - 16GB RAM - ATI 5870 HD - OCZ Vertex 2 60GB SSD

76561197984667096.png

Link to comment
Share on other sites

I'm not sure how your GAME_MODE idea works, because then it should support all kind of game types. I think it's easier to make a seperate lua file for each game type (at least in the beginning).

 

You are thinking to specific. The game lua file shouldn't be game specific at all. The objects that we drag into our scene should handle the specific behavior.

 

My game mode variable is so the object scripts can tell if they are in game mode or editing mode. In the Update() method inside scripts you will want to know if you are actually running the game in the editor or if you are editing the scene in the editor. You would want to know this because for camera control objects (3rd person/first person/topdown) you don't want that logic running when in editor mode because it'll take over your editing camera, which would render editing impossible.

 

In my view the code listed above (and maybe some more non specific things) should be the only game lua file you need. Everything should be done via object/model lua files. If you want fps camera controls, make a object that handles that. If I want to use it I just drag that object into my scene and boom, fps style game. In my 3rd person camera example I drag a 3rd person camera object into my scene, give it a target, set some settings and then when I run my game I have 3rd person controls on my target. The positioning of the 3rd person object in the scene is where the camera starts out. This is the ultimate flexibility and way more object oriented than having different lua files for different game types.

 

We have to break away from the idea of these objects we drag into our scene needing to be models. They can be camera/game/gui logic as well.

 

Another example of what I'm doing is character keyboard control object. Place it in your scene, give it a target and set settings like Forward/Backward/Strafe Left/Right/Jump etc... These will be bound to keys. When you run the game and press these keys it'll move your target accordingly.

 

As far as the res and map a config/ini file would probably work well enough?

Link to comment
Share on other sites

Putting additional game core related entities to a Editor scene is also not the optimal solution. Then all those additional entities would be needed to be present in all scenes. That's redundant and allows unique information to be corrupted (as the same information should be present in all scenes).

Of course this problem is raised by Editor itself, since it doesn't utilize a "common scene" and the "actual scene" concept. The "common scene" would contain all entities which are common in all scenes (for a specific project).

However, there is a indirect solution for this problem: You could have a "common scene reference" entity, which would then load the common scene, and all its contained entities.

 

Another solution would be to rewrite Editor to use sqlite databases instead of sbx files :(

Ryzen 9 RX 6800M ■ 16GB XF8 Windows 11 ■
Ultra ■ LE 2.53DWS 5.6  Reaper ■ C/C++ C# ■ Fortran 2008 ■ Story ■
■ Homepage: https://canardia.com ■

Link to comment
Share on other sites

I don't see that as a huge issue, but you are correct it does make things cumbersome as you have to add these elements for each scene, and forgetting something could mess your game up. If we had prefabs it could ease the pain as you could make a prefab of your core game objects so it's easier to just add the prefab to the each scene.

 

I still think it's a more object oriented approach and gives greater flexibility than a hardcoded game script.

 

The basic game script I provided could use more code for switching levels. Ideally you would have a volume trigger that would communicate back to the main game script on what level to load.

Link to comment
Share on other sites

Let's also not forget that we can create global things. So we could get creative and have objects have global variables that aren't part of the objects class. That would be one way to share data that needs to persist over multiple scenes. Although if I needed data to persist through multiple scenes it's probably best to have the object use sqllite to store the data. When the object starts up it queries the tables to get it's data. That way when you place an object in the first scene it's writing data to the sqllite db. Then when you unload the first scene and reload the second scene and the object is in the second scene it would read the sqllite db to get the data. This would make sense for something like inventory. The cool thing about this is it would most likely be required for saving points anyway AND we can distribute all this with the object and the users wouldn't need anything extra since sqllite doesn't require anything special. I think there is a lua binding for sqllite :(

 

So I can make an inventory object that you drag into your scene. It writes to a sqllite db all the items you have. When it first loads up it reads the sqllite db to populate the items you have. That would allow multiple scenes to share the data of an object that you drag into your scene. Global values could work also but you might run into variable naming issues.

Link to comment
Share on other sites

I think the term Nodes is also good?

 

There are many words we are using the mean the same thing, and some creative multi-word ones:

  • Entity
  • Object
  • Node
  • Element
  • Type
  • Item
  • Thing
  • ScriptedEntity
  • ScriptedObject
  • ScriptedElement
  • Scripted...
  • SceneNode
  • SceneEntity
  • Scene...
  • ModelScript

For all intensive purposes I think they (they=objects created from a class archetype in Lua) should be called Scripted Entities, the model they are associated with is a Model, the combined Model/Script Entity File should be called an Entity.

52t__nvidia.png nVidia 530M cpu.gif Intel Core i7 - 2.3Ghz 114229_30245_16_hardware_memory_ram_icon.png 8GB DDR3 RAM Windows7_Start.gif Windows 7 Ultimate (64x)

-----

IconVisualStudio16.png Visual Studio 2010 Ultimate google-Chrome.png Google Chrome PhotoshopLinkIndicator.png Creative Suite 5 icon28.gif FL Studio 10 MicrosoftOfficeLive.png Office 15

-----

csharp.png Expert cpp.png Professional lua_icon.png Expert BMX Programmer

-----

i-windows-live-messenger-2009.pngskype-icon16.pngaim_online.pnggmail.pngicon_48x48_prism-facebook.pngtunein-web.pngyahoo.giftwitter16.png

Link to comment
Share on other sites

Then why can't we say TEntity for that? Or maybe an internal entity, or scenegraph entity.

52t__nvidia.png nVidia 530M cpu.gif Intel Core i7 - 2.3Ghz 114229_30245_16_hardware_memory_ram_icon.png 8GB DDR3 RAM Windows7_Start.gif Windows 7 Ultimate (64x)

-----

IconVisualStudio16.png Visual Studio 2010 Ultimate google-Chrome.png Google Chrome PhotoshopLinkIndicator.png Creative Suite 5 icon28.gif FL Studio 10 MicrosoftOfficeLive.png Office 15

-----

csharp.png Expert cpp.png Professional lua_icon.png Expert BMX Programmer

-----

i-windows-live-messenger-2009.pngskype-icon16.pngaim_online.pnggmail.pngicon_48x48_prism-facebook.pngtunein-web.pngyahoo.giftwitter16.png

Link to comment
Share on other sites

Thing works well but is a little generic. I think Thingoid would be both descriptive and unique enough that it wouldn't be confused with other "things" we're talking about.

 

 

lol I like Thingoid :(

 

"So I drop a thingoid into my scene and it doesn't work"

 

That sounds right

Link to comment
Share on other sites

Thing works well but is a little generic. I think Thingoid would be both descriptive and unique enough that it wouldn't be confused with other "things" we're talking about.

 

 

Gets my vote .. but then I stack tables into caves so that might not be a ringing endorsment :)

AMD Bulldozer FX-4 Quad Core 4100 Black Edition

2 x 4GB DDR3 1333Mhz Memory

Gigabyte GeForce GTX 550 Ti OC 1024MB GDDR5

Windows 7 Home 64 bit

 

BlitzMax 1.50 • Lua 5.1 MaxGUI 1.41 • UU3D Pro • MessiahStudio Pro • Silo Pro

3D Coat • ShaderMap Pro • Hexagon 2 • Photoshop, Gimp & Paint.NET

 

LE 2.5/3.4 • Skyline UE4 • CE3 SDK • Unity 5 • Esenthel Engine 2.0

 

Marleys Ghost's YouTube Channel Marleys Ghost's Blog

 

"I used to be alive like you .... then I took an arrow to the head"

Link to comment
Share on other sites

No, you stack table-like Thingoids into caves...get with the program :blink: Maybe onces prefabs are in we could call them Throngoids.

 

 

 

hmm.. risky .. as typos where the "r" got dropped would leave you with something that sounded like a medical complaint :)

AMD Bulldozer FX-4 Quad Core 4100 Black Edition

2 x 4GB DDR3 1333Mhz Memory

Gigabyte GeForce GTX 550 Ti OC 1024MB GDDR5

Windows 7 Home 64 bit

 

BlitzMax 1.50 • Lua 5.1 MaxGUI 1.41 • UU3D Pro • MessiahStudio Pro • Silo Pro

3D Coat • ShaderMap Pro • Hexagon 2 • Photoshop, Gimp & Paint.NET

 

LE 2.5/3.4 • Skyline UE4 • CE3 SDK • Unity 5 • Esenthel Engine 2.0

 

Marleys Ghost's YouTube Channel Marleys Ghost's Blog

 

"I used to be alive like you .... then I took an arrow to the head"

Link to comment
Share on other sites

Anyone know why if I run this in the Script editor (outside of Editor) it is very slow to load, and runs ten times slower than just dropping the .lua file on engine.exe ?

 

Robin

 

Happy new year everyone :blink:

Programmer , Intel Quad core, NVIDIA GeForce GT 220, Windows 7 Pro, Galaxy Tab 2 ( 7" and 10"), LE2,LE3,3DWS

Link to comment
Share on other sites

I don't seem to be able to remove the 'Frames per Second stats' from this code. Usually it is with the SetStats Framework command but I can find no sign of it here or in the 'require' scripts. Has anyone located it? :D

AMD Athlon x2 7750 2.7ghz, 6gb ddr2 ram, Galaxy9800GT 1gig ddr2 video card, Windows 7,64.

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

 Share

×
×
  • Create New...