Bom, este sistema eu fiz faz alguns dias, fiquei com preguiça de postar, tem mais alguns ainda, logo eu posto.
Primeiro, antes de usar o sistema, que é inteiro baseado em um NPC, você precisa importar essa table aqui na sua database do OTServer:
Query SQL:
-- phpMyAdmin SQL Dump-- version 2.11.7
--
-- Servidor: localhost
-- Tempo de Geração: Dez 06, 2008 as 04:39 PM
-- Versão do Servidor: 5.0.51
-- Versão do PHP: 5.2.6
SET SQL_MODE="NO_AUTO_VALUE_ON_ZERO";
--
-- Banco de Dados: `tfs84`
--
-- --------------------------------------------------------
--
-- Estrutura da tabela `merchantsystem`
--
CREATE TABLE IF NOT EXISTS `merchantsystem` (
`id` int(10) NOT NULL auto_increment,
`ownerid` int(10) NOT NULL,
`itemid` int(10) NOT NULL,
`price` int(10) NOT NULL,
`selled` int(10) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_bin AUTO_INCREMENT=9 ;
--
-- Extraindo dados da tabela `merchantsystem`
--
Aqui o script LUA do NPC:
dofile('./config.lua')local offerTime = 10 -- Seconds to offer items
local keywordHandler = KeywordHandler:new()
local npcHandler = NpcHandler:new(keywordHandler)
NpcSystem.parseParameters(npcHandler)
function onCreatureAppear(cid) npcHandler:onCreatureAppear(cid) end
function onCreatureDisappear(cid) npcHandler:onCreatureDisappear(cid) end
function onCreatureSay(cid, type, msg) npcHandler:onCreatureSay(cid, type, msg) end
time = os.clock()
time2 = os.clock()
function onThink()
npcHandler:onThink()
if (time2 + 10) < os.clock() then
selfSay('Come here to buy and sell your items.')
time2 = os.clock()
end
if (time + offerTime) < os.clock() then
time = os.clock()
if sqlType == "mysql" then
env = assert(luasql.mysql())
con = assert(env:connect(mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort))
else -- sqlite
env = assert(luasql.sqlite3())
con = assert(env:connect(sqliteDatabase))
end
local cur = assert(con:execute("SELECT * FROM merchantsystem WHERE selled LIKE 0 ORDER BY itemid ASC,price ASC"))
results = 0
money = 0
row = cur:fetch({}, "a")
totallines = cur:numrows()
local itemrand = math.random(1,totallines)
while results < totallines do
local itemrand2 = math.random(1,totallines)
if (itemrand == itemrand2) then
offerid = row.id
itemid = row.itemid
itemname = getItemName(itemid)
local cur2 = assert(con:execute("SELECT * FROM merchantsystem WHERE selled LIKE 0 AND itemid LIKE "..itemid.." ORDER BY price ASC LIMIT 1"))
row2 = cur2:fetch({}, "a")
itemprice2 = row2.price
if (itemprice2 == row.price) then
broadcastMessage('Merchant NPC: Sell '.. itemname ..' for '.. row.price ..' gold coins.',MESSAGE_EVENT_ADVANCE)
break
end
end
row = cur:fetch(row, "a")
results = results+1
end
end
end
function setMerchantItem(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, playerid, itemid, price)
if sqlType == "mysql" then
env = assert(luasql.mysql())
con = assert(env:connect(mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort))
else -- sqlite
env = assert(luasql.sqlite3())
con = assert(env:connect(sqliteDatabase))
end
textsArray = {}
indextype = 0
assert(con:execute("INSERT INTO merchantsystem VALUES (id,"..playerid..","..itemid..","..price..",0)"))
return TRUE
end
function getMerchantItem(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, itemid)
if sqlType == "mysql" then
env = assert(luasql.mysql())
con = assert(env:connect(mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort))
else -- sqlite
env = assert(luasql.sqlite3())
con = assert(env:connect(sqliteDatabase))
end
local cur = assert(con:execute("SELECT * FROM merchantsystem WHERE itemid LIKE "..itemid.." AND selled LIKE 0 ORDER BY price ASC LIMIT 1"))
row = cur:fetch({}, "a")
return row
end
function buyedMerchantItem(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, offerid)
if sqlType == "mysql" then
env = assert(luasql.mysql())
con = assert(env:connect(mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort))
else -- sqlite
env = assert(luasql.sqlite3())
con = assert(env:connect(sqliteDatabase))
end
textsArray = {}
indextype = 0
local cur = assert(con:execute("UPDATE merchantsystem SET selled=1 WHERE id LIKE "..offerid.." AND selled LIKE 0"))
return TRUE
end
function getNPCMoney(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, playerid)
if sqlType == "mysql" then
env = assert(luasql.mysql())
con = assert(env:connect(mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort))
else -- sqlite
env = assert(luasql.sqlite3())
con = assert(env:connect(sqliteDatabase))
end
textsArray = {}
indextype = 0
local cur = assert(con:execute("SELECT * FROM merchantsystem WHERE ownerid LIKE "..playerid.." AND selled LIKE 1"))
results = 0
money = 0
row = cur:fetch({}, "a")
totallines = cur:numrows()
while results < totallines do
money = money + row.price
row = cur:fetch(row, "a")
results = results+1
end
local cur = assert(con:execute("UPDATE merchantsystem SET selled=2 WHERE ownerid LIKE "..playerid.." AND selled LIKE 1"))
return money
end
function getNPCItem(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, playerid)
if sqlType == "mysql" then
env = assert(luasql.mysql())
con = assert(env:connect(mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort))
else -- sqlite
env = assert(luasql.sqlite3())
con = assert(env:connect(sqliteDatabase))
end
textsArray = {}
indextype = 0
local cur = assert(con:execute("SELECT * FROM merchantsystem WHERE ownerid LIKE "..playerid.." AND selled LIKE 0"))
results = 0
items = {}
row = cur:fetch({}, "a")
totallines = cur:numrows()
while results < totallines do
items[results] = row.itemid
row = cur:fetch(row, "a")
results = results+1
end
local cur = assert(con:execute("UPDATE merchantsystem SET selled=3 WHERE ownerid LIKE "..playerid.." AND selled LIKE 0"))
return items
end
function trim(s)
-- from PiL2 20.4
return (s:gsub("^%s*(.-)%s*$", "%1"))
end
function sellItem(cid, message, keywords, parameters, node)
if(not npcHandler:isFocused(cid)) then
return false
end
msg = string.lower(message)
storages = {}
storages.itemid = 21547
storages.cost = 21548
if (parameters.getitem == TRUE) then
b = string.find(msg, "item:")
itemname = trim(string.sub(msg, 6))
npcHandler:say(itemname, cid)
itemid = getItemIdByName(itemname)
if itemid ~= LUA_ERROR then
setPlayerStorageValue(cid,storages.itemid,itemid)
npcHandler:say('So, for how much gold coins do you want to sell your '.. itemname ..'? (To say the item\'s cost use this format message: "money: Cost Goes Here")', cid)
return TRUE
else
npcHandler:say('Sorry, I didn\'t understand the item\'s name!', cid)
return FALSE
end
elseif (parameters.getmoney == TRUE) then
b, e = string.find(msg, "%d+")
if b == nil or e == nil then
quantity = 1
else
quantity = tonumber(string.sub(msg, b, e))
end
if isNumber(quantity) ~= TRUE then
quantity = 1
end
setPlayerStorageValue(cid,storages.cost,quantity)
itemid = getPlayerStorageValue(cid,storages.itemid)
itemname = getItemName(itemid)
npcHandler:say('Do you want to sell your '..itemname..' for '..quantity..' gold coins? (You will need to pay a fee of 1000 gold coins to me.)', cid)
return TRUE
elseif (parameters.decline == TRUE) then
npcHandler:say('Ok then.', cid)
npcHandler:resetNpc()
return TRUE
elseif (parameters.confirm == TRUE) then
itemid = getPlayerStorageValue(cid,storages.itemid)
itemname = getItemName(itemid)
cost = getPlayerStorageValue(cid,storages.cost)
playerid = getPlayerGUIDByName(getPlayerName(cid))
if(doPlayerTakeItem(cid, itemid, 1) == LUA_NO_ERROR) then
if getPlayerMoney(cid) >= 1000 then
if cost >= 0 then
doPlayerRemoveMoney(cid, 1000)
setMerchantItem(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, playerid, itemid, cost)
npcHandler:say('Right, now you are selling your '.. itemname ..' for '.. cost ..' gold coins. You can \'get back\' it or wait for someone buy. When someone buy, I will get the money and you will need to get it here.', cid)
else
npcHandler:say('You cannot sell an item costing a negative value.', cid)
end
else
npcHandler:say('You don\'t have 1000 gold coins to pay the fee.', cid)
end
else
npcHandler:say('You don\'t have a '.. itemname ..' to sell.', cid)
end
npcHandler:resetNpc()
return TRUE
end
end
function buyItem(cid, message, keywords, parameters, node)
if(not npcHandler:isFocused(cid)) then
return false
end
msg = string.lower(message)
storages = {}
storages.id = 21610
storages.owner = 21611
storages.itemid = 21612
storages.price = 21613
if (parameters.getitem == TRUE) then
b = string.find(msg, "item:")
itemname = trim(string.sub(msg, 6))
itemid = getItemIdByName(itemname)
if itemid ~= LUA_ERROR then
local itemget = getMerchantItem(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, itemid)
if itemget ~= nil then
npcHandler:say('The cheaper '.. itemname ..' that I have costs '.. itemget.price ..' gold coins. Do you want to buy?', cid)
setPlayerStorageValue(cid,storages.id,itemget.id)
setPlayerStorageValue(cid,storages.owner,itemget.ownerid)
setPlayerStorageValue(cid,storages.itemid,itemget.itemid)
setPlayerStorageValue(cid,storages.price,itemget.price)
return TRUE
else
npcHandler:say('Sorry, I don\'t have a '.. itemname ..' to sell you now!', cid)
return FALSE
end
return TRUE
else
npcHandler:say('Sorry, I didn\'t understand the item\'s name!', cid)
return FALSE
end
elseif (parameters.decline == TRUE) then
npcHandler:say('Ok then.', cid)
npcHandler:resetNpc()
return TRUE
elseif (parameters.confirm == TRUE) then
offerid = getPlayerStorageValue(cid,storages.id)
itemprice = getPlayerStorageValue(cid,storages.price)
ownerid = getPlayerStorageValue(cid,storages.owner)
itemid = getPlayerStorageValue(cid,storages.itemid)
itemname = getItemName(itemid)
playerid = getPlayerGUIDByName(getPlayerName(cid))
if getPlayerMoney(cid) >= itemprice then
doPlayerRemoveMoney(cid, itemprice)
doPlayerAddItem(cid,itemid,1)
buyedMerchantItem(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, offerid)
npcHandler:say('Thank you for buying it!', cid)
else
npcHandler:say('You don\'t have enough money to buy it.', cid)
end
npcHandler:resetNpc()
return TRUE
end
end
function getMoneyBack(cid, message, keywords, parameters, node)
if(not npcHandler:isFocused(cid)) then
return false
end
msg = string.lower(message)
if (parameters.confirm == TRUE) then
playerid = getPlayerGUIDByName(getPlayerName(cid))
moneyhave = getNPCMoney(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, playerid)
if (moneyhave > 0) then
doPlayerAddMoney(cid,moneyhave)
npcHandler:say('Ok, take it man.', cid)
else
npcHandler:say('You don\'t have money to get back.', cid)
end
npcHandler:resetNpc()
return TRUE
end
end
function getItemBack(cid, message, keywords, parameters, node)
if(not npcHandler:isFocused(cid)) then
return false
end
msg = string.lower(message)
if (parameters.confirm == TRUE) then
playerid = getPlayerGUIDByName(getPlayerName(cid))
itemshave = getNPCItem(sqlType, mysqlDatabase, mysqlUser, mysqlPass, mysqlHost, mysqlPort, sqliteDatabase, playerid)
if (itemshave[0] ~= nil) then
for k,v in pairs(itemshave) do
doPlayerAddItem(cid,v,1)
end
npcHandler:say('Ok, take it man.', cid)
else
npcHandler:say('You don\'t have items to get back.', cid)
end
npcHandler:resetNpc()
return TRUE
end
end
local getItemNode = KeywordNode:new({'item:'}, sellItem, {getitem = TRUE})
local getMoneyNode = KeywordNode:new({'money: '}, sellItem, {getmoney = TRUE})
local noSellNode = KeywordNode:new({'no'}, sellItem, {decline = TRUE})
local yesSellNode = KeywordNode:new({'yes'}, sellItem, {confirm = TRUE})
local sellnode = keywordHandler:addKeyword({'sell item'}, StdModule.say, {npcHandler = npcHandler, onlyFocus = true, text = 'What is the name of the item which you want to sell? (To say the item\'s name use this format message: "item: Item Name Goes Here")'})
local getItem = sellnode:addChildKeywordNode(getItemNode)
local getMoney = getItem:addChildKeywordNode(getMoneyNode)
getMoney:addChildKeywordNode(yesSellNode)
getMoney:addChildKeywordNode(noSellNode)
local getItemNode = KeywordNode:new({'item:'}, buyItem, {getitem = TRUE})
local noBuyNode = KeywordNode:new({'no'}, buyItem, {decline = TRUE})
local yesBuyNode = KeywordNode:new({'yes'}, buyItem, {confirm = TRUE})
local buynode = keywordHandler:addKeyword({'buy item'}, StdModule.say, {npcHandler = npcHandler, onlyFocus = true, text = 'What is the name of the item which you want to buy? (To say the item\'s name use this format message: "item: Item Name Goes Here")'})
local getItem = buynode:addChildKeywordNode(getItemNode)
getItem:addChildKeywordNode(yesBuyNode)
getItem:addChildKeywordNode(noBuyNode)
keywordHandler:addKeyword({'get money'}, getMoneyBack, {confirm = TRUE})
keywordHandler:addKeyword({'getback item'}, getItemBack, {confirm = TRUE})
npcHandler:addModule(FocusModule:new())
Arquivo XML:
<npc name="Merchant" script="data/npc/scripts/merchant.lua" access="5" lookdir="1"><health now="1000" max="1000"/>
<look type="133" head="0" body="86" legs="0" feet="38" addons="1"/>
<parameters>
<parameter key="message_greet" value="Hello |PLAYERNAME|. I am a items' re-seller. You can 'sell item', 'buy item', 'getback item' and 'get money'."/>
</parameters>
</npc>
Edite em negrito para o arquivo LUA do NPC.
Exemplo de Uso (Conversa):
Vendendo Item:
hisell item
item: dragon shield
money: 5000
yes
bye
Comprando Item:
hibuy item
item: dragon shield
yes
bye
Retirando items e money:
higetback item
bye
hi
get money
bye
Screenshoots:
Espero que usem, obrigado.
Yunie.