Skip to content
Snippets Groups Projects
Commit 05049fda authored by dg's avatar dg
Browse files

more alchemist

git-svn-id: http://svn.net-core.org/repos/t-engine4@898 51575b47-30f0-44d4-a5cc-537603b46e54
parent 753682b8
No related branches found
No related tags found
No related merge requests found
......@@ -420,6 +420,12 @@ function _M:combatAttackDex(weapon)
return self.combat_atk + self:getTalentLevel(Talents.T_WEAPON_COMBAT) * 5 + (weapon.atk or 0) + (self:getDex(100) - 10) + (self:getLck() - 50) * 0.4
end
--- Gets the attack using only magic
function _M:combatAttackDex(weapon)
weapon = weapon or self.combat
return self.combat_atk + self:getTalentLevel(Talents.T_WEAPON_COMBAT) * 5 + (weapon.atk or 0) + (self:getMag(100) - 10) + (self:getLck() - 50) * 0.4
end
--- Gets the armor penetration
function _M:combatAPR(weapon)
weapon = weapon or self.combat
......
......@@ -81,7 +81,7 @@ newBirthDescriptor{
life_rating = 10,
resolvers.equip{ id=true,
{type="weapon", subtype="staff", name="elm staff", autoreq=true},
{type="armor", subtype="cloth", name="robe", autoreq=true},
{type="armor", subtype="cloth", name="linen robe", autoreq=true},
},
resolvers.inventory{ id=true,
{type="potion", subtype="potion", name="potion of lesser mana", ego_chance=-1000},
......@@ -98,9 +98,9 @@ newBirthDescriptor{
"Alchemists have an empirical knowledge of magic, which they can not use directly but through focuses.",
"A focus is usualy a gem which they can imbue with power to throw at their foes, exploding in fires, acid, ...",
"Alchemists are also known for their golem craft and are usualy accompagnied by such a construct which acts as a body guard.",
"Their most important stats are: Magic and Willpower",
"Their most important stats are: Magic and Dexterity",
},
stats = { mag=5, wil=3, cun=1, },
stats = { mag=5, dex=3, wil=1, },
talents_types = {
["spell/alchemy"]={true, 0.3},
["spell/infusion"]={true, 0.3},
......@@ -108,6 +108,7 @@ newBirthDescriptor{
["spell/advanced-golemancy"]={true, 0.3},
["spell/gemology"]={true, 0.3},
["spell/herbalism"]={true, 0.3},
["spell/staff-combat"]={true, 0.3},
["cunning/survival"]={false, -0.1},
},
talents = {
......@@ -115,14 +116,14 @@ newBirthDescriptor{
[ActorTalents.T_REFIT_GOLEM] = 1,
[ActorTalents.T_THROW_BOMB] = 1,
[ActorTalents.T_FIRE_INFUSION] = 1,
[ActorTalents.T_GOLEM_TAUNT] = 1,
[ActorTalents.T_CHANNEL_STAFF] = 1,
},
copy = {
max_life = 90,
life_rating = 10,
resolvers.equip{ id=true,
{type="weapon", subtype="staff", name="elm staff", autoreq=true},
{type="armor", subtype="cloth", name="robe", autoreq=true}
{type="armor", subtype="cloth", name="linen robe", autoreq=true}
},
resolvers.inventory{ id=true,
{type="gem",},
......@@ -132,8 +133,15 @@ newBirthDescriptor{
{type="potion", subtype="potion", name="potion of lesser mana", ego_chance=-1000},
},
resolvers.generic(function(self)
-- Invoke the golem
local t = self:getTalentFromId(self.T_REFIT_GOLEM)
t.action(self, t)
-- Make and wield some alchemist gems
local t = self:getTalentFromId(self.T_CREATE_ALCHEMIST_GEMS)
local gem = t.make_gem(self, t, "GEM_AGATE")
self:wearObject(gem, true, true)
self:sortInven()
end),
},
}
-- ToME - Tales of Middle-Earth
-- Copyright (C) 2009, 2010 Nicolas Casalini
--
-- This program is free software: you can redistribute it and/or modify
-- it under the terms of the GNU General Public License as published by
-- the Free Software Foundation, either version 3 of the License, or
-- (at your option) any later version.
--
-- This program is distributed in the hope that it will be useful,
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-- GNU General Public License for more details.
--
-- You should have received a copy of the GNU General Public License
-- along with this program. If not, see <http://www.gnu.org/licenses/>.
--
-- Nicolas Casalini "DarkGod"
-- darkgod@te4.org
local nb = 0
return { generator = function()
local radius = radius
local sradius = (radius + 0.5) * (engine.Map.tile_w + engine.Map.tile_h) / 2
local ad = rng.float(0, 360)
local a = math.rad(ad)
local r = rng.float(0, sradius / 2)
local x = r * math.cos(a)
local y = r * math.sin(a)
local bx = math.floor(x / engine.Map.tile_w)
local by = math.floor(y / engine.Map.tile_h)
local static = rng.percent(40)
return {
trail = 1,
life = 10,
size = 3, sizev = 0, sizea = 0,
x = x, xv = 0, xa = 0,
y = y, yv = 0, ya = 0,
dir = a, dirv = 0, dira = 0,
vel = sradius / 2 / 10, velv = 0, vela = 0,
r = rng.range(140, 200)/255, rv = 0, ra = 0,
g = rng.range(180, 220)/255, gv = 0, ga = 0,
b = rng.range(220, 240)/255, bv = 0, ba = 0,
a = rng.range(230, 255)/255, av = 0, aa = 0,
}
end, },
function(self)
if nb < 5 then
self.ps:emit(radius*266)
nb = nb + 1
self.ps:emit(radius*266)
nb = nb + 1
self.ps:emit(radius*266)
nb = nb + 1
self.ps:emit(radius*266)
nb = nb + 1
self.ps:emit(radius*266)
nb = nb + 1
end
end,
5*radius*266
......@@ -60,7 +60,7 @@ return { generator = function()
local r = rng.range(1, f.size)
return {
life = 4,
life = life or 4,
size = f.thick, sizev = 0, sizea = 0,
x = r * math.cos(a) + 3 * math.cos(ra) + f.bx, xv = 0, xa = 0,
......@@ -80,4 +80,4 @@ function(self)
self.ps:emit(230*tiles)
end
end,
4*230*tiles
4*(nb_particles or 230)*tiles
......@@ -104,7 +104,7 @@ newTalent{
print("[Chain lightning] jumping from", sx, sy, "to", actor.x, actor.y)
local dam = self:spellCrit(self:combatTalentSpellDamage(t, 10, 200))
self:project(tgr, actor.x, actor.y, DamageType.LIGHTNING, rng.avg(rng.avg(dam / 3, dam, 3), dam, 5))
game.level.map:particleEmitter(sx, sy, math.max(math.abs(actor.x-sx), math.abs(actor.y-sy)), "lightning", {tx=actor.x-sx, ty=actor.y-sy})
game.level.map:particleEmitter(sx, sy, math.max(math.abs(actor.x-sx), math.abs(actor.y-sy)), "lightning", {tx=actor.x-sx, ty=actor.y-sy, nb_particles=150, life=6})
sx, sy = actor.x, actor.y
end
......
......@@ -26,22 +26,25 @@ newTalent{
return math.ceil(5 + self:getDex(12))
end,
mana = 30,
action = function(self, t)
make_gem = function(self, t, base_define)
local nb = rng.range(40, 80)
local gem = game.zone:makeEntityByName(game.level, "object", "ALCHEMIST_" .. base_define)
self:showEquipInven("Use which gem?", function(o) return o.type == "gem" end, function(o, inven, item)
local gem = game.zone:makeEntityByName(game.level, "object", "ALCHEMIST_" .. o.define_as)
local s = {}
while nb > 0 do
s[#s+1] = gem:clone()
nb = nb - 1
end
for i = 1, #s do gem:stack(s[i]) end
local s = {}
while nb > 0 do
s[#s+1] = gem:clone()
nb = nb - 1
end
for i = 1, #s do gem:stack(s[i]) end
return gem
end,
action = function(self, t)
self:showEquipInven("Use which gem?", function(o) return o.type == "gem" end, function(o, inven, item)
local gem = t.make_gem(self, t, o.define_as)
self:addObject(self.INVEN_INVEN, gem)
self:removeObject(inven, item)
game.logPlayer(self, "You create: %s", gem:getName{do_color=true, do_count=true})
self:removeObject(self.INVEN_INVEN, item)
return true
end)
game:playSoundNear(self, "talents/arcane")
......@@ -59,6 +62,7 @@ newTalent{
require = spells_req1,
points = 5,
mana = 5,
cooldown = 8,
range = function(self, t)
return math.ceil(5 + self:getDex(12))
end,
......@@ -82,8 +86,7 @@ newTalent{
return
end
local tg = {type="ball", range=self:getTalentRange(t), radius=self:getTalentLevelRaw(self.T_EXPLOSION_EXPERT), talent=t}
if tg.radius == 0 then tg.type = "hit" end
local tg = {type="ball", range=self:getTalentRange(t), radius=1+self:getTalentLevelRaw(self.T_EXPLOSION_EXPERT), talent=t}
local x, y = self:getTarget(tg)
if not x or not y then return nil end
......@@ -101,7 +104,20 @@ newTalent{
end)
local _ _, x, y = self:canProject(tg, x, y)
game.level.map:particleEmitter(x, y, tg.radius, particle, {radius=tg.radius, grids=grids, tx=x, ty=y})
-- Lightning ball gets a special treatment to make it look neat
if particle == "ball_lightning" then
local sradius = (tg.radius + 0.5) * (engine.Map.tile_w + engine.Map.tile_h) / 2
local nb_forks = 16
local angle_diff = 360 / nb_forks
for i = 0, nb_forks - 1 do
local a = math.rad(rng.range(0+i*angle_diff,angle_diff+i*angle_diff))
local tx = x + math.floor(math.cos(a) * tg.radius)
local ty = y + math.floor(math.sin(a) * tg.radius)
game.level.map:particleEmitter(x, y, tg.radius, "lightning", {radius=tg.radius, grids=grids, tx=tx-x, ty=ty-y, nb_particles=25, life=8})
end
else
game.level.map:particleEmitter(x, y, tg.radius, particle, {radius=tg.radius, grids=grids, tx=x, ty=y})
end
game:playSoundNear(self, "talents/arcane")
return true
......
......@@ -36,10 +36,13 @@ newTalent{
end
local tg = {type="bolt", range=self:getTalentRange(t), talent=t}
local x, y = self:getTarget(tg)
if not x or not y then return nil end
local dam = self:combatDamage(weapon) * self:combatTalentWeaponDamage(t, 0.4, 1.1)
self:project(tg, x, y, weapon.combat.damtype or DamageType.ARCANE, self:spellCrit(dam), {type="manathrust"})
local x, y, target = self:getTarget(tg)
if not x or not y or not target then return nil end
self.combat_apr = self.combat_apr + 10000
self.combat_atk = self.combat_atk + 10000
local speed, hit = self:attackTargetWith(target, weapon.combat, nil, self:combatTalentWeaponDamage(t, 0.4, 1.1))
self.combat_atk = self.combat_atk - 10000
self.combat_apr = self.combat_apr - 10000
game:playSoundNear(self, "talents/arcane")
return true
end,
......@@ -82,7 +85,7 @@ newTalent{
local power = self:combatTalentSpellDamage(t, 10, 20)
game:playSoundNear(self, "talents/arcane")
return {
dam = self:addTemporaryValue("combat_def", -power / 2),
dam = self:addTemporaryValue("combat_dam", -power / 2),
def = self:addTemporaryValue("combat_def", power),
}
end,
......@@ -92,8 +95,8 @@ newTalent{
return true
end,
info = function(self, t)
return ([[Adopt a defensive posture, reducing your staff attack power by %d and increasing your defense by %d.
The mana restored will increase with the Magic stat]]):format(self:combatTalentSpellDamage(t, 20, 230) / 2, self:combatTalentSpellDamage(t, 20, 230))
return ([[Adopt a defensive posture, reducing your staff attack power by %d and increasing your defense by %d.]]):
format(self:combatTalentSpellDamage(t, 20, 230) / 2, self:combatTalentSpellDamage(t, 20, 230))
end,
}
......@@ -106,7 +109,7 @@ newTalent{
tactical = {
ATTACK = 10,
},
actiion = function(self, t)
action = function(self, t)
local weapon = self:hasStaffWeapon()
if not weapon then
game.logPlayer(self, "You cannot use Stunning Blow without a two-handed weapon!")
......@@ -122,16 +125,15 @@ newTalent{
-- Try to stun !
if hit then
if target:checkHit(self:combatAttackStr(weapon.combat), target:combatPhysicalResist(), 0, 95, 5 - self:getTalentLevel(t) / 2) and target:canBe("stun") then
target:setEffect(target.EFF_STUNNED, 2 + self:getTalentLevel(t), {})
target:setEffect(target.EFF_DAZED, 4 + self:getTalentLevel(t), {})
else
game.logSeen(target, "%s resists the stunning blow!", target.name:capitalize())
game.logSeen(target, "%s resists the dazing blow!", target.name:capitalize())
end
end
return true
end,
info = function(self, t)
return ([[Hit a target for %d%% melee damage and daze it for %d turns.]]):format(
)
return ([[Hit a target for %d%% melee damage and daze it for %d turns.]]):format(100 * self:combatTalentWeaponDamage(t, 1, 1.5), 4 + self:getTalentLevel(t))
end,
}
......@@ -29,6 +29,7 @@ return {
all_lited = true,
persistant = "zone",
no_level_connectivity = true,
no_worldport = true,
ambiant_music = "Hold the Line.ogg",
generator = {
map = {
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment