- 'Dome' options should no longer be inverted - tweaked some of the A90 ones I added, like Halo
Some new stuff in this table:
code:
C Accumulation of magic around caster, before it 'launches', and when it hits 0 - accumulate over caster, land in body of target 1 - accumulate within caster, land in body of target 2 - accumulate under caster, land in body of target 3 - in the body of the caster, but 128pixels away from target 4 - in the body of the caster, but 128pixels towards target 5 - in the body of the caster, but halfway between caster and target 6 - Over the head of both caster and receiver 7 - at the feet of both caster and receiver
Some new stuff in this table
code:
DD 'cloud' shape of magic accumulation 00 - tight random cloud 01 - looser random cloud 02 - loose random cloud 03 - single circle 04 - two circles 05 - single circle - vertical 06 - two circles - vertical 07 - Big round circle 08 - Halo 09 - Vertical Halo 10 - Horizontal Line 11 - Vertical Line 12 - Slow Large Dome 13 - Fast LArge Dome 14 - Slow Small Dome 15 - Fast Small Dome 16 - increasing to large radius 17 - increasing to medium radius 18 - decreasing from large radius 19 - decreasing from meidum radius 20 - Spiraling Outward Circle 21 - Spiraling inward Circle
* NEW IF CONDITIONAL
IF<> or IF!= will go to the label if the previous COMPARE operation yieled 'not equal'
* ASK OPCODE CAN BE SECRET TO ALL
If you add an optional '1' like this
ASK 600 1
Then it will NOT send what you (the host) typed to the other players in the scene.
You will still see it yourself, however. This is one of those bits of code which I am too lazy to actually test though...
* BUGFIX - More support for 64 actors
The ACTOR and MOVE commands were only giving access to the first 32 (of 64 max actors).
* MOVE command can now move scene host
This is non-binding since it doesn't stop the host from moving elsewhere, but now you can move the host around like this:
MOVE H, x, y
Could be fun. "Hero, approach the king!"
* COOKIE SUPPORT ADDED TO MORE COMMANDS
I did this sort of randomly, and it's possible I might have broken something, and missed other things. But basically, you can use cookies in more commands now than you used to be able to. For example the ACTOR and POSE commands let you get all the numeric values out of cookies, if you like.
I only upgraded numeric values, since that felt like I would be less likely to prematurely evaluate a cookie.
Hopefully you won't even notice I did this.. knock on wood.
* TIMER EVENTS!!
At long last, you can use timers to restart a script after it has ENDed. You have 10 timers (numbered 0 - 9). When a scene first starts, all the timers are turned off. You turn on a timer like this:
TIMER 4, 7.8 END
This means that timer 4 will fire in 7.8 seconds from RIGHT NOW (time starts from the moment you execute the TIMER command, NOT from a subsequent END command.)
When the timer fires, it looks for a label like:
@eventTimer4
(where 4 is the timer ID from this example, but could be 0 through 9)
Like other events, timer events can only trigger while the scene is ENDed (and they wake the scene back up.)
So, what are timers good for?
Well, you could maybe end a fight, change the weather, play a sound effect, change the background, evaluate how long it took someone to do something, etc.
If you wanted a periodic timer, you might try something like this
1: I will change the weather every second TIMER 1, 1.0 END
@timerEvent1 WEATHER %R9 TIMER 1, 1.0 END
So, when the timer triggers, I change the weather to a random value 0-9 and then restart the timer for another second (and then END again, of course!)
* SPECIAL TIMER TRICKS
cookie: 'num.timerLengthN' returns length of timer N in milliseconds
cookie: 'num.timerLeftN' returns number of msec left in timer N (before it will trigger.. assuming you END again before that)
TIMER N, 0 -- kills timer N TIMER -1 -- kills ALL timers
Please don't be confused by my lazy implementation. I let you set the timer by SECONDS (like the WAIT command), but the cookie reads time left as MILLISECONDS... I only added the cookies so you could do things like praise the player if they finished some action with lots of time left.
* BUGFIX - NO MORE CAMP DRAGGING
Sorry. And thanks to Pippin (and others) for clearly documenting the procedure.
* GENDER-SPECIFIC PAIN SOUND
I think this is probably a slippery slope here, since ultimately people should be able to specify their own favorite sounds.. but for NOW, the enhancement is that the gender.ini file can optionally override the pain sound used for players when they get hurt.
Add a line like:
pain1.wav=pain10.wav
which will make it play pain10.wav when a player of that gender is hurt. I know it's weird to have "pain1.wav" on the left instead of just "pain" or "painSfx" but that's life. Gender.ini is all about 'translation'
* COMMAS IN MONSTER NAMES AND SKIN NAMES ARE REMOVED
Turns out that a comma in a name would lead to corrupted packet handling. I'm afraid commas are not legal in these fields, and hence "Konan, The Destroyer" will now appear as "Konan The Destroyer"
* CURSED TROPHIES
If you set the 'gold per stack' value to a negative number, then the holder of a trophy cannot 'sell' the trophy, but instead has to 'pay' the shopkeeper to be rid of it. Neither can the trophy be discarded or given away.
Something like a 'healing fairy heart' from something you killed that shouldn't ought to have killed, and now must carry your shame with you. (and yes, Cowardly PK Kill Hearts are my intended ultimate target for this )
Note that if the price is over 1 million (and the stack size is 1), they can't get rid of it. Which is probably pretty nasty since it consumes a trophy bag slot. An NPC could remove it, of course.
* AMMUNITION TROPHIES
This is a very simple implementation. Basically in the ITEM and SPELL tables is a new field "trophyNeeded"
If you set this to a non-zero value, then the player cannot use that (right-hand) weapon, or cast that spell, unless they have at least one of the specified trophy (and a trophy is then removed from their bag). This does NOT affect 'use item on yourself' just right-hands and spells. (in the case of a wand, where the right-hand does a spell, it uses the ITEM trophy and not the SPELL trophy.. I think).
For example, see the Evergreen 'Rubber Balls' DART (now consumes a green jelly pigment) and the spell GEL (which also consumes a green jelly pigment)
* RESIDUE TROPHIES
Also in the ITEM and SPELL tables are new arguments for 'trophyMade' When you use a right-hand weapon, or spell, with one of these, then that trophy is added to your bag. These could be good things (the 'mining' spell resulting in 'gold nuggets' appearing) or bad things (using 'armageddon' giving you a 'cursed spark' trophy)
For example, see the Evergreen GEL command which consumes a Green Jelly Pigment trophy, but creates a Slobber Eyeball trophy.
And sorry, only one ammunition per thingy, so you can't use this to trivially do things like "this spell consumes 4 jellies, 5 earwigs, and 14 gondolas to create one hand of flax" You have to do that sort of thing with a script. Though with the miracle of subroutines, you should be able to make that data-driven within your quest files.
And I extended the property editor to support these.
* NEW SLASH COMMAND: /Trophy
Opens the trophy bag.. if you have one..
* NEW TROPHY TABLE COLUMN: Flags
Arg 9 of the trophy table is now a 'flags' field which includes:
1 - no sell 2 - no give 4 - no discard
This limits right-click menu functionality on the trophy bag. Scripted NPCs can disobey these settings.
* NEW ACTOR ARGUMENT: Pain Sound
The script command to add an ACTOR to the scene now lets you specify its 'pain' sound effect as well.
The full list is now:
ACTOR <id>, <nam>, <skin>, <pose>, <x>, <y>, <colorTable>, "pain.wav"
And without this, they should be silent. (so all old worlds will suddenly have silent-when-hit actors. Blame... um... Crusard!
* NEW QUEST BOOLEAN COMMANDS: AND/OR/NOT/XOR
Not sure if anyone would ever really NEED these, but they let you do 'bit-wise' boolean math. They work just like the ADD instruction in that they start with a cookie, then modify it per the instruction. NOT is a bit odd since it requires no second argument.
AND cookieName, 1 (contents of cookie 'ANDed' with 1) OR cookieName, 12 (contents ORed with 12) XOR cookieName, 8 (contents XORed with 8) NOT cookieName (contents ones-complemented)
* NEW IF CONDITIONS: EVEN AND ODD
I can't believe I added this. How lazy can a world developer be, hmm? But here you go:
And there is no such thing as 'neither odd nor even' in my universe.
* ACTOR CLICK EVENT INCLUDES TRANSPARENCY CHECK
When you get an onEventActorClick event, you can look at this cookie:
event.actorVisible
and if it is not zero, it means they clicked on a VISIBLE (not transparent) part of the actor skin. If you don't check this, then it just means they clicked somewhere inside the actors skin rectangle.
OK OK, this doesn't work. Sorry. It will only work if you actor uses pose 0 of its image strip, and that image looks the same when 'flipped' Sorry.
To make up for that false alarm, I give you two more:
event.inActorX event.inActorY
These are set to the offset inside the actor rectangle where you clicked, in 'pixels' (not in screen percentags). (0,0) is the top left of the rectangle.
* NEW CONDITIONAL TEST: J for 'Mission'
Yeah yeah, I ran out of letters. Must mean the game is just about complete
This allows you to test if the host has completed a mission (see below).
IF J23, @hasDoneMission 23
* MISSIONS
This is actually a pretty big deal and I hope I left it general purpose enough to be used for lots of stuff.
Basically, with trophies we got the ability to make simple 'collection' quests (hereafter called 'missions') where your hero needs to go achieve N things and in return gets some reward. Without necessarily requiring a lot of scripting or scene work. Though, as you will see, Missions are handed out by NPCs in scenes via the new 'missions' button.
Please read the Evergreen 'missions.ini' file for details, but the flow is something like this:
1.) You define your missions in worldFolder/missions.ini
2.) Each mission has a name, description, some message text, a requirements list, a needs list, and a set of rewards.
3.) You issue missions via the new MISSIONS script command, which generally acts a lot like the OFFER command, adding a MISSION button in the scene.
4.) Pressing the MISSIONs button opens the 'Available Missions' dialog which shows a list of all the missions offered in that scene, for which you meet the starting qualifications.
5.) You can ACCEPT a mission, at which time it becomes OPEN/IN PROGRESS. At any time, you can ABANDON a mission to get it off of your open missions list.
6.) You can review your OPEN MISSIONs list at any time by using the Book menu "Book of Missions" and see the progress you have made towards completing each mission.
7.) When you have met the mission requirements, a 'collect reward' button will appear. Press that and you will collect a reward. (and the mission will be marked 'DONE' and thereafter only appear on the 'review past missions' dialog.)
8.) Each mission specifies a "Qualifies" string which is a conditional just like that used in the quest IF command. So you could say:
Qualifies=L3+T4-T7+J23
Meaning to qualify you must be Level 3 or above, have token 4, but NOT token 7, and you must have completed mission 23 (yeah yeah, 'J' Ok, call it a JOB and then it sounds like I planned it)
9.) Each mission specifies a "Trophies" string which is a list of all the trophies you need to acquire before the mission is complete. For example:
Trophies=5x1,10x23,100x16
Meaning you need five trophy 1s, 10 trophy 23s, and 100 trophy 16s to complete the quest. When you collect your reward, these trophies will be removed from your trophy bag
10.) each mission provides one or more of the following rewards:
- Gold - Experience - abstract item - token
By Abstract Item I mean:
RewardObject=I23 (item23)
which could be S15 (spell 15), etc. The same syntax as used by the GIVE command. Which can also give Gold and Tokens, so it's a little redundant and I leave it to you to best decide how you want to use it.
11.) In the trophies table is a new field 'flags' and one of those flags is 'mission only' which means a monster will only drop it if it knows it is needed by one of your open missions.
12.) Mission Sound Effects (which you should be able to override by world or theme, as well as any other sound)
missionAccepted.wav missionAbandoned.wav missionComplete.wav missionTrophy.wav -- each time you get a mission trophy
* HOLIDAY COOKIES
This is a little silly, and you can test the date yourself, but there is some small advantage to this since I do things like "3rd monday in may" and "easter" calculations for you which are slightly non-trivial. You probably won't find your favorite holiday here, but hey, that just means you are some godless commie and not a member of the one true greatest country on earth! Denmark!
num.holidayID (if this is 0, its not a holiday) str.holidayName (e.g. "Christmas") str.holidayGreeting (e.g. "Merry Christmas")
My goal was to make it easier to have easter eggs in scenes, which only triggered on special days.
The BIRTHDAY holiday is the annual birth day of the WoS character you are using. (It remembers the day of the year you made the character)
All holidays last for 24 hours from local midnight.
* GENERIC WORLD TABLES
So, say your world has need for a lot of tabular data.. stuff that the WoS engine doesn't need to know about directly, but that you use in your scripts a lot. Say you have your own skill system, or potion making formulas or anything else which can be defined by rows of columns of data in a table.
First the limitations. No more than 100 tables (stored in your world folder in files called "DevTableNN.txt" where NN is 00-99)
No real limit on the number of rows in a table (one line of text in your file is a row), but smaller is faster.
each row is a bunch of comma-separated values (just like a QUEST file, only YOU decide what the columns mean.) You are limited to 30 columns and each row of text must be less that 4000 characters wide.
You can pepper your table with comments, where anthing on the line after a 'semicolon' is ignored.
Each column can have an arbitrary string (max length of 100 characters per string, I think.. well, same as for QUEST whatever that is MAX_PATH in computer terms.. minus a couple). It can be a number or text, but you should put text inside double-quotes.
You can NOT use #include in a DevTable.
You do NOT put QUEST commands in a DevTable.
The first argument on each line is its "RowId" and should be unique. It can be a number (like I do with spells and such) or some text if you like. But each row needs a unique id (unique within that one table file). When you ask me to look for a row by its id, I am going to start with the first line of the file and keep looking until I find it or the end of the file.
Remember, WoS will do nothing with your devTables other than fetch values from them (via cookies). And these are read-only, like the quest files. (Developer can edit them, just like quest files, but for the end player they do not change.)
They are included in the world version, so tampering will result in a 'modified world'
Example Table: DevTable32.txt in your world folder
code:
; This is my table of skins used in my mini-game ; ROWID, COL1=Actor#, COL2=SkinName Butter, 1, "Jumping Butter Can" Cheese, 2, "BlueCheese" ; Note, dan doesn't read these comments ; so that stuff I said about COL1 is just for me
Then, to read the table in my SCENE script, I need to do three things:
1.) select the current DevTable
SET num.DevTableId, 32
2.) select the current ROW of the table
SET str.DevTableRowId, "Butter"
3.) fetch one of the COLUMNS of information
1: the skin name is #<str.DevTableCOL2>
The end.
* EVEN MORE COOKIES
str.worldName - name of current world being played (may not be capitalized in any particular way)
item.desc - long desctiption of item item.ap - ability points provided by item item.fp - find probability of item event.missionId - id associated with @eventMission event str.actorNameNN - name of actor NN in this scene, if any.
* MISSION EVENTS
OK, these only work, like all 'events' if you are in a scene, are the host of the scene, and the scene is currently ENDed. They bring the scene back to life at the @label matching the event description.
You can then ask for cookie "event.missionId" to find out which mission is being talked about.
@eventMissionAccepted - they pushed the accept button @eventMissionAbandoned - they pushed the abandon button @eventMissionRewarded - they collected their mission reward
Remember, they can do the Abandon or Reward anywhere they like, so don't depend on seeing these events inside of any particular scene (or even at all, since they can do these actions outside of scenes). These events are just for happy friendly NPC acknowledgements, and maybe some 'extra value' for those players who DO go all the way back to the scene which offered the mission in the first place.
* NEW MAP FLAG - NO_ITEM
MAP_FLAG_NO_ITEM 0x00100000 1048576 // No using of items in the scene
-------------------- He knows when you are sleeping. Posts: 10581 | From: California | Registered: Dec 1998
| IP: Logged