diff --git a/game/engines/default/engine/interface/ActorTalents.lua b/game/engines/default/engine/interface/ActorTalents.lua
index e85496bea6ac1c32bfcd89ac0632e25c1d1aea4e..716436a0425be75f836fa1453bb917cee66f5a81 100644
--- a/game/engines/default/engine/interface/ActorTalents.lua
+++ b/game/engines/default/engine/interface/ActorTalents.lua
@@ -727,6 +727,11 @@ function _M:canLearnTalent(t, offset, ignore_special)
 				end
 			end
 		end
+		if req.birth_descriptors then
+			for _, d in ipairs(req.birth_descriptors) do
+				if not self.descriptor or self.descriptor[d[1]] ~= d[2] then return nil, ("is not %s"):format(d[2]) end
+			end
+		end
 	end
 
 	if not self:knowTalentType(t.type[1]) and not t.type_no_req then return nil, "unknown talent type" end
@@ -747,7 +752,7 @@ end
 function _M:getTalentReqDesc(t_id, levmod)
 	local t = _M.talents_def[t_id]
 	local req = t.require
-	if not req then return "" end
+	if not req then return tstring{}, nil end
 	if type(req) == "function" then req = req(self, t) end
 
 	local tlev = self:getTalentLevelRaw(t_id) + (levmod or 0)
@@ -797,8 +802,14 @@ function _M:getTalentReqDesc(t_id, levmod)
 			end
 		end
 	end
+	if req.birth_descriptors then
+		for _, d in ipairs(req.birth_descriptors) do
+			local c = self.descriptor and self.descriptor[d[1]] == d[2] and {"color", 0x00,0xff,0x00} or {"color", 0xff,0x00,0x00}
+			str:add(c, ("- is %s"):format(d[2]), true)
+		end
+	end
 
-	return str
+	return str, req
 end
 
 --- Return the full description of a talent
diff --git a/game/modules/tome/class/interface/PlayerDumpJSON.lua b/game/modules/tome/class/interface/PlayerDumpJSON.lua
index 8f2fc4e84929545a35dffbc3b3613422520de46d..5b67846781072a85f1bcb659e05f818067f29eef 100644
--- a/game/modules/tome/class/interface/PlayerDumpJSON.lua
+++ b/game/modules/tome/class/interface/PlayerDumpJSON.lua
@@ -51,13 +51,16 @@ function _M:dumpToJSON(js, bypass, nosub)
 		addons[add.short_name] = ("%s %d.%d.%d"):format(add.long_name, add.version[1], add.version[2], add.version[3])
 	end
 
+	local class_evo = ""
+	if self.descriptor and self.descriptor.class_evolution then class_evo = " ("..self.descriptor.class_evolution..")" end
+
 	js:newSection("character", {
 		game = string.format("%s %d.%d.%d", game.__mod_info.long_name, game.__mod_info.version[1], game.__mod_info.version[2], game.__mod_info.version[3]),
 		addons = addons,
 		name = self.name,
 		sex = self.descriptor and self.descriptor.sex or (self.female and "Female" or "Male"),
 		race = ((self.descriptor and self.descriptor.subrace) or self.type:capitalize()),
-		class = ((self.descriptor and self.descriptor.subclass) or self.subtype:capitalize()),
+		class = ((self.descriptor and self.descriptor.subclass) or self.subtype:capitalize())..class_evo,
 		size = self:TextSizeCategory(),
 		campaign = self.descriptor and self.descriptor.world or "---",
 		difficulty = self.descriptor and self.descriptor.difficulty or "---",
diff --git a/game/modules/tome/data/quests/start-archmage.lua b/game/modules/tome/data/quests/start-archmage.lua
index e8b5ac234e01e6f84d86547e130722388e700409..ed226afb9f99011afe8a404a116a2eb6096364e0 100644
--- a/game/modules/tome/data/quests/start-archmage.lua
+++ b/game/modules/tome/data/quests/start-archmage.lua
@@ -57,6 +57,8 @@ on_grant = function(self, who)
 
 	who:move(x, y, true)
 
+	if config.settings.cheat and __module_extra_info.no_birth_popup then return end
+
 	local Chat = require"engine.Chat"
 	local chat = Chat.new("tarelion-start-archmage", npc, who)
 	chat:invoke()
diff --git a/game/modules/tome/data/talents.lua b/game/modules/tome/data/talents.lua
index 60affff7ca63944d6d91de25b46276d16c379c84..6292f173f63acfb679c2c10c9b9a1c754ab75231 100644
--- a/game/modules/tome/data/talents.lua
+++ b/game/modules/tome/data/talents.lua
@@ -53,7 +53,7 @@ Talents.newTalent = function(self, t)
 	if tt.speed and not t.speed then t.speed = tt.speed end
 	if t.tactical then t.tactical = Talents.aiLowerTacticals(t.tactical) end
 	if t.tactical_imp then t.tactical_imp = Talents.aiLowerTacticals(t.tactical_imp) end -- DEBUGGING transitional
-	
+
 	if not t.image then
 		t.image = "talents/"..(t.short_name or t.name):lower():gsub("[^a-z0-9_]", "_")..".png"
 	end
@@ -61,6 +61,11 @@ Talents.newTalent = function(self, t)
 	else t.display_entity = Entity.new{image="talents/default.png", is_talent=true}
 	end
 
+	if t.is_class_evolution then
+		t.short_name = (t.short_name or t.name):upper():gsub("[ ']", "_")
+		t.name = "#LIGHT_STEEL_BLUE#"..t.name.." (Class Evolution)"
+	end
+
 	return oldNewTalent(self, t)
 end
 
diff --git a/game/modules/tome/dialogs/Birther.lua b/game/modules/tome/dialogs/Birther.lua
index 126eb46976bdc1ec688d0d09b43eb5dbb9775e39..222760e98dd73cae7e4c8daf43b08babaf8eb6d0 100644
--- a/game/modules/tome/dialogs/Birther.lua
+++ b/game/modules/tome/dialogs/Birther.lua
@@ -391,8 +391,10 @@ function _M:makeDefault()
 	self:setDescriptor("permadeath", "Adventure")
 	self:setDescriptor("race", "Human")
 	self:setDescriptor("subrace", "Cornac")
-	self:setDescriptor("class", "Warrior")
-	self:setDescriptor("subclass", "Berserker")
+	self:setDescriptor("class", "Mage")
+	self:setDescriptor("subclass", "Archmage")
+	-- self:setDescriptor("class", "Warrior")
+	-- self:setDescriptor("subclass", "Berserker")
 	__module_extra_info.no_birth_popup = true
 	self:atEnd("created")
 end
diff --git a/game/modules/tome/dialogs/CharacterSheet.lua b/game/modules/tome/dialogs/CharacterSheet.lua
index 6865e9b2ce553a47fcbe4cd733810dfccb2189a6..aa4a2dad2435fe3b60839a8e50bd8042ff96d7cc 100644
--- a/game/modules/tome/dialogs/CharacterSheet.lua
+++ b/game/modules/tome/dialogs/CharacterSheet.lua
@@ -603,7 +603,9 @@ function _M:drawDialog(kind, actor_to_compare)
 		w = 0
 		s:drawStringBlended(self.font, "Sex  : "..((player.descriptor and player.descriptor.sex) or (player.female and "Female" or "Male")), w, h, 0, 200, 255, true) h = h + self.font_h
 		s:drawStringBlended(self.font, (player.descriptor and "Race : " or "Type : ")..((player.descriptor and player.descriptor.subrace) or player.type:capitalize()), w, h, 0, 200, 255, true) h = h + self.font_h
-		s:drawStringBlended(self.font, (player.descriptor and "Class: " or "Stype: ")..((player.descriptor and player.descriptor.subclass) or player.subtype:capitalize()), w, h, 0, 200, 255, true)
+		local class_evo = ""
+		if player.descriptor and player.descriptor.class_evolution then class_evo = " ("..player.descriptor.class_evolution..")" end
+		s:drawStringBlended(self.font, (player.descriptor and "Class: " or "Stype: ")..((player.descriptor and player.descriptor.subclass) or player.subtype:capitalize())..class_evo, w, h, 0, 200, 255, true)
 		if player:attr("forbid_arcane") then
 			local follow = (player.faction == "zigur" or player:attr("zigur_follower")) and "Zigur follower" or "Antimagic adherent"
 			self:mouseTooltip(self.TOOLTIP_ANTIMAGIC_USER, s:drawColorStringBlended(self.font, "#ORCHID#"..follow, w+200, h, 255, 255, 255, true))
diff --git a/game/modules/tome/dialogs/UberTalent.lua b/game/modules/tome/dialogs/UberTalent.lua
index e5fbf44f270da0e40d94fa0924e8a1ac87b0e1a5..f6b615a4213c906448a9c4400adc0d62e712ee76 100644
--- a/game/modules/tome/dialogs/UberTalent.lua
+++ b/game/modules/tome/dialogs/UberTalent.lua
@@ -85,7 +85,13 @@ function _M:generateList()
 
 	for _, s in ipairs{"uber/strength", "uber/dexterity", "uber/constitution", "uber/magic", "uber/willpower", "uber/cunning"} do
 		local n = {}
-		table.sort(cols[s], function(a,b) return a.name < b.name end)
+		table.sort(cols[s], function(a,b)
+			if a.is_class_evolution ~= b.is_class_evolution then
+				return b.is_class_evolution and true or false
+			else
+				return a.name < b.name
+			end
+		end)
 
 		for i = 1, max do
 			if not cols[s][i] then