• There is NO official Otland's Discord server and NO official Otland's server list. The Otland's Staff does not manage any Discord server or server list. Moderators or administrator of any Discord server or server lists have NO connection to the Otland's Staff. Do not get scammed!

[Lua] How to make a working Lua script

Wason

UnKnow Member
Joined
Jan 12, 2015
Messages
1,249
Reaction score
255
Location
EgypT
Ok, before we start with the tutorial, I'd like to say that I won't make any scripts for a server, I got my own at the moment
tongue.png

NOTE: THIS TUTORIAL EXPLAINS MORE HOW TO CREATE A SCRIPT, THEN WHAT THE BASICS ARE!

Do not think you won't learn anything, it's worth your time reading this tutorial! (only for the ones who haven't started LUA yet).

First of all, the functions. Now for every kind of script, you have other functions to start with. You HAVE to put a function in a script, otherwise it won't work.
Now there are several functions to start with:

  1. function onUse(cid, item, fromPosition, itemEx, toPosition)
  2. function onSay(cid, words, param)
  3. function onEquip(cid, item, slot)
  4. function onAddItem(moveitem, tileitem, position)
  5. function onDeEquip(cid, item, slot)
  6. function onStepIn(cid, item, frompos, item2, topos)
  7. function onStepOut(cid, item, frompos, item2, topos)

In this tutorial, I'm going to explain three of them:
  1. function onUse(cid, item, frompos, item2, topos)
  2. function onSay(cid, words, param)
  3. function onStepIn(cid, item, frompos, item2, topos)
    [*]function onStepOut(cid, item, frompos, item2, topos)
  4. And one extra:
  5. StorageValues!

Note that the functions onStepIn and onStepOut are placed in one script!
 
Last edited:
Note that the functions onStepIn and onStepOut are placed in one script!

Now in a function, we have commands. In OT we have ALOT of them!
Here are a few of them:

  1. getPlayerFood(uid)--Returns the food ticks of player
  2. getPlayerHealth(uid)--Returns the player's health
  3. getPlayerMana(uid) -- Returns the player's mana
  4. getPlayerLevel(uid)--Returns the player's level
  5. getPlayerMagLevel(uid) -- Returns the player's magic level
  6. getPlayerName(uid)--Returns the player's name
  7. getPlayerAccess(uid) -- Returns the player's access
  8. getPlayerPosition(uid)--Returns the player's position
  9. getPlayerSkill(uid,skillid) -- Returns the player's skill level of a skill
  10. getPlayerMasterPos(cid)--Returns the player's temple position
  11. getPlayerTown(cid) -- Returns the player's town-id
  12. getPlayerVocation(cid)--Returns the player's vocation
  13. getPlayerItemCount(cid,itemid) -- Returns the amount of an item that the player has
  14. getPlayerSoul(cid) -- Returns the player's soul
  15. getPlayerFreeCap(cid)--Returns the player's free capacity
  16. getPlayerLight(cid) -- Returns the player's light ticks
  17. getPlayerSlotItem(cid, slot)--Returns an item if an item is found in the slot
  18. getPlayerDepotItems(uid, depotid)--Returns the player's depot items of a decent depot
  19. getPlayerSex(cid) -- Returns the player's gender
  20. getPlayerLookDir(cid)--Returns the player's look direction
  21. getPlayerStorageValue(uid,valueid) -- Returns the value of the value id of a player
  22. setPlayerStorageValue(uid,valueid, newvalue) -- Adds a new value-id to the storage map of player
  23. getGlobalStorageValue(valueid) -- Returns the value of the value id
  24. setGlobalStorageValue(valueid, newvalue) -- Adds a new value-id to the storage map
  25. getTilePzInfo(pos) 1 is pz. 0 no pz. -- Returns the protection zone status of a tile
  26. getTileHouseInfo(pos). 0 no house. != 0 house id -- Returns the house status of a tile
  27. getItemRWInfo(uid) -- Check if the item is writeable
  28. getThingfromPos(pos) -- Returns something that matches the position
  29. getThingPos(uid) -- Returns the position of something
  30. doRemoveItem(uid,n) -- Removes any item (from the map or player doesn't matter)
  31. doPlayerFeed(uid,food)--Increase the food ticks of a player
  32. doPlayerSendCancel(uid,text)--Send any cancel message to a player
  33. doPlayerSendDefaultCancel(uid,ReturnValue)--Send a cancel message to player
  34. doTeleportThing(uid,newpos)--Teleports something to a position
  35. doTransformItem(uid,toitemid)--Changes the item's id
  36. doPlayerSay(uid,text,type) -- Let's the player say any text
  37. doSendMagicEffect(position,type)--Show a magic effect at a position
  38. doChangeTypeItem(uid,new_type)--Change the type/count of an item
  39. doSetItemActionId(uid,actionid)--Set the item's action id
  40. doSetItemText(uid,text) -- Set the text of an item if you open it
  41. doSetItemSpecialDescription(uid,desc) -- Set an item's description
  42. doSendAnimatedText(position,text,color)--Show animated text at a position (any text or color)
  43. doPlayerAddSkillTry(cid,skillid,tries)--Add skill tries to a decent skill
  44. doPlayerAddHealth(cid,health)--Add health to a player
  45. doCreatureAddHealth(cid,health)--Add health to a creature
  46. doPlayerAddMana(cid,mana)--Add mana to a player
  47. doPlayerAddSoul(cid,soul)--Add soul points to a player
  48. doPlayerAddItem(cid,itemid,count or type)--Add an item to a player -- returns uid of the created item
  49. doPlayerSendTextMessage(cid,MessageClasses,message)--Send a message to a player
  50. doPlayerMoney(cid,money)--Remove money from a player
  51. doShowTextWindow(cid,maxlen,canWrite)--Show a text dialog which is writable
  52. doShowTextDialog(cid,itemid,text)--Show a text dialog to a player that contains text
  53. doDecayItem(uid)--Start to decay an item
  54. doCreateItem(itemid,type or count,position)--Only working on ground;Returns uid of the created item
  55. doSummonCreature(name, position)--Creates a creature
  56. doMoveCreature(cid, direction)--Move a creature to a decent direction
  57. doPlayerSetMasterPos(cid,pos)--Set the player's temple position
  58. doPlayerSetTown(cid,townid) -- Set the player's town-id
  59. doPlayerSetVocation(cid,voc)--Set the player's vocation
  60. doPlayerRemoveItem(cid,itemid,count) -- Remove an item from a player
  61. doPlayerAddExp(cid,exp) -- Add experience to a player
  62. doSetCreatureLight(cid, lightLevel, lightColor, time) -- Add a new light condtion to a player
  63. isPlayer(cid) -- Check if something is a player
  64. isCreature(cid) -- Check if something is a creature
  65. isContainer(uid)-- Check if something is a container
  66. isMoveable(uid) -- Check if something is moveable
  67. getPlayerByName(name) -- Returns a player if the name matches any player on the server
  68. registerCreature(cid) -- Returns and adds a new creature to the script
  69. getContainerSize(uid) -- Returns the size of a container
  70. getContainerCap(uid) -- Returns the capacity of a container
  71. getContainerItem(uid, slot) -- Check if the slot contains a container
  72. doAddContainerItem(uid, itemid, count or subtype) -- Add an item to a container
  73. getHouseOwner(houseid) -- Returns the owner of a house
  74. getHouseName(houseid) -- Returns the name of a house
  75. getHouseEntry(houseid) -- Return the entry-position of a house
  76. getHouseRent(houseid) -- Returns the rent of a house
  77. getHouseTown(houseid) -- Returns the town-id of a house
  78. getHouseAccessList(houseod, listid) -- Returns the house-id of a house that matches the listid
  79. getHouseByPlayerName(playername) -- Returns the house-id of a house that matches the player's name
  80. setHouseAccessList(houseid, listid, listtext)--Set the accesslist of a door or anything elsein a house
  81. setHouseOwner(houseid, ownername)--Set the owner of a house
  82. getWorldType()--Returns the worldtype (0=no-pvp,1= pvp,2= pvp-enf)
  83. getWorldTime()--Returns the ingame time
  84. getWorldLight()--Returns the light level of the server
  85. getWorldCreatures(type)Returns the amount of creatures (0 players,1 monsters,2 npcs,3 all)
  86. getWorldUpTime()--Returns the uptime of the server
  87. createCombatArea({area},{extArea})--Create a new combat area
  88. createConditionObject(type)--Creates a new condition (condition-type required)
  89. setCombatArea(combat, area)--Set the area of a combat object
  90. setCombatCondition(combat, condition)--Adds a condtion to a combat object
  91. setCombatParam(combat, key, value)--Adds a parameter to a combat objectwith a decent value
  92. setConditionParam(condition, key, value)--Adds a parameter to a condition with a decent value
  93. addDamageCondition(condition, key, rounds, time, value)--Adds a damage value to a condtion
  94. addOutfitCondition(condition, lookTypeEx, lookType, lookHead, lookBody, lookLegs, lookFeet)--Adds a new outfit condtion to a creature
  95. setCombatCallBack(combat, key, function_name)--Set the callback of a combat object
  96. setCombatFormula(combat, type, mina, minb, maxa, maxb)--Set the combat's formula
  97. setConditionFormula(combat, mina, minb, maxa, maxb) -- Set the condition's formula
  98. doCombat(cid, combat, param)--Execute the combat object
  99. createCombatObject()--Creates a new combat object
  100. doAreaCombatHealth(cid, type, pos, area, min, max, effect)--Change any creature's health (area)
  101. doTargetCombatHealth(cid, target, type, min, max, effect) -- Change any creature's health (target)
  102. doAreaCombatMana(cid, pos, area, min, max, effect)--Change any creature's mana (area)
  103. doTargetCombatMana(cid, target, min, max, effect) -- Change any creature's mana (target)
  104. doAreaCombatCondition(cid, pos, area, condition, effect)--Adds a condition (area)
  105. doTargetCombatCondition(cid, target, condition, effect)--Adds a condition (target)
  106. doAreaCombatDispel(cid, pos, area, type, effect)--Removes a condition (area)
  107. doTargetCombatDispel(cid, target, type, effect)--Removes a condition (target)
  108. doChallengeCreature(cid, target)--Challenge a creature
  109. doConvinceCreature(cid, target)--Convince a creature
  110. doChangeSpeed(cid, delta)--Change the creature's speed
  111. doSetMonsterOutfit(cid, name, time) -- Sets the creature's outfit to a monster look
  112. doSetItemOutfit(cid, item, time)--Sets the creature's outfit to an item
  113. doSetCreatureOutfit(cid, outfit, time) -- Sets the creature's outfit (table required)
  114. getCreatureOutfit(cid)--Returns the creature's outfit (in a table)
  115. getCreaturePosition(cid) -- Returns the creature's position (in a table)
  116. getCreatureName(cid)--Returns the name of a creature
  117. isItemStackable(itemid)--Checkif an item is stackable
  118. isItemRune(itemid)--Checkif an item is a rune
  119. isItemDoor(itemid)--Checkif an item is a door
  120. isItemContainer(itemid)--Checkif an item is a container
  121. isItemFluidContainer(itemid)--Checkif an item is a fluid
  122. getItemName(itemid)--Returns the item's name
  123. getPlayerSkull(cid) -- Returns the skull-type of a player
  124. getPlayerConditionTicks(cid, conditionid) -- Returns the ticks of a decent condtion of a player
  125. doPlayerAddAddon(cid, looktype, addon) -- Add an addon to an outfit of the player
  126. getPlayerOutfitAddon(cid, looktype) -- Returns the addon-value of an outfit of a player
  127. getItemStackable(itemid) -- Check if the item is stackabl
 
Actions!

  1. function onUse(cid, item, frompos, item2, topos)

This function is used most of the time. onUse means, if you Use something, something will take place... For example: you use a rune, and you get some health and mana in once.

So this is how we start:
  1. function onUse(cid, item, frompos, item2, topos)

Then, we need to tell the server what is being used. The item is a rune. Now we start with our script.

Let's tell the server that only players higher then level 150, and have atleast magiclevel 30 and players with the sorcerer vocation can use the rune. Search in the list... here it is:
-getPlayerLevel(cid)
-getPlayerMagLevel(cid)
-getPlayerVocation(cid)

If you look good, you see (cid) on the end. cid is just the player. (creatureID) Don't change it! Unless you know what you're doing.
Otherwise you'll get an error saying: "Player not found."We got something new here. >= and ==, what does it mean?




    • < 50 -- lower level then 50.
    • > 50 then -- higher level then 50.
    • <= 50 then -- lower or the same level as 50.
    • >= 50 then -- higher level or same level as 50
    • ~= 50 then -- if the Player doesn't have level 50.
    • == 50 then -- only if the Player has level 50 exactly.
This is how to put it in the script:




    • function onUse(cid, item, frompos, item2, topos)
    • if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
This tells the server that if the player is level 150 or higher and if he got mlvl 30 or higher, and if his vocation is ONLY 1(sorcerer) and he uses the rune, something will take place, but what?
Oh right, we wanted an Health and Mana rune in one, so what does it do? It adds health and mana. Search in the list... here it is:
-doPlayerAddHealth(cid, health)
-doPlayerAddMana(cid, mana)

Then we put it in our script:




    • function onUse(cid, item, frompos, item2, topos)
    • if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
    • doPlayerAddHealth(cid,250)
    • doPlayerAddMana(cid,500)
This means that the player will get 250 health and 500 mana. Ok this is done.
Now we want ofcourse that there will be a magical effect, and that the player will say something. Remember that the player will say two things, that he got mana AND hp. Search in the list... here it is:
-doPlayerSay(cid,text,type)
-doPlayerSay(cid,text,type)
-doSendMagicEffect(position,type)

But watch out! He got 250 health and mana, two different things! So the script has to have two say commands, each saying how much mana and health. So now we add them to our script:

  1. function onUse(cid, item, frompos, item2, topos)
  2. if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
  3. doPlayerAddHealth(cid,250)
  4. doPlayerAddMana(cid,500)
  5. doPlayerSay(cid,text,type)
  6. doPlayerSay(cid,text,type)
  7. doSendMagicEffect(position,type)

Now what will the player say? Ofcourse how much mana and health he just got. 250 health and 500 mana. The player will say if he gets mana: Aaaaah!!! 500 Mana! and for health: Aaaaah!!! 250 Health!
We put this where the say-command says text. Let's say the type is 16, so: (those types can be found in global.lua)

  1. function onUse(cid, item, frompos, item2, topos)
  2. if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
  3. doPlayerAddHealth(cid,250)
  4. doPlayerAddMana(cid,500)
  5. doPlayerSay(cid,"Aaaaah!!! 500 Mana!",16)
  6. doPlayerSay(cid,"Aaaaah!!! 250 Health!",16)
  7. doSendMagicEffect(position,type)

Now we have to work on the MagicEffect. Where it says position, put getPlayerPosition(cid). You thought we have to put real coordinates, didin't you? But that ain't gonna work, and I'll tell you why:
if you put coordinates, that means that the magic effect will take place only at that specific coordinate. But I know for SURE your server has more then one coordinate to walk on, so if you want to put coordinates, you have to put all walkable coordinates in your server, like .. i don't know... 10000? Way more
tongue.png

So if you put getPlayerPosition(cid), it means the magic effect takes place wherever the player is standing.
Ok and the type of the magiceffect is 1, so:

  1. function onUse(cid, item, frompos, item2, topos)
  2. if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
  3. doPlayerAddHealth(cid,250)
  4. doPlayerAddMana(cid,500)
  5. doPlayerSay(cid,"Aaaaah!!! 500 Mana!",16)
  6. doPlayerSay(cid,"Aaaaah!!! 250 Health!",16)
  7. doSendMagicEffect(getPlayerPosition(cid),1)

If you understood it so far, well done! You'll be able to make a proper script in no-time!
tongue.png


Ok, we have more to do, so don't sit back.

Smart people think forward. What if the player doesn't have level 150, mlvl 30 and is not a sorcerer? Or he doesn't have only 1 of those requirements? We send the player a cancel-message!
This is the command to do that:
-doPlayerSendCancel(cid,text)

Now we just put as the text: You don't have to required skills or vocation to use this rune.
So:

  1. function onUse(cid, item, frompos, item2, topos)
  2. if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
  3. doPlayerAddHealth(cid,250)
  4. doPlayerAddMana(cid,500)
  5. doPlayerSay(cid,"Aaaaah!!! 500 Mana!",16)
  6. doPlayerSay(cid,"Aaaaah!!! 250 Health!",16)
  7. doSendMagicEffect(getPlayerPosition(cid),1)
  8. else
  9. doPlayerSendCancel(cid,"You don't have to required skills or vocation to use this rune.")
 
In this part of the script, you saw else. That means, if the player doesn't have the required skills or vocation, which you can see at the first line of the script, he will get a cancel. Now most of the time, you get a kind of white effect if you can't use something. The type of that magiceffect is 2. So we add it before the cancel-command:

  1. function onUse(cid, item, frompos, item2, topos)
  2. if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
  3. doPlayerAddHealth(cid,250)
  4. doPlayerAddMana(cid,500)
  5. doPlayerSay(cid,"Aaaaah!!! 500 Mana!",16)
  6. doPlayerSay(cid,"Aaaaah!!! 250 Health!",16)
  7. doSendMagicEffect(getPlayerPosition(cid),1)
  8. else
  9. doSendMagicEffect(getPlayerPosition(cid),2)
  10. doPlayerSendCancel(cid,"You don't have the required skills or vocation to use this rune.")

Here I added getPlayerPosition(cid) again, because the player gets another magic-effect.

Now the "end"s. Every "if" and "function" in your script, has to be ended. So we put one end for the "if" under that whole nice script of us
tongue.png


  1. function onUse(cid, item, frompos, item2, topos)
  2. if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
  3. doPlayerAddHealth(cid,250)
  4. doPlayerAddMana(cid,500)
  5. doPlayerSay(cid,"Aaaaah!!! 500 Mana!",16)
  6. doPlayerSay(cid,"Aaaaah!!! 250 Health!",16)
  7. doSendMagicEffect(getPlayerPosition(cid),1)
  8. else
  9. doSendMagicEffect(getPlayerPosition(cid),2)
  10. doPlayerSendCancel(cid,"You don't have the required skills or vocation to use this rune.")
  11. end

Ok, one more thing to do.
We want that the rune is usable more then once, so we put return TRUE after end, and end the "function" with an other end as stated above also has to be ended... understood?
tongue.png

Here is our final script:

  1. function onUse(cid, item, frompos, item2, topos)
  2. if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
  3. doPlayerAddHealth(cid,250)
  4. doPlayerAddMana(cid,500)
  5. doPlayerSay(cid,"Aaaaah!!! 500 Mana!",16)
  6. doPlayerSay(cid,"Aaaaah!!! 250 Health!",16)
  7. doSendMagicEffect(getPlayerPosition(cid),1)
  8. else
  9. doSendMagicEffect(getPlayerPosition(cid),2)
  10. doPlayerSendCancel(cid,"You don't have the required skills or vocation to use this rune.")
  11. end
  12. return TRUE
  13. end

So the first end is for the "if" and the second end is for the "function".

OK, now for the advanced scripters here... What about getting random mana and hp?
tongue.png

This is the command to do that:
-math.random(min, max)

For this command, I'll also use the local-command. (If you don't know what this is, leave it and read this script again after you've read the Movements part!)
The script will look like this:
  1. function onUse(cid, item, frompos, item2, topos)
  2. local mana = math.random(150,500)
  3. local hp = math.random(80,250)
  4. if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
  5. doPlayerAddHealth(cid, mana)
  6. doPlayerAddMana(cid, hp)
  7. doPlayerSay(cid,"Aaaaah!!! ".. mana .." Mana!",16)
  8. doPlayerSay(cid,"Aaaaah!!! ".. hp .." Health!",16)
  9. doSendMagicEffect(getPlayerPosition(cid),1)
  10. else
  11. doSendMagicEffect(getPlayerPosition(cid),2)
  12. doPlayerSendCancel(cid,"You don't have the required skills or vocation to use this rune.")
  13. end
  14. return TRUE
  15. end

What I did here, is putting a random number for hp and mana. For hp between 80 and 250, and for mana between 150 and 500. Ok, for the say-command you saw I did something weird: "Aaaaah!!! " .. mana .. " Mana!". Where it says " .. mana .. ", the server will put there automatically the random number. Same for Hitpoints. This command comes in a handy way, like for gambling or something
tongue.png


This is the onUse-function. Hope you liked and of course, learned something
tongue.png
 
You should really use more spaces. Example:
if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
this will error to hell and back because it's going to check if the player's level is greater than or equal to "150and" and even if somehow that didn't break it, the fact that there's nothing then connecting it to the next condition, it'll return an unexpected symbol error in the console, or an expected phrase. If a new scripter copies and pastes this to play around with it, they're gonna be in for a world of double-u tee effs

You should also promote the use of constants. Example:
doSendMagicEffect(getPlayerPosition(cid),2)
Should use the CONST_ME_(effectname) constant rather than just the value it represents (if memory serves correct, 2 is CONST_ME_POFF or something).

"We want that the rune is usable more then once, so we put return TRUE after end"
I'm not sure I follow what you mean with this one. The only thing return true does in this case is prevent you from receiving "you cannot use this object". With return false or no return, the script will still run fully and you'll just receive "you cannot use this object" even though it was used. Regardless of that, the return true has nothing to do with whether or not the item can be used once or again.

As a suggestion, if you're going to go into stuff like randomizing, you may as well go into nested ifs as well, that way the script can check the requirements individually and return a different cancel message depending on what isn't being met. Some people might like that.

It might also be worth briefly explaining the concatenation you did with the local variables, as most people will not know what the double period does in strings or how to use them. You should also explain the local keyword as being a method for creating a local variable, and explain what that is. It might get confusing for a new scripter if you're using things and telling them to use them, but not explaining them. They can't learn what they're doing beyond copying/pasting unless they actually understand what they're copying and pasting.

Just some thoughts for improvement. Otherwise, it's a good tutorial for beginners :D
 
You should really use more spaces. Example:
if getPlayerLevel(cid)>=150and getPlayerMagLevel >=30and getPlayerVocation ==1then
this will error to hell and back because it's going to check if the player's level is greater than or equal to "150and" and even if somehow that didn't break it, the fact that there's nothing then connecting it to the next condition, it'll return an unexpected symbol error in the console, or an expected phrase. If a new scripter copies and pastes this to play around with it, they're gonna be in for a world of double-u tee effs

You should also promote the use of constants. Example:
doSendMagicEffect(getPlayerPosition(cid),2)
Should use the CONST_ME_(effectname) constant rather than just the value it represents (if memory serves correct, 2 is CONST_ME_POFF or something).

"We want that the rune is usable more then once, so we put return TRUE after end"
I'm not sure I follow what you mean with this one. The only thing return true does in this case is prevent you from receiving "you cannot use this object". With return false or no return, the script will still run fully and you'll just receive "you cannot use this object" even though it was used. Regardless of that, the return true has nothing to do with whether or not the item can be used once or again.

As a suggestion, if you're going to go into stuff like randomizing, you may as well go into nested ifs as well, that way the script can check the requirements individually and return a different cancel message depending on what isn't being met. Some people might like that.

It might also be worth briefly explaining the concatenation you did with the local variables, as most people will not know what the double period does in strings or how to use them. You should also explain the local keyword as being a method for creating a local variable, and explain what that is. It might get confusing for a new scripter if you're using things and telling them to use them, but not explaining them. They can't learn what they're doing beyond copying/pasting unless they actually understand what they're copying and pasting.

Just some thoughts for improvement. Otherwise, it's a good tutorial for beginners :D
the copy / paste of my text was wrong i was can't paste all here so i just copy and i don't looking for it when i paste :)
>Fixed the bugs i see in our thread<
 
Last edited:
Talkactions!

  1. function onSay(cid, words, param)

Ok, for this function I'm going to, just like the action one, make step by step a nice, working sript.
Action means, if a player uses something... something will happen.
Talkactions means: if a player says something... something will happen.

What shall we make this time??? Hmmm.....
[think]...[/think] I got it!
What about a script, if you say something, you'll get an item, and money from your backpack will be removed.
But which item??? Hmmm.....
[think]...[/think] An amulet of loss! People use it many times, so this command will make it faster for them to get one.

Ok here we go...!

The beginning:

  1. function onSay(cid, words, param)

In order to get the aol, the player has to give money. To do that, we use this command:
-doPlayerRemoveMoney(cid,count)

We have to change this command a bit, so the player has to give 15k, or: 15.000 gold, so:
(NOTE THAT YOU CAN'T PUT 15K INSTEAD OF 15000! ALWAYS IN GOLD COINS!)

  1. function onSay(cid, words, param)
  2. if doPlayerRemoveMoney(cid,15000)== TRUE then

Did you see I put if before the command? It just says, if the player gives 15000 gp... then something will happen.
Also, I put == TRUE after the command. That is so the server checks if it's true which means, if the player really gives money... if I put FALSE, then the player can get as many aols as he want, because they're for free then
tongue.png


Then, we want the player to get an amulet of loss.. the itemID if an aol is 2173. To give the player an item, use this command:
-doPlayerAddItem(cid,itemid,count or type)

Now we have to change the command a bit before we add it to our script. The itemid is 2173, and the count? Only 1 right.. so:
-doPlayerAddItem(cid,2173,1)

In our script:

  1. function onSay(cid, words, param)
  2. if doPlayerRemoveMoney(cid,15000)==1then
  3. doPlayerAddItem(cid,2173,1)

Now we can end the script by placing an "end" at the end, but this one would be really boring. Why won't we send a text to the player, a magic effect and put a cancel if the player doesn't have enough money? That would me more awesome.
biggrin.png

To send a magic effect, you'll need this command:
-doSendMagicEffect(position,type)

Now we get to something new. Where it says position, we have to put the player's position. But were not going to place like 1000000 coordinates... We have a special command for that:
-getPlayerPosition(cid)

With this command, it doesn't matter where the player is standing, it'll always work. So we have to put this command into the other, where it says position:
-doSendMagicEffect(getPlayerPosition(cid),type)

Now there is one thing left, the type. ALL the types can be found in global.lua. Let's take type 12 (uh type). So it's going to be:
-doSendMagicEffect(getPlayerPosition(cid),12)

If we put this on our script:

  1. function onSay(cid, words, param)
  2. if doPlayerRemoveMoney(cid,15000)==1then
  3. doPlayerAddItem(cid,2173,1)
  4. doSendMagicEffect(getPlayerPosition(cid),12)

Now there are two things left: the text, and the cancel. We'll begin with the text. To send the player a text, use this command:
-doPlayerSendTextMessage(cid,MessageClasses,message)

Where it says MessageClasses, we have to put a number. I looked into global.lua, and I saw number 22. That will do the job.
And ofcourse, the message: "You've bought an Amulet of Loss!"
So it's going to be:
-doPlayerSendTextMessage(cid,22,"You've bought an Amulet of Loss!")

In our script:

  1. function onSay(cid, words, param)
  2. if doPlayerRemoveMoney(cid,15000)==1then
  3. doPlayerAddItem(cid,2173,1)
  4. doSendMagicEffect(getPlayerPosition(cid),12)
  5. doPlayerSendTextMessage(cid,22,"You've bought an Amulet of Loss!")

Now for the last thing: if the player doesn't have the money, we send him a cancel with this command:
-doPlayerSendCancel(cid,text)

Let's put in text: "You don't have enough money."

So:
-doPlayerSendCancel(cid,"You don't have enough money.")

I just thought, why not send also a magic-effect if the player gets a cancel? You know that kinda white flash...? It's magiceffect is 2, so:
-doSendMagicEffect(getPlayerPosition(cid),2)

In our script:

  1. function onSay(cid, words, param)
  2. if doPlayerRemoveMoney(cid,15000)==1then
  3. doPlayerAddItem(cid,2173,1)
  4. doSendMagicEffect(getPlayerPosition(cid),12)
  5. doPlayerSendTextMessage(cid,22,"You've bought an Amulet of Loss!")
  6. else--if the player doesn't have enough money...
  7. doPlayerSendCancel(cid,"You don't have enough money.")
  8. doSendMagicEffect(getPlayerPosition(cid),2)

Now did you notice that else? It means, if the player doesn't have the requirements which are shown in the beginning of the script, he gets a cancel-message. In scripting language: else, doPlayerSendCancel(...)

Don't forget to put "end" at the end of every if! This is our final script:

  1. function onSay(cid, words, param)
  2. if doPlayerRemoveMoney(cid,15000)==1then
  3. doPlayerAddItem(cid,2173,1)
  4. doSendMagicEffect(getPlayerPosition(cid),12)
  5. doPlayerSendTextMessage(cid,22,"You've bought an Amulet of Loss!")
  6. else
  7. doPlayerSendCancel(cid,"You don't have enough money.")
  8. doSendMagicEffect(getPlayerPosition(cid),2)
  9. end
  10. return TRUE
  11. end

You can do everything with talkactions. Like, say something on a special tile, and you get teleported to another place. Or, you say something, and a wall will be removed.
It's quite fun
tongue.png
 
There are numerous of tutorials for the legacy scripting system.
Do tutorials for the 1.x series and how they should handle userdatas in addEvent functions etc insted.
 
There are numerous of tutorials for the legacy scripting system.
Do tutorials for the 1.x series and how they should handle userdatas in addEvent functions etc insted.

i'll add soon :)
 
A good tutorial for beginners, well done

What tfs version you used as base to do the tutorial?

PD. I'm sure some arguments are incomplets depending of TFS version, well you got the most common

  • function onUse(cid, item, fromPosition, itemEx, toPosition)
  • function onSay(cid, words, param)
  • function onEquip(cid, item, slot)
  • function onAddItem(moveitem, tileitem, position)
  • function onDeEquip(cid, item, slot)
  • function onStepIn(cid, item, frompos, item2, topos)
  • function onStepOut(cid, item, frompos, item2, topos)
 
Back
Top