Page 1 of 1
CODING ADVICE NEEDED!
Posted: Tue Jan 27, 2015 11:45 am
by WaspUK1966
I have written the following script that makes a random champion say something when triggered:
Code: Select all
function champspeech()
x = math.random(1,4)
if party:getChampion(x):isAlive() then
local Name1 = party:getChampion(x):getName()
hudPrint(""..Name1.." whispers: WHAT was that?..")
playSound("secret")
else
end
end
In it's present form, if the random champion IS ALIVE then the script prints to the screen. However, if the random champion is dead or not enabled, the script will end. I want to code it so that, if the chosen champion is dead , it will then keep looping (generating random numbers 1 thru 4 ), until it finds a champion that is still alive, and then runs the code, rather than just end as it does now. Any advice?
Thanks
George
Re: CODING ADVICE NEEDED!
Posted: Wed Jan 28, 2015 12:03 pm
by Komag
Code: Select all
function champspeech()
x = math.random(1,4)
if party:getChampion(x):isAlive() then
local Name1 = party:getChampion(x):getName()
hudPrint(""..Name1.." whispers: WHAT was that?..")
playSound("secret")
else
end
end
I'm not up to snuff with Grimrock 2 Lua, but you might try check for NOT isAlive(), and if it finds that the champion is dead, go back to the start of the function. Or maybe try a While loop with a variable "itsAlive":
itsAlive = FALSE
WHILE itsAlive = FALSE DO
x = math.random(1,4)
if party:getChampion(x):isAlive() then itsAlive = TRUE
END
I'm sure some of that syntax is wrong
Re: CODING ADVICE NEEDED!
Posted: Wed Jan 28, 2015 1:55 pm
by WaspUK1966
Thanks for the reply, Komag. I should have stated that this code is for LOG 1, not the sequel. Does that help?
George
Re: CODING ADVICE NEEDED!
Posted: Wed Jan 28, 2015 11:01 pm
by Komag
Not really, but the concept should be the same, maybe the exact code even
Re: CODING ADVICE NEEDED!
Posted: Thu Jan 29, 2015 2:41 pm
by bitcpy
For a small data-set it doesn't really matter if you would loop until finding a champion alive or if you would randomize a value inside a known list of valid indices.
But pretend you would have a list of one hundred thousand indices, half of them having the state 'alive' and the rest being counted as 'dead'.
Looping until finding an 'alive' index could take you some time, if you're unlucky in that case.
I'd suggest you figure out what champions are alive, then randomize in that set.
It could look something like this,
Code: Select all
function champspeech()
-- build a list of alive champions
local champIds = {}
for i = 1, 4 do
if party:getChampion(i):isAlive() then
table.insert(champIds, i)
end
end
-- only allow a champion to speech if anyone was actually alive
local num = table.getn(champIds)
if num > 0 then
-- fetch a random champion from the list of alive ones
local x = math.random(1,num)
local champId = champIds[x]
local champName = party:getChampion(champId):getName()
-- print information to screen that the champion found something
hudPrint( champName .. " whispers: WHAT was that?" )
playSound("secret")
end
end
Re: CODING ADVICE NEEDED!
Posted: Thu Jan 29, 2015 5:56 pm
by Komag
I agree that's actually the best way for a longer set, I thought of it but figured it was overkill in this case. One problem with my simpler option, though, is if all four champions are dead (and you don't let the game be over), it would loop forever. Probably not an issue though unless you plan to allow a full dead party to keep playing.
Re: CODING ADVICE NEEDED!
Posted: Thu Jan 29, 2015 10:14 pm
by Isaac
You can try this in a script. You can call it with optional arguments, or just link directly to it with a plate or switch.
* Try calling it with: speak("We are locked in!", "shouts", 3, "gate_lock")
* includes a help function: script_name:help()
Code: Select all
discern_triggers = true --set false to disable special handling of button and switches
function speak(caller, message, action, ordinal, secret, option) --ordinal nil for random champion; secret and option are booleans
local ordinal = ordinal or math.random(4)
--=-------------------------------------------------------------------------------[check for live PC]--
for x = 0,3 do
local z = (((ordinal - 1) + x) % 4) +1
local champion = party:getChampion(z)
if champion:isAlive() then
local message = message or _randomAlert() --=-----[ensures default values]--
if option then
message = _randomAction().." "..message
else
local action = action or "says"
message = action..": "..message
end
if discern_triggers and _isSwitch(caller) then --=---------------------[button/switch check]--
message, secret = _buttonSpeak(caller, champion)
end
if secret then --=--------------------------------[check for sound and then print to screen]--
if type(secret) == "string" then
playSound(secret)
else playSound("secret")
end
end
hudPrint(tostring(champion:getName().." "..message))
break
end
end
end
function _buttonSpeak(caller, champion)
--=-----------------------------------------------------------[special handling for switches]--
--Ids and messages for the connected switches, and optional sound effect.
local switch_trigger_data = { --switch id, --action, --message, --sound
"pressure_plate_hidden_1", "shouts" , _randomAlert(3), "", --no sound -- no sound
"pressure_plate_hidden_2", _randomAction(), _randomAlert(), "secret", -- secret sound
"pressure_plate_hidden_3", "yells", "OUCH! I think I stepped on a tack.", "default_pain", --correct PC pain sound
}
local secret
local message
for t = 1, #switch_trigger_data, 4 do
if caller.id == switch_trigger_data[t] then
message = switch_trigger_data[t+1]..": "..switch_trigger_data[t+2]
if switch_trigger_data[t+3] == "default_pain" then
champion:playDamageSound()
elseif switch_trigger_data[t+3] ~= "" then
secret = switch_trigger_data[t+3]
end
break
end
end
return message, secret
end
--=-----------------------------------------------[utilities]--
function _isSwitch(target)
local switches = { "Receptor", "Lock", "Lever", "Button", "PressurePlate",
"Alcove", "Counter", "Timer", "TorchHolder",
}
for check = 1,#switches do
if switches[check] == target.class then
return true
end
end
end
function _randomAlert(pick)
local response = {"WHAT was that?", "Did you hear that?", "I heard something!", } --You can add as many responses to the list as you like; same with the actions.
if pick and type(pick) == "number" and pick <= #response then
return " "..response[pick]
end
return " "..response[math.random(#response)]
end
function _randomAction(pick)
local response = {"wispers", "says", "[startled] says", }
if pick and type(pick) == "number" and pick <= #response then
return " "..response[pick]
end
return " "..response[math.random(#response)]
end
function help()
print("Usage: speak(self, message, action, ordinal, secret, optional_expression)")
print("All arguments are optional, and any argument can be nil.")
print("Calling speak() will pick a champion and print their [random] announcement.")
print("")
print("Calling speak(\"Hello!\"), will use the given string as a random champion's statement.")
print("")
print("Calling speak(\"Hello!\", \"screams\"), will use \"screams\" instead of the default \"says\".")
print("")
print("Calling speak(\"Hello!\",nil,2), will choose champion [ordinal] 2 as the speaker; and use the default \"says\".")
print("")
print("Calling speak(\"Hello!\",nil,nil,[any non-string input]), will play the \"secret\" sound; or...")
print("You may enter the name of ant valid sound effect [in quotes] to play instead of the default of \"secret\".")
print("")
print("Calling speak(nil,nil,nil,\"gate_lock\", true), will play the \"gate_lock\" sound, and have a random champion")
print("exclaim a random alert.")
end
Re: CODING ADVICE NEEDED!
Posted: Fri Jan 30, 2015 1:16 pm
by WaspUK1966
Thank you everyone for all your input. Really appreciate it. Everyone on this forum is so helpful. People seemed to like my first game, OGRE, so I`m working hard on the sequel. I`m trying to make my games different from what's already out there, and like to try new stuff that will surprise people. So this code should come in handy.
Once again (until the next time I need help! lol!), thank you everyone.
George