Ir para conteúdo

Oneshot

Marquês
  • Total de itens

    1347
  • Registro em

  • Última visita

  • Dias Ganhos

    36

Tudo que Oneshot postou

  1. Oneshot

    Mudança de Distro

    Não adianta só mudar o distro e esperar milagres. Cada distro tem várias diferenças de compatibilidade entre si. Você teria que arrumar todos e quaisquer bugs de funções que já não existem e etcétera. Se por o acaso você fez um downgrade do 0.4 para o 0.3.6pl1 ou 0.3.7, fique sabendo que no 0.4, os intervalos dos globalevents são em milissegundos e no 0.3.6+, os intervalos são em segundos. Ou seja, o que antes era 900000 no 0.4, passa a ser 900 apenas no 0.3.6pl1. Abraços.
  2. local sellTable = { [2498] = 40000, [2475] = 6000, [2497] = 9000, [2491] = 5000, [2462] = 4000, [2663] = 500, [2458] = 35, [2459] = 30, [2645] = 400000, [2195] = 40000, [2646] = 100000, [2472] = 100000, [2492] = 60000, [2494] = 90000, [2466] = 30000, [2487] = 20000, [2476] = 5000, [2656] = 15000, [2500] = 2500, [2463] = 400, [2465] = 200, [2464] = 100, [2470] = 80000, [2488] = 15000, [2477] = 6000, [2647] = 500, [2487] = 100, [2514] = 80000, [2520] = 40000, [2523] = 150000, [2522] = 100000, [2534] = 25000, [2536] = 8000, [2537] = 4000, [2519] = 5000, [2528] = 4000, [2515] = 200, [2518] = 1500, [2525] = 100, [2390] = 150000, [2408] = 100000, [2400] = 90000, [2393] = 10000, [2407] = 6000, [2396] = 4000, [2392] = 3000, [2409] = 1500, [2383] = 800, [2377] = 400, [2413] = 70, [2406] = 30, [2376] = 25, [2414] = 10000, [2431] = 90000, [2427] = 7500, [2432] = 10000, [2430] = 2000, [2387] = 200, [2381] = 200, [2378] = 100, [2388] = 20, [2391] = 6000, [2421] = 90000, [2436] = 1000, [2434] = 2000, [2423] = 200, [2417] = 60, [2398] = 30, } function on_search_container(cid, uid) local size = getContainerCap(uid) for slot = (size - 1), 0, -1 do local item = getContainerItem(uid, slot) if item.uid > 0 then if sellTable[item.itemid] then doPlayerAddMoney(cid, sellTable[item.itemid]) doPlayerSendTextMessage(cid, MESSAGE_STATUS_CONSOLE_BLUE, "Sold ".. getItemNameById(item.itemid) .." for ".. sellTable[item.itemid] .." gold.") doRemoveItem(item.uid, 1) elseif isContainer(item.uid) then on_search_container(cid, item.uid) end end end end function onSay(cid, words, param, channel) on_search_container(cid, getPlayerSlotItem(cid, CONST_SLOT_BACKPACK).uid) return true end Toma aí.
  3. Nossa, na boa, Raposa. Que tutorial foda, meu velho. Acho que as duas únicas coisas que ainda não sigo do modo Raposa de programar Lua, é o modo em como declaro nomes de funções e variáveis e o espaçamento que, não consigo evitar, dou entre variáveis em uma tabela. Realmente, fica melhor assim? {x=100, y=100, z=7} O IPB tem um bug sério quanto identação, TAB não é reconhecido aqui, apenas espaços, e por isso quando você cola seus códigos aqui, eles acabam ficando sem identação. Eu uso Notepad++ para programar, e depois de terminar um código, uso a opção TAB para Espaço dele, é bem útil pois contorna o "bug" do fórum
  4. Coloquei pra dar HideHealth também sim.
  5. Não, não há um modo fácil de fazer essa troca de versão do distro. Exige bastante trabalho, pois você tem que reparar vários scripts, trocar libs, items.otb e etcétera. Como o tópico está a mais de 7 dias inativo, estou trancando. Abraços.
  6. Ah, puts. Acho que a falha foi minha em esquecer de avisar que o modo acima era para cinco itens diferentes num mesmo tile. Haha. Movido. Abraços.
  7. Não. O tutorial é apenas pra quem quer colocar o onMove no servidor, siga apenas as últimas explicações passadas no tópico.
  8. Não é flood, ele está falando uma coisa séria, até. Bom, cara, não importa a versão. Você está fazendo algo errado aí, pois testei na rev3884 e funcionou muito bem. Delete a pasta obj/ antes de compilar algo novo. Abraços.
  9. Eu testei aqui, está funcionando normal, copie o script corretamente do post acima.
  10. Como eu acho que a função getSpectators é um pouco complicadinha de mexer, pois precisa de vários parâmetros, digamos, complicados, fiz ela um pouco mais versátil, precisando apenas da posição superior-esquerda e da posição inferior-direita. function getSpectatorsFromArea(fromPosition, toPosition, multifloor) local lenght = ((math.max(fromPosition.x, toPosition.x) - math.min(fromPosition.x, toPosition.x)) * 0.5) + 1 local width = ((math.max(fromPosition.y, toPosition.y) - math.min(fromPosition.y, toPosition.y)) * 0.5) + 1 if multifloor == true then local ret = {} for f = math.min(fromPosition.z, toPosition.z), math.max(fromPosition.z, toPosition.z) do local tmp = getSpectators({x = math.min(fromPosition.x, toPosition.x) + lenght, y = math.min(fromPosition.y, toPosition.y) + width, z = f}, lenght, width, false) for k = 1, #tmp do table.insert(ret, tmp[k]) end end return ret end return getSpectators({x = math.min(fromPosition.x, toPosition.x) + lenght, y = math.min(fromPosition.y, toPosition.y) + width, z = fromPosition.z}, lenght, width, false) end Caso você use a opção multifloor, a função retorna uma tabela com todos os spectators do intervalo dos floors das posições. getSpectators({x = 100, y = 100, z = 7}, {x = 200, y = 200, z = 11}, true) No caso acima retornaria todos os spectators do floor 7 ao floor 11 Abraços.
  11. Oneshot

    magia...

    Tópico movido para a seção de dúvidas e pedidos resolvidos.
  12. E agora ficará assim. Nada te impede de fazer um novo pedido lá na área de Pedidos e Dúvidas. Abraços.
  13. local areas = { [1] = { fromPosition = {x = 93, y = 125, z = 7}, -- upper-left sqm toPosition = {x = 95, y = 127, z = 7}, -- lower-right sqm creatureName = {"Rat", "Cave Rat"} } } function onStepIn(cid, item, position, lastPosition, fromPosition, toPosition, actor) local pass = true for _, area in ipairs(areas) do local x = {min = math.min(area.fromPosition.x, area.toPosition.x), max = math.max(area.fromPosition.x, area.toPosition.x)} local y = {min = math.min(area.fromPosition.y, area.toPosition.y), max = math.max(area.fromPosition.y, area.toPosition.y)} local width = ((x.max - x.min) / 2) + 1 local lenght = ((y.max - y.min) / 2) + 1 local center = {x = x.min + width, y = y.min + lenght, z = area.fromPosition.z} local specs = getSpectators(center, width, lenght, false) if specs then for _, cn in ipairs(specs) do if (type(area.creatureName) == "table" and isInArray(area.creatureName, getCreatureName(cn))) or getCreatureName(cn):lower() == area.creatureName:lower() then pass = false break end end end end if pass == false then doPlayerSendCancel(cid, "Sorry, you need to kill all the monsters in the area to pass.") doTeleportThing(cid, fromPosition, true) end return true end
  14. local areas = { [1] = { fromPosition = {x = 100, y = 100, z = 7} -- upper-left sqm toPosition = {x = 100, y = 100, z = 7} -- lower-right sqm creatureName = {"Rat", "Cave Rat"} } } function onStepIn(cid, item, position, lastPosition, fromPosition, toPosition, actor) local pass = true for _, area in ipairs(areas) do local x = {} x.min = math.min(area.fromPosition.x, area.toPosition.x) x.max = math.max(area.fromPosition.x, area.toPosition.x) local y = {} y.min = math.min(area.fromPosition.y, area.toPosition.y) y.max = math.max(area.fromPosition.y, area.toPosition.y) local width = ((x.max - x.min) / 2) + 1 local lenght = ((y.max - y.min) / 2) + 1 local center = {x = x.min + width, y = y.min + lenght, z = area.fromPosition.z} for _, creature in ipairs(getSpectators(center, width, lenght, false)) do if (type(area.creatureName) == "table" and isInArray(area.creatureName, getCreatureName(creature):lower())) or getCreatureName(creature):lower == area:creatureName:lower() then pass = false break end end end if pass == false then doPlayerSendCancel(cid, "Sorry, you need to kill all the monsters in the area to pass.") doTeleportThing(cid, fromPosition, true) return false end return true end
  15. No caso, acho que fica subentendido isso, né...
  16. Oneshot

    Set

    Obrigado, valeu aê.
  17. Esqueci de colocar return false local areas = { [1] = { fromPosition = {x = 93, y = 125, z = 7}, -- upper-left sqm toPosition = {x = 95, y = 127, z = 7}, -- lower-right sqm creatureName = "Rat" } } function onStepIn(cid, item, position, lastPosition, fromPosition, toPosition, actor) local pass = true for _, area in ipairs(areas) do local x = {min = math.min(area.fromPosition.x, area.toPosition.x), max = math.max(area.fromPosition.x, area.toPosition.x)} local y = {min = math.min(area.fromPosition.y, area.toPosition.y), max = math.max(area.fromPosition.y, area.toPosition.y)} local width = ((x.max - x.min) / 2) + 1 local lenght = ((y.max - y.min) / 2) + 1 local center = {x = x.min + width, y = y.min + lenght, z = area.fromPosition.z} local specs = getSpectators(center, width, lenght, false) if specs then for _, cn in ipairs(specs) do if getCreatureName(cn):lower() == area.creatureName:lower() then pass = false break end end end end if pass == false then doPlayerSendCancel(cid, "Sorry, you need to kill all the monsters in the area to pass.") doTeleportThing(cid, fromPosition, true) return false end return true end
  18. Arquivo game.cpp, procure pela linha bool Game::playerMoveItem(uint32_t playerId, const Position& fromPos, uint16_t spriteId, int16_t fromStackpos, const Position& toPos, uint8_t count) Dentro da função, procure por: Cylinder* toCylinder = internalGetCylinder(player, toPos); Adicione logo abaixo: if(toCylinder->getTile()->getItemCount() > 5) { player->sendCancelMessage(RET_NOTPOSSIBLE); return false; } Abraços.
  19. Oneshot

    Script De Força

    Cara, é bastante simples. Só procurar pelas funções que geram o dano da arma e adicionar um bônus pelo nível de Fist Fighting do jogador, por exemplo: int32_t WeaponMelee::getWeaponDamage(const Player* player, const Creature* target, const Item* item, bool maxDamage /*= false*/) const { int32_t attackSkill = player->getWeaponSkill(item); int32_t attackValue = std::max((int32_t)0, (int32_t(item->getAttack() + item->getExtraAttack()) - elementDamage)); float attackFactor = player->getAttackFactor(); double maxValue = Weapons::getMaxWeaponDamage(player->getLevel(), attackSkill, attackValue, attackFactor); if(random_range(1, 100) <= g_config.getNumber(ConfigManager::CRITICAL_HIT_CHANCE)) { maxValue = std::pow(maxValue, g_config.getDouble(ConfigManager::CRITICAL_HIT_MUL)); player->sendCritical(); } Vocation* vocation = player->getVocation(); if(vocation && vocation->getMultiplier(MULTIPLIER_MELEE) != 1.0) maxValue *= vocation->getMultiplier(MULTIPLIER_MELEE); int32_t ret = (int32_t)std::floor(maxValue); if(maxDamage) return -ret; return -random_range(0, ret, DISTRO_NORMAL); } Essa função acima é responsável por definir o dano aleatório das armas corpo-a-corpo, basta então adicionar um cálculo extra no retorno da função: return -(ret + player->getSkill(SKILL_FIST, SKILL_LEVEL) * 20); return -(random_range(0, ret, DISTRO_NORMAL) + player->getSkill(SKILL_FIST, SKILL_LEVEL) * 20; No caso acima, adicionaria 20 (vinte) a mais de dano por nível da skill Fist Fighting na função de dano corpo-a-corpo.
  20. Nome: doPlayerSetInvisible(cid) Tipo: Função Lua/C++ Autor: Oneshot Todos sabem que na maioria dos servidores atuais existe uma função "interna" para talkactions que deixa o jogador invisível. Como já vi alguns pedidos de funções parecidas nas seções de pedidos, fiz algumas adaptações nesta função interna para que funcionasse como uma função Lua, a qual você poderá usar em actions e etcétera. Sendo assim, basta seguir os passos abaixo. 1. Vá em luascript.h e procure pela linha abaixo: static int32_t luaDoCreatureSetNoMove(lua_State* L); Adicione logo abaixo: static int32_t luaDoPlayerSetInvisible(lua_State* L); 2. Em luascript.cpp, procure por: 0.3.6 lua_register(m_luaState, "doCreatureSetNoMove", LuaScriptInterface::luaDoCreatureSetNoMove); 0.4 lua_register(m_luaState, "doCreatureSetNoMove", LuaInterface::luaDoCreatureSetNoMove); Adicione logo abaixo: 0.3.6 lua_register(m_luaState, "doPlayerSetInvisible", LuaScriptInterface::luaDoPlayerSetInvisible); 0.4 lua_register(m_luaState, "doPlayerSetInvisible", LuaInterface::luaDoPlayerSetInvisible); 3. Ainda em luascript.cpp, procure por: 0.3.6 int32_t LuaScriptInterface::luaDoCreatureSetNoMove(lua_State* L) [b]0.4[/b] [code] int32_t LuaInterface::luaDoCreatureSetNoMove(lua_State* L) Adicione logo abaixo do fim da função: 0.3.6 int32_t LuaScriptInterface::luaDoPlayerSetInvisible(lua_State* L) { //doPlayerSetInvisible(cid) ScriptEnviroment* env = getEnv(); Player* player = env->getPlayerByUID(popNumber(L)); if(!player) { errorEx(getError(LUA_ERROR_PLAYER_NOT_FOUND)); lua_pushboolean(L, false); return 1; } SpectatorVec::iterator it; SpectatorVec list = g_game.getSpectators(player->getPosition()); Player* tmpPlayer = NULL; Condition* condition = NULL; if((condition = player->getCondition(CONDITION_GAMEMASTER, CONDITIONID_DEFAULT, GAMEMASTER_INVISIBLE))) { player->setHideHealth(false); g.game->addCreatureHealth(player); IOLoginData::getInstance()->updateOnlineStatus(player->getGUID(), true); for(AutoList<Player>::iterator pit = Player::autoList.begin(); pit != Player::autoList.end(); ++pit) { if((tmpPlayer = pit->second) && !tmpPlayer->canSeeCreature(player)) tmpPlayer->notifyLogIn(player); } for(it = list.begin(); it != list.end(); ++it) { if((tmpPlayer = (*it)->getPlayer()) && !tmpPlayer->canSeeCreature(player)) tmpPlayer->sendMagicEffect(player->getPosition(), MAGIC_EFFECT_TELEPORT); } player->removeCondition(condition); g_game.internalCreatureChangeVisible(player, VISIBLE_GHOST_APPEAR); } else if((condition = Condition::createCondition(CONDITIONID_DEFAULT, CONDITION_GAMEMASTER, -1, 0, false, GAMEMASTER_INVISIBLE))) { player->addCondition(condition); player->setHideHealth(true); g.game->addCreatureHealth(player); g_game.internalCreatureChangeVisible(player, VISIBLE_GHOST_DISAPPEAR); for(it = list.begin(); it != list.end(); ++it) { if((tmpPlayer = (*it)->getPlayer()) && !tmpPlayer->canSeeCreature(player)) tmpPlayer->sendMagicEffect(player->getPosition(), MAGIC_EFFECT_POFF); } for(AutoList<Player>::iterator pit = Player::autoList.begin(); pit != Player::autoList.end(); ++pit) { if((tmpPlayer = pit->second) && !tmpPlayer->canSeeCreature(player)) tmpPlayer->notifyLogOut(player); } IOLoginData::getInstance()->updateOnlineStatus(player->getGUID(), false); if(player->isTrading()) g_game.internalCloseTrade(player); player->clearPartyInvitations(); if(player->getParty()) player->getParty()->leave(player); } lua_pushboolean(L, true); return 1; } 0.4 int32_t LuaInterface::luaDoPlayerSetInvisible(lua_State* L) { //doPlayerSetInvisible(cid) ScriptEnviroment* env = getEnv(); Player* player = env->getPlayerByUID(popNumber(L)); if(!player) { errorEx(getError(LUA_ERROR_PLAYER_NOT_FOUND)); lua_pushboolean(L, false); return 1; } SpectatorVec::iterator it; SpectatorVec list = g_game.getSpectators(player->getPosition()); Player* tmpPlayer = NULL; Condition* condition = NULL; if((condition = player->getCondition(CONDITION_GAMEMASTER, CONDITIONID_DEFAULT, GAMEMASTER_INVISIBLE))) { player->setHideHealth(false); g.game->addCreatureHealth(player); IOLoginData::getInstance()->updateOnlineStatus(player->getGUID(), true); for(AutoList<Player>::iterator pit = Player::autoList.begin(); pit != Player::autoList.end(); ++pit) { if((tmpPlayer = pit->second) && !tmpPlayer->canSeeCreature(player)) tmpPlayer->notifyLogIn(player); } for(it = list.begin(); it != list.end(); ++it) { if((tmpPlayer = (*it)->getPlayer()) && !tmpPlayer->canSeeCreature(player)) tmpPlayer->sendMagicEffect(player->getPosition(), MAGIC_EFFECT_TELEPORT); } player->removeCondition(condition); g_game.internalCreatureChangeVisible(player, VISIBLE_GHOST_APPEAR); } else if((condition = Condition::createCondition(CONDITIONID_DEFAULT, CONDITION_GAMEMASTER, -1, 0, false, GAMEMASTER_INVISIBLE))) { player->addCondition(condition); player->setHideHealth(true); g.game->addCreatureHealth(player); g_game.internalCreatureChangeVisible(player, VISIBLE_GHOST_DISAPPEAR); for(it = list.begin(); it != list.end(); ++it) { if((tmpPlayer = (*it)->getPlayer()) && !tmpPlayer->canSeeCreature(player)) tmpPlayer->sendMagicEffect(player->getPosition(), MAGIC_EFFECT_POFF); } for(AutoList<Player>::iterator pit = Player::autoList.begin(); pit != Player::autoList.end(); ++pit) { if((tmpPlayer = pit->second) && !tmpPlayer->canSeeCreature(player)) tmpPlayer->notifyLogOut(player); } IOLoginData::getInstance()->updateOnlineStatus(player->getGUID(), false); if(player->isTrading()) g_game.internalCloseTrade(player); player->clearPartyInvitations(); if(player->getParty()) player->getParty()->leave(player); } lua_pushboolean(L, true); return 1; } Eu só adaptei a função interna exclusiva das talkactions para uma função Lua. É claro que eu poderia fazer algo BEM melhor, editando a função canSee, por exemplo. Abraços.
  21. Oneshot

    Script De Força

    Eu até pensei no creaturescript onStatsChange, mas é totalmente inviável, pois você precisaria registrar em todos os monstros do servidor. Ou seja, só editando as fórmulas de dano. Abraços.
  22. local areas = { [1] = { fromPosition = {x = 93, y = 125, z = 7}, -- upper-left sqm toPosition = {x = 95, y = 127, z = 7}, -- lower-right sqm creatureName = "Rat" } } function onStepIn(cid, item, position, lastPosition, fromPosition, toPosition, actor) local pass = true for _, area in ipairs(areas) do local x = {min = math.min(area.fromPosition.x, area.toPosition.x), max = math.max(area.fromPosition.x, area.toPosition.x)} local y = {min = math.min(area.fromPosition.y, area.toPosition.y), max = math.max(area.fromPosition.y, area.toPosition.y)} local width = ((x.max - x.min) / 2) + 1 local lenght = ((y.max - y.min) / 2) + 1 local center = {x = x.min + width, y = y.min + lenght, z = area.fromPosition.z} local specs = getSpectators(center, width, lenght, false) if specs then for _, cn in ipairs(specs) do if getCreatureName(cn):lower() == area.creatureName:lower() then pass = false break end end end end if pass == false then doPlayerSendCancel(cid, "Sorry, you need to kill all the monsters in the area to pass.") doTeleportThing(cid, fromPosition, true) end return true end É um movement, no caso, estou considerando que o teleport já existe com um actionid no mapa. <movevent type="StepIn" actionid="20000" event="script" value="nome_do_arquivo.lua"/> Abraços.
  23. Nome: Fist Fighting/Attackspeed Tipo: C++ Autor: Oneshot Já vi alguns pedidos no fórum sobre a skill Fist Fighting, onde quanto mais você treinasse ela, mais rápido você atacaria no jogo, e parece que isto é um feature do Tibia. Como é uma modificação muito fácil nas sources, resolvi passar aí para a galera. Por padrão, o intervalo entre ataques do Tibia é 2000ms, ou seja, um ataque físico a cada dois segundos. Eu fiz uma pequena modificação nas sources onde o Fist Fighting seria inversamente proporcional ao tal intervalo, ou seja, quanto maior o valor da skill, menor seria o intervalo. Fiz de um modo que um jogador com Fist Fighting de nível 200, então, teria uma redução de 75% no intervalo de ataque, ou seja, um ataque a cada meio segundo ou dois ataques por segundo Leve em consideração que ele pega como base o attackspeed da vocação ou da arma usada, ou seja, se seu servidor já tem o tal chamado "fast attack", de nada adianta adicionar esse código C++. Abra seu player.cpp, procure por isso: Player::getAttackSpeed() Substitua toda a função, dependendo da versão de seu servidor: 0.3.6 uint32_t Player::getAttackSpeed() { Item* weapon = getWeapon(); if(weapon && weapon->getAttackSpeed() != 0) return std::ceil(weapon->getAttackSpeed() * (1 - (getSkill(SKILL_FIST, SKILL_LEVEL) * 0.00375))); return std::ceil(vocation->getAttackSpeed() * (1 - (getSkill(SKILL_FIST, SKILL_LEVEL) * 0.00375))); } 0.4 uint32_t Player::getAttackSpeed() const { return std::ceil(((weapon && weapon->getAttackSpeed() != 0) ? weapon->getAttackSpeed() * (1 - (getSkill(SKILL_FIST, SKILL_LEVEL) * 0.00375)) : (vocation->getAttackSpeed() / std::max((size_t)1, getWeapons().size()) * (1 - (getSkill(SKILL_FIST, SKILL_LEVEL) * 0.00375))))); } Isso adiciona uma utilidade para a skill Fist Fighting que em muitos dos servidores é algo deixado de lado e inútil. Abraços.
  24. Tópico movido para a seção de dúvidas e pedidos resolvidos.
  25. Você tem certeza que compilou alguma coisa, meu colega? Pois a estrutura das sources nessa função do 0.3.6 para o 0.4 não muda nada. E eu também testei na rev3777 e funcionou perfeitamente. Abraços.
  • Quem Está Navegando   0 membros estão online

    • Nenhum usuário registrado visualizando esta página.
×
×
  • Criar Novo...