Jump to content

{Character perks} mining gems


Recommended Posts

Well, some of my mods are also using AddPrefabPostInit(), and i can only get them to work on both server and client, by NOT checking for ismastersim or similar. Try the code below instead. It checks for the workable component, and if it doesn't find it, it doesn't try to change it.
Only the server needs prefabs (objects in the world) to have all components on them, since it is responsible for running their "lives". In a game without caves, you are the server, so it works because all the prefabs have all their components on them. When you add caves, you are instead a client, and the server is set up separately as a dedicated server behind the scenes, which you join automatically. This is convenient when testing mods, because starting a server without caves lets you test whether the mod works on servers, and with caves it lets you test whether your mod also works on clients :)

This is an important change, because as the client, all your prefabs are only sort of "shells" of themselves. They don't have all the components, so when you're about to try to make changes to a component in your mod code, you should ALWAYS check that that component is actually there.

local function MyPostInit(inst)
	if inst.components.workable ~= nil then
		cached_onwork = inst.components.workable.onwork
		inst.components.workable:SetOnWorkCallback(MyOnWork)
	end
end

 

Now that I think about it, the above is basically just a workaround for doing the IsServer checks.

You can try another way. Change your MyPostInit back to:

local function MyPostInit(inst)
	cached_onwork = inst.components.workable.onwork
	inst.components.workable:SetOnWorkCallback(MyOnWork)
end

and then surround your AddPrefabPostInit() calls with this server check:

if GLOBAL.TheNet and GLOBAL.TheNet:GetIsServer() then
        -- Put all your AddPrefabPostInit calls in here
end

 

Edited by Ultroman
Link to comment
Share on other sites

1 hour ago, Ultroman said:

Well, some of my mods are also using AddPrefabPostInit(), and i can only get them to work on both server and client, by NOT checking for ismastersim or similar. Try the code below instead. It checks for the workable component, and if it doesn't find it, it doesn't try to change it.
Only the server needs prefabs (objects in the world) to have all components on them, since it is responsible for running their "lives". In a game without caves, you are the server, so it works because all the prefabs have all their components on them. When you add caves, you are instead a client, and the server is set up separately as a dedicated server behind the scenes, which you join automatically. This is convenient when testing mods, because starting a server without caves lets you test whether the mod works on servers, and with caves it lets you test whether your mod also works on clients :)

This is an important change, because as the client, all your prefabs are only sort of "shells" of themselves. They don't have all the components, so when you're about to try to make changes to a component in your mod code, you should ALWAYS check that that component is actually there.


local function MyPostInit(inst)
	if inst.components.workable ~= nil then
		cached_onwork = inst.components.workable.onwork
		inst.components.workable:SetOnWorkCallback(MyOnWork)
	end
end

 

Now that I think about it, the above is basically just a workaround for doing the IsServer checks.

You can try two other ways. Change your MyPostInit back to:


local function MyPostInit(inst)
	cached_onwork = inst.components.workable.onwork
	inst.components.workable:SetOnWorkCallback(MyOnWork)
end

and then surround your AddPrefabPostInit() calls with one of these server checks:


if GLOBAL.TheWorld.ismastersim then
        -- Put all your AddPrefabPostInit calls in here
end

OR


if GLOBAL.TheNet and GLOBAL.TheNet:GetIsServer() then
        -- Put all your AddPrefabPostInit calls in here
end

 

I've given it a good long test and it works perfectly, no errors or crashes :D

Thank you so much again! Super helpful!!

Link to comment
Share on other sites

I've done some more testing.

For the record, the second option (with GLOBAL.TheWorld.ismastersim) doesn't work for this purpose, as the TheWorld variable hasn't been created yet, when the mods are being loaded. It only works when used within functions.

The third option (with GLOBAL.TheNet and GLOBAL.TheNet:GetIsServer()) is to be preferred for the purpose of limiting the execution of AddPrefabPostInit, AddPlayerPostInit and AddComponentPostInit etc. to the server.

The first option (with checking every component for whether it's there), adds unwanted overhead when starting or joining a server, and depending on the code, may introduce unwanted results and errors.

Edited by Ultroman
Link to comment
Share on other sites

On 14/10/2018 at 1:16 AM, Ultroman said:

I've done some more testing.

For the record, the second option (with GLOBAL.TheWorld.ismastersim) doesn't work for this purpose, as the TheWorld variable hasn't been created yet, when the mods are being loaded. It only works when used within functions.

The third option (with GLOBAL.TheNet and GLOBAL.TheNet:GetIsServer()) is to be preferred for the purpose of limiting the execution of AddPrefabPostInit, AddPlayerPostInit and AddComponentPostInit etc. to the server.

The first option (with checking every component for whether it's there), adds unwanted overhead when starting or joining a server, and depending on the code, may introduce unwanted results and errors.

Ah, thank you!! It works nicely!

I've been testing myself and I've had no issues atm.

Thanks again for all the help, I really appreciate it :) !!

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

×
  • Create New...