Browse Source

Cleaned up remaining TODO for Achievements (#4446)

* Converts labels to camelCase.
* Converts labels to plural where needed.
* Converts Target MobID to use the Sprite name.
* Converts Rewards ItemID to use the Aegis name.
* Dependents now checks for duplicate IDs.
* Dependents now properly supports import methods.
* Added YAMLUpgrade tool to convert previous YAML databases to new format.
* Removes the unique index value for Dependent Achievement ID.
* Adds support for the AG_CHATTING achievement types triggered by script (achievementupdate script command).
* AG_CHATTING map type achievements are still disabled as behavior is unknown.
* AG_HEAR and AG_SEE are now dropped and those achievements have been converted to AG_CHATTING.
* Converts the group constants to how Aegis names them.
Co-authored-by: Lemongrass3110 <lemongrass@kstp.at>
Aleos 4 years ago
parent
commit
5aa9f75343

+ 2 - 0
.gitignore

@@ -43,6 +43,7 @@ Thumbs.db
 /mapcache
 /mapcache
 /nbproject
 /nbproject
 /yaml2sql
 /yaml2sql
+/yamlupgrade
 
 
 # /3rdparty/libconfig/
 # /3rdparty/libconfig/
 /3rdparty/libconfig/Makefile
 /3rdparty/libconfig/Makefile
@@ -122,6 +123,7 @@ Thumbs.db
 /runserver.bat
 /runserver.bat
 /serv.bat
 /serv.bat
 /yaml2sql.bat
 /yaml2sql.bat
+/yamlupgrade.bat
 
 
 # dlls
 # dlls
 /libmysql.dll
 /libmysql.dll

+ 19 - 55
db/achievement_db.yml

@@ -16,70 +16,34 @@
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 #
 #
 ###########################################################################
 ###########################################################################
-# Renewal Achievement Database
+# Achievement Database
 ###########################################################################
 ###########################################################################
 #
 #
 # Achievement Settings
 # Achievement Settings
 #
 #
 ###########################################################################
 ###########################################################################
-# ID - Unique achievement ID.
-###########################################################################
-# Group - Achievement group type. Each achievement type calls a specific
-# objective check.
-# Valid groups:
-#  AG_ADD_FRIEND
-#  AG_ADVENTURE
-#  AG_BABY
-#  AG_BATTLE
-#  AG_CHATTING
-#  AG_CHATTING_COUNT
-#  AG_CHATTING_CREATE
-#  AG_CHATTING_DYING
-#  AG_EAT
-#  AG_GET_ITEM
-#  AG_GET_ZENY
-#  AG_GOAL_ACHIEVE
-#  AG_GOAL_LEVEL
-#  AG_GOAL_STATUS
-#  AG_HEAR
-#  AG_JOB_CHANGE
-#  AG_MARRY
-#  AG_PARTY
-#  AG_ENCHANT_FAIL
-#  AG_ENCHANT_SUCCESS
-#  AG_SEE
-#  AG_SPEND_ZENY
-#  AG_TAMING
-###########################################################################
-# Name - Achievement name. Used when sending rewards through RODEX.
-###########################################################################
-# Target - A list of monster ID and count values that the achievement
-# requires. The target count can also be used for achievements that keep
-# a counter while not being related to monster kills.
-# Capped at MAX_ACHIEVEMENT_OBJECTIVES.
-###########################################################################
-# Condition - A conditional statement that must be met for the achievement
-# to be considered complete.
-###########################################################################
-# Map - A map name that is used for the AG_CHATTING type which increments
-# the counter based on the player's map.
-###########################################################################
-# Dependent: - A list of achievement IDs that need to be completed before
-# this achievement is considered complete.
-###########################################################################
-# Reward - A list of rewards that are given on completion. All fields are
-# optional.
-#   ItemID: Item ID
-#   Amount:  Amount of Item ID (default 1)
-#   Script: Bonus Script
-#   TitleID: Title ID
-###########################################################################
-# Score - Achievement points that are given on completion.
+# - Id                  Achievement ID.
+#   Group               Achievement group type. (Defaut: None)
+#   Name                Achievement name.
+#   Targets:            List of targets the achievement requires. (Default: null)
+#     - Id              Index value used for import methods.
+#       Mob             Target mob. (Default: 0)
+#       Count           Target count. (Default: 1)
+#   Condition           Conditional statement that must be met for the achievement to be considered complete. (Default: null)
+#   Map                 Map name that is used for the AG_CHATTING type. (Default: -1)
+#   Dependents:         List of achievements that need to be completed before this achievement is considered complete. (Default: null)
+#     - Id: <bool>      Achievement ID pre-requisite.
+#   Rewards:            List of rewards that are given on completion. (Default: null)
+#     Item              Item name.
+#     Amount            Amount of item. (Default: 1)
+#     Script            Bonus Script. (Default: null)
+#     TitleId           Title ID. (Default: 0)
+#   Score               Achievement points that are given on completion. (Default: 0)
 ###########################################################################
 ###########################################################################
 
 
 Header:
 Header:
   Type: ACHIEVEMENT_DB
   Type: ACHIEVEMENT_DB
-  Version: 1
+  Version: 2
 
 
 Footer:
 Footer:
   Imports:
   Imports:

+ 2 - 3
db/achievement_level_db.yml

@@ -22,9 +22,8 @@
 # Achievement Level Settings
 # Achievement Level Settings
 #
 #
 ###########################################################################
 ###########################################################################
-# Level - Achievement Level
-###########################################################################
-# Points - Required total scoring points to reach this level.
+# - Level     Achievement Level.
+#   Points    Required total scoring points to reach this level.
 ###########################################################################
 ###########################################################################
 
 
 Header:
 Header:

+ 19 - 55
db/import-tmpl/achievement_db.yml

@@ -16,67 +16,31 @@
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 #
 #
 ###########################################################################
 ###########################################################################
-# Custom Achievement Database
+# Achievement Database
 ###########################################################################
 ###########################################################################
 #
 #
 # Achievement Settings
 # Achievement Settings
 #
 #
 ###########################################################################
 ###########################################################################
-# ID - Unique achievement ID.
-###########################################################################
-# Group - Achievement group type. Each achievement type calls a specific
-# objective check.
-# Valid groups:
-#  AG_ADD_FRIEND
-#  AG_ADVENTURE
-#  AG_BABY
-#  AG_BATTLE
-#  AG_CHATTING
-#  AG_CHATTING_COUNT
-#  AG_CHATTING_CREATE
-#  AG_CHATTING_DYING
-#  AG_EAT
-#  AG_GET_ITEM
-#  AG_GET_ZENY
-#  AG_GOAL_ACHIEVE
-#  AG_GOAL_LEVEL
-#  AG_GOAL_STATUS
-#  AG_HEAR
-#  AG_JOB_CHANGE
-#  AG_MARRY
-#  AG_PARTY
-#  AG_ENCHANT_FAIL
-#  AG_ENCHANT_SUCCESS
-#  AG_SEE
-#  AG_SPEND_ZENY
-#  AG_TAMING
-###########################################################################
-# Name - Achievement name. Used when sending rewards through RODEX.
-###########################################################################
-# Target - A list of monster ID and count values that the achievement
-# requires. The target count can also be used for achievements that keep
-# a counter while not being related to monster kills.
-# Capped at MAX_ACHIEVEMENT_OBJECTIVES.
-###########################################################################
-# Condition - A conditional statement that must be met for the achievement
-# to be considered complete.
-###########################################################################
-# Map - A map name that is used for the AG_CHATTING type which increments
-# the counter based on the player's map.
-###########################################################################
-# Dependent: - A list of achievement IDs that need to be completed before
-# this achievement is considered complete.
-###########################################################################
-# Reward - A list of rewards that are given on completion. All fields are
-# optional.
-#   ItemID: Item ID
-#   Amount:  Amount of Item ID (default 1)
-#   Script: Bonus Script
-#   TitleID: Title ID
-###########################################################################
-# Score - Achievement points that are given on completion.
+# - Id                  Achievement ID.
+#   Group               Achievement group type. (Defaut: None)
+#   Name                Achievement name.
+#   Targets:            List of targets the achievement requires. (Default: null)
+#     - Id              Index value used for import methods.
+#       Mob             Target mob. (Default: 0)
+#       Count           Target count. (Default: 1)
+#   Condition           Conditional statement that must be met for the achievement to be considered complete. (Default: null)
+#   Map                 Map name that is used for the AG_CHATTING type. (Default: -1)
+#   Dependents:         List of achievements that need to be completed before this achievement is considered complete. (Default: null)
+#     - Id: <bool>      Achievement ID pre-requisite.
+#   Rewards:            List of rewards that are given on completion. (Default: null)
+#     Item              Item name.
+#     Amount            Amount of item. (Default: 1)
+#     Script            Bonus Script. (Default: null)
+#     TitleId           Title ID. (Default: 0)
+#   Score               Achievement points that are given on completion. (Default: 0)
 ###########################################################################
 ###########################################################################
 
 
 Header:
 Header:
   Type: ACHIEVEMENT_DB
   Type: ACHIEVEMENT_DB
-  Version: 1
+  Version: 2

+ 3 - 4
db/import-tmpl/achievement_level_db.yml

@@ -16,15 +16,14 @@
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 #
 #
 ###########################################################################
 ###########################################################################
-# Import Achievement Level Database
+# Achievement Level Database
 ###########################################################################
 ###########################################################################
 #
 #
 # Achievement Level Settings
 # Achievement Level Settings
 #
 #
 ###########################################################################
 ###########################################################################
-# Level - Achievement Level
-###########################################################################
-# Points - Required total scoring points to reach this level.
+# - Level     Achievement Level.
+#   Points    Required total scoring points to reach this level.
 ###########################################################################
 ###########################################################################
 
 
 Header:
 Header:

+ 2255 - 2223
db/pre-re/achievement_db.yml

@@ -16,2710 +16,2742 @@
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 #
 #
 ###########################################################################
 ###########################################################################
-# Pre-Renewal Achievement Database
+# Achievement Database
 ###########################################################################
 ###########################################################################
 #
 #
 # Achievement Settings
 # Achievement Settings
 #
 #
 ###########################################################################
 ###########################################################################
-# ID - Unique achievement ID.
-###########################################################################
-# Group - Achievement group type. Each achievement type calls a specific
-# objective check.
-# Valid groups:
-#  AG_ADD_FRIEND
-#  AG_ADVENTURE
-#  AG_BABY
-#  AG_BATTLE
-#  AG_CHATTING
-#  AG_CHATTING_COUNT
-#  AG_CHATTING_CREATE
-#  AG_CHATTING_DYING
-#  AG_EAT
-#  AG_GET_ITEM
-#  AG_GET_ZENY
-#  AG_GOAL_ACHIEVE
-#  AG_GOAL_LEVEL
-#  AG_GOAL_STATUS
-#  AG_HEAR
-#  AG_JOB_CHANGE
-#  AG_MARRY
-#  AG_PARTY
-#  AG_ENCHANT_FAIL
-#  AG_ENCHANT_SUCCESS
-#  AG_SEE
-#  AG_SPEND_ZENY
-#  AG_TAMING
-###########################################################################
-# Name - Achievement name. Used when sending rewards through RODEX.
-###########################################################################
-# Target - A list of monster ID and count values that the achievement
-# requires. The target count can also be used for achievements that keep
-# a counter while not being related to monster kills.
-# Capped at MAX_ACHIEVEMENT_OBJECTIVES.
-###########################################################################
-# Condition - A conditional statement that must be met for the achievement
-# to be considered complete.
-###########################################################################
-# Map - A map name that is used for the AG_CHATTING type which increments
-# the counter based on the player's map.
-###########################################################################
-# Dependent: - A list of achievement IDs that need to be completed before
-# this achievement is considered complete.
-###########################################################################
-# Reward - A list of rewards that are given on completion. All fields are
-# optional.
-#   ItemID: Item ID
-#   Amount:  Amount of Item ID (default 1)
-#   Script: Bonus Script
-#   TitleID: Title ID
-###########################################################################
-# Score - Achievement points that are given on completion.
+# - Id                  Achievement ID.
+#   Group               Achievement group type. (Defaut: None)
+#   Name                Achievement name.
+#   Targets:            List of targets the achievement requires. (Default: null)
+#     - Id              Index value used for import methods.
+#       Mob             Target mob. (Default: 0)
+#       Count           Target count. (Default: 1)
+#   Condition           Conditional statement that must be met for the achievement to be considered complete. (Default: null)
+#   Map                 Map name that is used for the AG_CHATTING type. (Default: -1)
+#   Dependents:         List of achievements that need to be completed before this achievement is considered complete. (Default: null)
+#     - Id: <bool>      Achievement ID pre-requisite.
+#   Rewards:            List of rewards that are given on completion. (Default: null)
+#     Item              Item name.
+#     Amount            Amount of item. (Default: 1)
+#     Script            Bonus Script. (Default: null)
+#     TitleId           Title ID. (Default: 0)
+#   Score               Achievement points that are given on completion. (Default: 0)
 ###########################################################################
 ###########################################################################
 
 
 Header:
 Header:
   Type: ACHIEVEMENT_DB
   Type: ACHIEVEMENT_DB
-  Version: 1
+  Version: 2
 
 
 Body:
 Body:
-  - ID: 110000
-    Group: "AG_EAT"
-    Name: "At this time I live to eat"
-    Score: 10
-  - ID: 110001
-    Group: "AG_SEE"
-    Name: "A fan of this polarity"
-    Score: 10
-  - ID: 120001
-    Group: "AG_ADVENTURE"
-    Name: "North Prontera Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120002
-    Group: "AG_ADVENTURE"
-    Name: "North Prontera Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120003
-    Group: "AG_ADVENTURE"
-    Name: "North Prontera Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120004
-    Group: "AG_ADVENTURE"
-    Name: "West Prontera Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120005
-    Group: "AG_ADVENTURE"
-    Name: "West Prontera Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120006
-    Group: "AG_ADVENTURE"
-    Name: "East Prontera Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120007
-    Group: "AG_ADVENTURE"
-    Name: "South Prontera Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120008
-    Group: "AG_ADVENTURE"
-    Name: "South Prontera Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120009
-    Group: "AG_ADVENTURE"
-    Name: "South Prontera Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120010
-    Group: "AG_ADVENTURE"
-    Name: "South Prontera Field Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120011
-    Group: "AG_ADVENTURE"
-    Name: "East Geffen Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120012
-    Group: "AG_ADVENTURE"
-    Name: "Southeast Geffen Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120013
-    Group: "AG_ADVENTURE"
-    Name: "Northwest Geffen Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120014
-    Group: "AG_ADVENTURE"
-    Name: "Northwest Geffen Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120015
-    Group: "AG_ADVENTURE"
-    Name: "Northwest Geffen Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120016
-    Group: "AG_ADVENTURE"
-    Name: "South Geffen Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120017
-    Group: "AG_ADVENTURE"
-    Name: "South Geffen Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120018
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120019
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120020
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120021
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120022
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(5)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120023
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(6)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120024
-    Group: "AG_ADVENTURE"
-    Name: "Southwest Payon Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120025
-    Group: "AG_ADVENTURE"
-    Name: "Southwest Payon Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120026
-    Group: "AG_ADVENTURE"
-    Name: "Southwest Payon Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120027
-    Group: "AG_ADVENTURE"
-    Name: "Southwest Payon Field Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120028
-    Group: "AG_ADVENTURE"
-    Name: "East Payon Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120029
-    Group: "AG_ADVENTURE"
-    Name: "East Payon Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120030
-    Group: "AG_ADVENTURE"
-    Name: "East Payon Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120031
-    Group: "AG_ADVENTURE"
-    Name: "East Payon Field Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120032
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120033
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120034
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120035
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120036
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(5)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120037
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120038
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120039
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120040
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120041
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(5)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120042
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(6)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120043
-    Group: "AG_ADVENTURE"
-    Name: "South Aldebaran Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120044
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120045
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120046
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120047
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120048
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(5)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120049
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(6)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120050
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(7)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120051
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(8)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120052
-    Group: "AG_ADVENTURE"
-    Name: "Border Checkpoint Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120053
-    Group: "AG_ADVENTURE"
-    Name: "Border Checkpoint Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120054
-    Group: "AG_ADVENTURE"
-    Name: "Kiel Hyre Mansion Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120055
-    Group: "AG_ADVENTURE"
-    Name: "El Mes Plateau Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120056
-    Group: "AG_ADVENTURE"
-    Name: "El Mes Plateau Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120057
-    Group: "AG_ADVENTURE"
-    Name: "El Mes Plateau Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120058
-    Group: "AG_ADVENTURE"
-    Name: "El Mes Gorge Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120059
-    Group: "AG_ADVENTURE"
-    Name: "Kiel Hyre Academy Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120060
-    Group: "AG_ADVENTURE"
-    Name: "Guard Camp Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120061
-    Group: "AG_ADVENTURE"
-    Name: "Juno Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120062
-    Group: "AG_ADVENTURE"
-    Name: "Front of Thanatos Tower Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120063
-    Group: "AG_ADVENTURE"
-    Name: "Hugel Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120064
-    Group: "AG_ADVENTURE"
-    Name: "Hugel Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120065
-    Group: "AG_ADVENTURE"
-    Name: "Hugel Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120066
-    Group: "AG_ADVENTURE"
-    Name: "Abyss Lake Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120067
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120068
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120069
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120070
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120071
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(5)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120072
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(6)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120073
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(7)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120074
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(8)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120075
-    Group: "AG_ADVENTURE"
-    Name: "Lighthalzen Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120076
-    Group: "AG_ADVENTURE"
-    Name: "Lighthalzen Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120077
-    Group: "AG_ADVENTURE"
-    Name: "Lighthalzen Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120078
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Audhumbla Plains Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120079
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Plains Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120080
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Plains Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120081
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Plains Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120082
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Audhumbla Grassland Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120083
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Audhumbla Grassland Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120084
-    Group: "AG_ADVENTURE"
-    Name: "Portus Luna Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120085
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120086
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120087
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120088
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120089
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(5)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120090
-    Group: "AG_ADVENTURE"
-    Name: "Eclage Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120091
-    Group: "AG_ADVENTURE"
-    Name: "North Bitfrost Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120092
-    Group: "AG_ADVENTURE"
-    Name: "South Bitfrost Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120093
-    Group: "AG_ADVENTURE"
-    Name: "Splendide Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120094
-    Group: "AG_ADVENTURE"
-    Name: "Splendide Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120095
-    Group: "AG_ADVENTURE"
-    Name: "Splendide Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120096
-    Group: "AG_ADVENTURE"
-    Name: "Manuk Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120097
-    Group: "AG_ADVENTURE"
-    Name: "Manuk Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120098
-    Group: "AG_ADVENTURE"
-    Name: "Manuk Field Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120099
-    Group: "AG_ADVENTURE"
-    Name: "Outskirts of Kamidal Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120100
-    Group: "AG_ADVENTURE"
-    Name: "Outskirts of Kamidal Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120101
-    Group: "AG_ADVENTURE"
-    Name: "Amatsu Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120102
-    Group: "AG_ADVENTURE"
-    Name: "Kunlun Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120103
-    Group: "AG_ADVENTURE"
-    Name: "Kunlun Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120104
-    Group: "AG_ADVENTURE"
-    Name: "Ayothaya Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120105
-    Group: "AG_ADVENTURE"
-    Name: "Moscovia Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120106
-    Group: "AG_ADVENTURE"
-    Name: "Brasilis Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120107
-    Group: "AG_ADVENTURE"
-    Name: "Dewata Field Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120108
-    Group: "AG_ADVENTURE"
-    Name: "Malaya Field Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120109
-    Group: "AG_ADVENTURE"
-    Name: "Malaya Field Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 10
-  - ID: 120110
-    Group: "AG_ADVENTURE"
-    Name: "Abbey Underground Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120111
-    Group: "AG_ADVENTURE"
-    Name: "Abyss Lake Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120112
-    Group: "AG_ADVENTURE"
-    Name: "Clock Tower Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120113
-    Group: "AG_ADVENTURE"
-    Name: "Amatsu Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120114
-    Group: "AG_ADVENTURE"
-    Name: "Ant Hell Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120115
-    Group: "AG_ADVENTURE"
-    Name: "Ayothaya Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120116
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120117
-    Group: "AG_ADVENTURE"
-    Name: "Brasilis Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120118
-    Group: "AG_ADVENTURE"
-    Name: "Clock Tower Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120119
-    Group: "AG_ADVENTURE"
-    Name: "Istana Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120120
-    Group: "AG_ADVENTURE"
-    Name: "Scaraba Hole Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120121
-    Group: "AG_ADVENTURE"
-    Name: "Bitfrost Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120122
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120123
-    Group: "AG_ADVENTURE"
-    Name: "Geffen Underground Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120124
-    Group: "AG_ADVENTURE"
-    Name: "Glastheim Dungeon Exploration(1)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120125
-    Group: "AG_ADVENTURE"
-    Name: "Glastheim Dungeon Exploration(2)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120126
-    Group: "AG_ADVENTURE"
-    Name: "Glastheim Dungeon Exploration(3)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120127
-    Group: "AG_ADVENTURE"
-    Name: "Glastheim Dungeon Exploration(4)"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120128
-    Group: "AG_ADVENTURE"
-    Name: "Kunlun Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120129
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120130
-    Group: "AG_ADVENTURE"
-    Name: "Sphinx Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120131
-    Group: "AG_ADVENTURE"
-    Name: "Izlude Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120132
-    Group: "AG_ADVENTURE"
-    Name: "Robot Factory Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120133
-    Group: "AG_ADVENTURE"
-    Name: "Bio Lab Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120134
-    Group: "AG_ADVENTURE"
-    Name: "Kunlun Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120135
-    Group: "AG_ADVENTURE"
-    Name: "Nogg Road Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120136
-    Group: "AG_ADVENTURE"
-    Name: "Coal Mine Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120137
-    Group: "AG_ADVENTURE"
-    Name: "Pyramid Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120138
-    Group: "AG_ADVENTURE"
-    Name: "Orc Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120139
-    Group: "AG_ADVENTURE"
-    Name: "Payon Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120140
-    Group: "AG_ADVENTURE"
-    Name: "Labyrinth Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120141
-    Group: "AG_ADVENTURE"
-    Name: "Undersea Tunnel Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120142
-    Group: "AG_ADVENTURE"
-    Name: "Thanatos Tower Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120143
-    Group: "AG_ADVENTURE"
-    Name: "Thor Volcano Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120144
-    Group: "AG_ADVENTURE"
-    Name: "Sunken Ship Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120145
-    Group: "AG_ADVENTURE"
-    Name: "Turtle Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 120146
-    Group: "AG_ADVENTURE"
-    Name: "Toy Factory Dungeon Exploration"
-    #Reward:
-    #  ItemID: 22876
-    Score: 20
-  - ID: 127001
-    Group: "AG_CHATTING"
-    Name: "Prontera Contribution"
-    Map: "prontera"
-    Target:
+  - Id: 110000
+    Group: Eat
+    Name: At this time I live to eat
+    Score: 10
+  - Id: 110001
+    Group: Chatting
+    Name: A fan of this polarity
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 1
+      - Id: 1
+        Count: 1
+      - Id: 2
+        Count: 1
+      - Id: 3
+        Count: 1
+      - Id: 4
+        Count: 1
+      - Id: 5
+        Count: 1
+      - Id: 6
+        Count: 1
     Score: 10
     Score: 10
-  - ID: 127002
-    Group: "AG_CHATTING"
-    Name: "Geffen Contribution"
-    Map: "geffen"
-    Target:
+  - Id: 120001
+    Group: Adventure
+    Name: North Prontera Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120002
+    Group: Adventure
+    Name: North Prontera Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120003
+    Group: Adventure
+    Name: North Prontera Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120004
+    Group: Adventure
+    Name: West Prontera Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120005
+    Group: Adventure
+    Name: West Prontera Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120006
+    Group: Adventure
+    Name: East Prontera Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120007
+    Group: Adventure
+    Name: South Prontera Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120008
+    Group: Adventure
+    Name: South Prontera Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120009
+    Group: Adventure
+    Name: South Prontera Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120010
+    Group: Adventure
+    Name: South Prontera Field Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120011
+    Group: Adventure
+    Name: East Geffen Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120012
+    Group: Adventure
+    Name: Southeast Geffen Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120013
+    Group: Adventure
+    Name: Northwest Geffen Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120014
+    Group: Adventure
+    Name: Northwest Geffen Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120015
+    Group: Adventure
+    Name: Northwest Geffen Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120016
+    Group: Adventure
+    Name: South Geffen Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120017
+    Group: Adventure
+    Name: South Geffen Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120018
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120019
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120020
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120021
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120022
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(5)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120023
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(6)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120024
+    Group: Adventure
+    Name: Southwest Payon Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120025
+    Group: Adventure
+    Name: Southwest Payon Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120026
+    Group: Adventure
+    Name: Southwest Payon Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120027
+    Group: Adventure
+    Name: Southwest Payon Field Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120028
+    Group: Adventure
+    Name: East Payon Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120029
+    Group: Adventure
+    Name: East Payon Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120030
+    Group: Adventure
+    Name: East Payon Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120031
+    Group: Adventure
+    Name: East Payon Field Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120032
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120033
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120034
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120035
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120036
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(5)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120037
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120038
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120039
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120040
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120041
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(5)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120042
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(6)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120043
+    Group: Adventure
+    Name: South Aldebaran Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120044
+    Group: Adventure
+    Name: Comodo Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120045
+    Group: Adventure
+    Name: Comodo Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120046
+    Group: Adventure
+    Name: Comodo Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120047
+    Group: Adventure
+    Name: Comodo Field Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120048
+    Group: Adventure
+    Name: Comodo Field Exploration(5)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120049
+    Group: Adventure
+    Name: Comodo Field Exploration(6)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120050
+    Group: Adventure
+    Name: Comodo Field Exploration(7)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120051
+    Group: Adventure
+    Name: Comodo Field Exploration(8)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120052
+    Group: Adventure
+    Name: Border Checkpoint Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120053
+    Group: Adventure
+    Name: Border Checkpoint Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120054
+    Group: Adventure
+    Name: Kiel Hyre Mansion Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120055
+    Group: Adventure
+    Name: El Mes Plateau Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120056
+    Group: Adventure
+    Name: El Mes Plateau Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120057
+    Group: Adventure
+    Name: El Mes Plateau Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120058
+    Group: Adventure
+    Name: El Mes Gorge Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120059
+    Group: Adventure
+    Name: Kiel Hyre Academy Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120060
+    Group: Adventure
+    Name: Guard Camp Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120061
+    Group: Adventure
+    Name: Juno Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120062
+    Group: Adventure
+    Name: Front of Thanatos Tower Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120063
+    Group: Adventure
+    Name: Hugel Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120064
+    Group: Adventure
+    Name: Hugel Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120065
+    Group: Adventure
+    Name: Hugel Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120066
+    Group: Adventure
+    Name: Abyss Lake Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120067
+    Group: Adventure
+    Name: Einbroch Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120068
+    Group: Adventure
+    Name: Einbroch Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120069
+    Group: Adventure
+    Name: Einbroch Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120070
+    Group: Adventure
+    Name: Einbroch Field Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120071
+    Group: Adventure
+    Name: Einbroch Field Exploration(5)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120072
+    Group: Adventure
+    Name: Einbroch Field Exploration(6)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120073
+    Group: Adventure
+    Name: Einbroch Field Exploration(7)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120074
+    Group: Adventure
+    Name: Einbroch Field Exploration(8)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120075
+    Group: Adventure
+    Name: Lighthalzen Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120076
+    Group: Adventure
+    Name: Lighthalzen Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120077
+    Group: Adventure
+    Name: Lighthalzen Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120078
+    Group: Adventure
+    Name: Rachel Audhumbla Plains Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120079
+    Group: Adventure
+    Name: Rachel Plains Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120080
+    Group: Adventure
+    Name: Rachel Plains Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120081
+    Group: Adventure
+    Name: Rachel Plains Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120082
+    Group: Adventure
+    Name: Rachel Audhumbla Grassland Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120083
+    Group: Adventure
+    Name: Rachel Audhumbla Grassland Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120084
+    Group: Adventure
+    Name: Portus Luna Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120085
+    Group: Adventure
+    Name: Veins Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120086
+    Group: Adventure
+    Name: Veins Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120087
+    Group: Adventure
+    Name: Veins Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120088
+    Group: Adventure
+    Name: Veins Field Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120089
+    Group: Adventure
+    Name: Veins Field Exploration(5)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120090
+    Group: Adventure
+    Name: Eclage Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120091
+    Group: Adventure
+    Name: North Bitfrost Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120092
+    Group: Adventure
+    Name: South Bitfrost Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120093
+    Group: Adventure
+    Name: Splendide Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120094
+    Group: Adventure
+    Name: Splendide Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120095
+    Group: Adventure
+    Name: Splendide Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120096
+    Group: Adventure
+    Name: Manuk Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120097
+    Group: Adventure
+    Name: Manuk Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120098
+    Group: Adventure
+    Name: Manuk Field Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120099
+    Group: Adventure
+    Name: Outskirts of Kamidal Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120100
+    Group: Adventure
+    Name: Outskirts of Kamidal Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120101
+    Group: Adventure
+    Name: Amatsu Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120102
+    Group: Adventure
+    Name: Kunlun Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120103
+    Group: Adventure
+    Name: Kunlun Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120104
+    Group: Adventure
+    Name: Ayothaya Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120105
+    Group: Adventure
+    Name: Moscovia Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120106
+    Group: Adventure
+    Name: Brasilis Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120107
+    Group: Adventure
+    Name: Dewata Field Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120108
+    Group: Adventure
+    Name: Malaya Field Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120109
+    Group: Adventure
+    Name: Malaya Field Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 10
+  - Id: 120110
+    Group: Adventure
+    Name: Abbey Underground Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120111
+    Group: Adventure
+    Name: Abyss Lake Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120112
+    Group: Adventure
+    Name: Clock Tower Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120113
+    Group: Adventure
+    Name: Amatsu Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120114
+    Group: Adventure
+    Name: Ant Hell Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120115
+    Group: Adventure
+    Name: Ayothaya Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120116
+    Group: Adventure
+    Name: Comodo Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120117
+    Group: Adventure
+    Name: Brasilis Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120118
+    Group: Adventure
+    Name: Clock Tower Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120119
+    Group: Adventure
+    Name: Istana Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120120
+    Group: Adventure
+    Name: Scaraba Hole Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120121
+    Group: Adventure
+    Name: Bitfrost Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120122
+    Group: Adventure
+    Name: Einbroch Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120123
+    Group: Adventure
+    Name: Geffen Underground Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120124
+    Group: Adventure
+    Name: Glastheim Dungeon Exploration(1)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120125
+    Group: Adventure
+    Name: Glastheim Dungeon Exploration(2)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120126
+    Group: Adventure
+    Name: Glastheim Dungeon Exploration(3)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120127
+    Group: Adventure
+    Name: Glastheim Dungeon Exploration(4)
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120128
+    Group: Adventure
+    Name: Kunlun Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120129
+    Group: Adventure
+    Name: Rachel Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120130
+    Group: Adventure
+    Name: Sphinx Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120131
+    Group: Adventure
+    Name: Izlude Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120132
+    Group: Adventure
+    Name: Robot Factory Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120133
+    Group: Adventure
+    Name: Bio Lab Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120134
+    Group: Adventure
+    Name: Kunlun Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120135
+    Group: Adventure
+    Name: Nogg Road Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120136
+    Group: Adventure
+    Name: Coal Mine Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120137
+    Group: Adventure
+    Name: Pyramid Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120138
+    Group: Adventure
+    Name: Orc Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120139
+    Group: Adventure
+    Name: Payon Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120140
+    Group: Adventure
+    Name: Labyrinth Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120141
+    Group: Adventure
+    Name: Undersea Tunnel Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120142
+    Group: Adventure
+    Name: Thanatos Tower Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120143
+    Group: Adventure
+    Name: Thor Volcano Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120144
+    Group: Adventure
+    Name: Sunken Ship Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120145
+    Group: Adventure
+    Name: Turtle Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 120146
+    Group: Adventure
+    Name: Toy Factory Dungeon Exploration
+    #Rewards:
+    #  Item: Shabby_Purse
+    Score: 20
+  - Id: 127001
+    Group: Chatting
+    Name: Prontera Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: prontera
     Score: 10
     Score: 10
-  - ID: 127003
-    Group: "AG_CHATTING"
-    Name: "Morocc Contribution"
-    Map: "morocc"
-    Target:
+  - Id: 127002
+    Group: Chatting
+    Name: Geffen Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: geffen
     Score: 10
     Score: 10
-  - ID: 127004
-    Group: "AG_CHATTING"
-    Name: "Payon Contribution"
-    Map: "payon"
-    Target:
+  - Id: 127003
+    Group: Chatting
+    Name: Morocc Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: morocc
     Score: 10
     Score: 10
-  - ID: 127005
-    Group: "AG_CHATTING"
-    Name: "Juno Contribution"
-    Map: "yuno"
-    Target:
+  - Id: 127004
+    Group: Chatting
+    Name: Payon Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: payon
     Score: 10
     Score: 10
-  - ID: 127006
-    Group: "AG_CHATTING"
-    Name: "Lighthalzen Contribution"
-    Map: "lighthalzen"
-    Target:
+  - Id: 127005
+    Group: Chatting
+    Name: Juno Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: yuno
     Score: 10
     Score: 10
-  - ID: 127007
-    Group: "AG_CHATTING"
-    Name: "Einbroch Contribution"
-    Map: "einbroch"
-    Target:
+  - Id: 127006
+    Group: Chatting
+    Name: Lighthalzen Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: lighthalzen
     Score: 10
     Score: 10
-  - ID: 127008
-    Group: "AG_CHATTING"
-    Name: "Rachel Contribution"
-    Map: "rachel"
-    Target:
+  - Id: 127007
+    Group: Chatting
+    Name: Einbroch Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: einbroch
     Score: 10
     Score: 10
-  - ID: 127009
-    Group: "AG_CHATTING"
-    Name: "Veins Contribution"
-    Map: "veins"
-    Target:
+  - Id: 127008
+    Group: Chatting
+    Name: Rachel Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: rachel
     Score: 10
     Score: 10
-  - ID: 128000
-    Group: "AG_BATTLE"
-    Name: "Uninvited Guest"
-    #Target:
+  - Id: 127009
+    Group: Chatting
+    Name: Veins Contribution
+    Targets:
+      - Id: 0
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: veins
+    Score: 10
+  - Id: 128000
+    Group: Battle
+    Name: Uninvited Guest
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2996
-    #    Count: 1
+    #    Mob: XM_CELINE_KIMI
     Score: 10
     Score: 10
-  - ID: 128001
-    Group: "AG_BATTLE"
-    Name: "Strange Guest"
-    #Target:
+  - Id: 128001
+    Group: Battle
+    Name: Strange Guest
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2996
+    #    Mob: XM_CELINE_KIMI
     #    Count: 10
     #    Count: 10
     Score: 10
     Score: 10
-  - ID: 128002
-    Group: "AG_BATTLE"
-    Name: "Get along with map..."
-    #Target:
+  - Id: 128002
+    Group: Battle
+    Name: Get along with map...
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2996
+    #    Mob: XM_CELINE_KIMI
     #    Count: 25
     #    Count: 25
     Score: 20
     Score: 20
-  - ID: 128003
-    Group: "AG_BATTLE"
-    Name: "Welcomed Guest"
-    #Target:
+  - Id: 128003
+    Group: Battle
+    Name: Welcomed Guest
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2996
+    #    Mob: XM_CELINE_KIMI
     #    Count: 50
     #    Count: 50
     Score: 30
     Score: 30
-  - ID: 128004
-    Group: "AG_BATTLE"
-    Name: "Kimmy's best friend"
-    #Target:
+  - Id: 128004
+    Group: Battle
+    Name: Kimmy's best friend
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2996
+    #    Mob: XM_CELINE_KIMI
     #    Count: 100
     #    Count: 100
     Score: 50
     Score: 50
-  - ID: 128005
-    Group: "AG_BATTLE"
-    Name: "Novice Angler"
-    #Target:
+  - Id: 128005
+    Group: Battle
+    Name: Novice Angler
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2322
-    #    Count: 1
+    #    Mob: BAKONAWA_3
     Score: 10
     Score: 10
-  - ID: 128006
-    Group: "AG_BATTLE"
-    Name: "Juicy Hunter"
-    #Target:
+  - Id: 128006
+    Group: Battle
+    Name: Juicy Hunter
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2322
+    #    Mob: BAKONAWA_3
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128007
-    Group: "AG_BATTLE"
-    Name: "Rhythm Master"
-    #Target:
+  - Id: 128007
+    Group: Battle
+    Name: Rhythm Master
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2322
+    #    Mob: BAKONAWA_3
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128008
-    Group: "AG_BATTLE"
-    Name: "Bold Adventurer"
-    Target:
+  - Id: 128008
+    Group: Battle
+    Name: Bold Adventurer
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1929
-        Count: 1
+        Mob: BAPHOMET_I
     Score: 10
     Score: 10
-  - ID: 128009
-    Group: "AG_BATTLE"
-    Name: "Baphomet Hatred"
-    Target:
+  - Id: 128009
+    Group: Battle
+    Name: Baphomet Hatred
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1929
+        Mob: BAPHOMET_I
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128010
-    Group: "AG_BATTLE"
-    Name: "Goat's Nemesis"
-    Target:
+  - Id: 128010
+    Group: Battle
+    Name: Goat's Nemesis
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1929
+        Mob: BAPHOMET_I
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128011
-    Group: "AG_BATTLE"
-    Name: "Ordinary Tourist"
-    #Target:
+  - Id: 128011
+    Group: Battle
+    Name: Ordinary Tourist
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3029
-    #    Count: 1
+    #    Mob: GRIM_REAPER_ANKOU
     Score: 10
     Score: 10
-  - ID: 128012
-    Group: "AG_BATTLE"
-    Name: "Backcountry Expert"
-    #Target:
+  - Id: 128012
+    Group: Battle
+    Name: Backcountry Expert
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3029
+    #    Mob: GRIM_REAPER_ANKOU
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128013
-    Group: "AG_BATTLE"
-    Name: "Able to eat more like this"
-    #Target:
+  - Id: 128013
+    Group: Battle
+    Name: Able to eat more like this
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3029
+    #    Mob: GRIM_REAPER_ANKOU
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128014
-    Group: "AG_BATTLE"
-    Name: "Digest hard meat"
-    #Target:
+  - Id: 128014
+    Group: Battle
+    Name: Digest hard meat
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2319
-    #    Count: 1
+    #    Mob: BUWAYA
     Score: 10
     Score: 10
-  - ID: 128015
-    Group: "AG_BATTLE"
-    Name: "Master of Escape"
-    #Target:
+  - Id: 128015
+    Group: Battle
+    Name: Master of Escape
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2319
+    #    Mob: BUWAYA
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128016
-    Group: "AG_BATTLE"
-    Name: "Immortal Hunter"
-    #Target:
+  - Id: 128016
+    Group: Battle
+    Name: Immortal Hunter
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2319
+    #    Mob: BUWAYA
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128017
-    Group: "AG_BATTLE"
-    Name: "Stood up and overcame despair"
-    #Target:
+  - Id: 128017
+    Group: Battle
+    Name: Stood up and overcame despair
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
-    #    Count: 1
+    #    Mob: MM_MOROCC_ADT
     Score: 10
     Score: 10
-  - ID: 128018
-    Group: "AG_BATTLE"
-    Name: "Ember of Hope"
-    #Target:
+  - Id: 128018
+    Group: Battle
+    Name: Ember of Hope
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
+    #    Mob: MM_MOROCC_ADT
     #    Count: 10
     #    Count: 10
     Score: 10
     Score: 10
-  - ID: 128019
-    Group: "AG_BATTLE"
-    Name: "Pouring Aurora"
-    #Target:
+  - Id: 128019
+    Group: Battle
+    Name: Pouring Aurora
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
+    #    Mob: MM_MOROCC_ADT
     #    Count: 25
     #    Count: 25
     Score: 20
     Score: 20
-  - ID: 128020
-    Group: "AG_BATTLE"
-    Name: "Who is desperate? I am hopeless!"
-    #Target:
+  - Id: 128020
+    Group: Battle
+    Name: Who is desperate? I am hopeless!
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
+    #    Mob: MM_MOROCC_ADT
     #    Count: 50
     #    Count: 50
     Score: 30
     Score: 30
-  - ID: 128021
-    Group: "AG_BATTLE"
-    Name: "I know god will save the world"
-    #Target:
+  - Id: 128021
+    Group: Battle
+    Name: I know god will save the world
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
+    #    Mob: MM_MOROCC_ADT
     #    Count: 100
     #    Count: 100
     Score: 50
     Score: 50
-  - ID: 128022
-    Group: "AG_BATTLE"
-    Name: "There was mercy in Morocc army"
-    #Target:
+  - Id: 128022
+    Group: Battle
+    Name: There was mercy in Morocc army
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3000
-    #  Count: 1
+    #    Mob: EP14_MORS_BOSSB
     Score: 10
     Score: 10
-  - ID: 128023
-    Group: "AG_BATTLE"
-    Name: "There was fear in Morocc army"
-    #Target:
+  - Id: 128023
+    Group: Battle
+    Name: There was fear in Morocc army
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3000
+    #    Mob: EP14_MORS_BOSSB
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128024
-    Group: "AG_BATTLE"
-    Name: "Guard of weak army"
-    #Target:
+  - Id: 128024
+    Group: Battle
+    Name: Guard of weak army
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3000
+    #    Mob: EP14_MORS_BOSSB
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128025
-    Group: "AG_BATTLE"
-    Name: "Audience with the queen"
-    #Target:
+  - Id: 128025
+    Group: Battle
+    Name: Audience with the queen
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2529
-    #    Count: 1
+    #    Mob: FACEWORM_QUEEN
     Score: 10
     Score: 10
-  - ID: 128026
-    Group: "AG_BATTLE"
-    Name: "Warm earth"
-    #Target:
+  - Id: 128026
+    Group: Battle
+    Name: Warm earth
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2533
-    #    Count: 1
+    #    Mob: FACEWORM_QUEEN_G
     Score: 10
     Score: 10
-  - ID: 128027
-    Group: "AG_BATTLE"
-    Name: "Water is very good exactly"
-    #Target:
+  - Id: 128027
+    Group: Battle
+    Name: Water is very good exactly
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2534
-    #    Count: 1
+    #    Mob: FACEWORM_QUEEN_B
     Score: 10
     Score: 10
-  - ID: 128028
-    Group: "AG_BATTLE"
-    Name: "Pleasant breeze"
-    #Target:
+  - Id: 128028
+    Group: Battle
+    Name: Pleasant breeze
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2535
-    #    Count: 1
+    #    Mob: FACEWORM_QUEEN_Y
     Score: 10
     Score: 10
-  - ID: 128029
-    Group: "AG_BATTLE"
-    Name: "Visitor of old castle"
-    #Target:
+  - Id: 128029
+    Group: Battle
+    Name: Visitor of old castle
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2476
-    #    Count: 1
+    #    Mob: MG_AMDARAIS
     Score: 10
     Score: 10
-  - ID: 128030
-    Group: "AG_BATTLE"
-    Name: "Lord of old castle"
-    #Target:
+  - Id: 128030
+    Group: Battle
+    Name: Lord of old castle
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2476
+    #    Mob: MG_AMDARAIS
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128031
-    Group: "AG_BATTLE"
-    Name: "Conqueror of old castle"
-    #Target:
+  - Id: 128031
+    Group: Battle
+    Name: Conqueror of old castle
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2476
+    #    Mob: MG_AMDARAIS
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128032
-    Group: "AG_BATTLE"
-    Name: "Haggard sucker"
-    #Target:
+  - Id: 128032
+    Group: Battle
+    Name: Haggard sucker
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3150
-    #    Count: 1
+    #    Mob: MG_AMDARAIS_H
     Score: 10
     Score: 10
-  - ID: 128033
-    Group: "AG_BATTLE"
-    Name: "Hope of the Knight"
-    #Target:
+  - Id: 128033
+    Group: Battle
+    Name: Hope of the Knight
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3150
+    #    Mob: MG_AMDARAIS_H
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128034
-    Group: "AG_BATTLE"
-    Name: "Guardian of the Dawn"
-    #Target:
+  - Id: 128034
+    Group: Battle
+    Name: Guardian of the Dawn
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3150
+    #    Mob: MG_AMDARAIS_H
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128035
-    Group: "AG_BATTLE"
-    Name: "Time Traveler"
-    #Target:
+  - Id: 128035
+    Group: Battle
+    Name: Time Traveler
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3190
-    #    Count: 1
+    #    Mob: MM_SARAH
     Score: 10
     Score: 10
-  - ID: 128036
-    Group: "AG_BATTLE"
-    Name: "Restore ancient relic"
-    #Target:
+  - Id: 128036
+    Group: Battle
+    Name: Restore ancient relic
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3190
+    #    Mob: MM_SARAH
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128037
-    Group: "AG_BATTLE"
-    Name: "Master of relic transport"
-    #Target:
+  - Id: 128037
+    Group: Battle
+    Name: Master of relic transport
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3190
+    #    Mob: MM_SARAH
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128038
-    Group: "AG_BATTLE"
-    Name: "Show Jailbreak to the captain"
-    #Target:
+  - Id: 128038
+    Group: Battle
+    Name: Show Jailbreak to the captain
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3181
-    #    Count: 1
+    #    Mob: E1_FELOCK
     Score: 10
     Score: 10
-  - ID: 128039
-    Group: "AG_BATTLE"
-    Name: "Show Jailbreak to the weak captain"
-    #Target:
+  - Id: 128039
+    Group: Battle
+    Name: Show Jailbreak to the weak captain
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3188
-    #    Count: 1
+    #    Mob: E2_FELOCK
     Score: 10
     Score: 10
-  - ID: 128040
-    Group: "AG_BATTLE"
-    Name: "Riot on board"
-    #Target:
+  - Id: 128040
+    Group: Battle
+    Name: Riot on board
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3181
-    #    Count: 1
+    #    Mob: E1_FELOCK
     Score: 20
     Score: 20
-  - ID: 128041
-    Group: "AG_BATTLE"
-    Name: "Turmoil on board"
-    #Target:
+  - Id: 128041
+    Group: Battle
+    Name: Turmoil on board
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3181
+    #    Mob: E1_FELOCK
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128042
-    Group: "AG_BATTLE"
-    Name: "Rebellion on board"
-    #Target:
+  - Id: 128042
+    Group: Battle
+    Name: Rebellion on board
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3181
+    #    Mob: E1_FELOCK
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128043
-    Group: "AG_BATTLE"
-    Name: "Revolt of Riot"
-    #Target:
+  - Id: 128043
+    Group: Battle
+    Name: Revolt of Riot
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3188
+    #    Mob: E2_FELOCK
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128044
-    Group: "AG_BATTLE"
-    Name: "Magic tournament champion"
-    #Target:
+  - Id: 128044
+    Group: Battle
+    Name: Magic tournament champion
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2564
-    #    Count: 1
+    #    Mob: GEFFEN_FENRIR
     Score: 10
     Score: 10
-  - ID: 128045
-    Group: "AG_BATTLE"
-    Name: "Gladiator of Coliseum"
-    #Target:
+  - Id: 128045
+    Group: Battle
+    Name: Gladiator of Coliseum
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2564
+    #    Mob: GEFFEN_FENRIR
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128046
-    Group: "AG_BATTLE"
-    Name: "Slayer of Colosseum"
-    #Target:
+  - Id: 128046
+    Group: Battle
+    Name: Slayer of Colosseum
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2564
+    #    Mob: GEFFEN_FENRIR
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128047
-    Group: "AG_BATTLE"
-    Name: "Endless Tower challenger"
-    Target:
+  - Id: 128047
+    Group: Battle
+    Name: Endless Tower challenger
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1956
-        Count: 1
+        Mob: NAGHT_SIEGER
     Score: 10
     Score: 10
-  - ID: 128048
-    Group: "AG_BATTLE"
-    Name: "Endless Tower Slayer"
-    Target:
+  - Id: 128048
+    Group: Battle
+    Name: Endless Tower Slayer
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1956
+        Mob: NAGHT_SIEGER
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128049
-    Group: "AG_BATTLE"
-    Name: "Lord of the tower"
-    Target:
+  - Id: 128049
+    Group: Battle
+    Name: Lord of the tower
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1956
+        Mob: NAGHT_SIEGER
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128050
-    Group: "AG_BATTLE"
-    Name: "Novice Exorcist"
-    #Target:
+  - Id: 128050
+    Group: Battle
+    Name: Novice Exorcist
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2327
-    #    Count: 1
+    #    Mob: BANGUNGOT_3
     Score: 10
     Score: 10
-  - ID: 128051
-    Group: "AG_BATTLE"
-    Name: "Experienced Exorcist"
-    #Target:
+  - Id: 128051
+    Group: Battle
+    Name: Experienced Exorcist
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2327
+    #    Mob: BANGUNGOT_3
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128052
-    Group: "AG_BATTLE"
-    Name: "Legendary Exorcist"
-    #Target:
+  - Id: 128052
+    Group: Battle
+    Name: Legendary Exorcist
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2327
+    #    Mob: BANGUNGOT_3
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 129001
-    Group: "AG_ADVENTURE"
-    Name: "Prontera Explorer"
-    Dependent:
-      - Id: 120001
-      - Id: 120002
-      - Id: 120003
-      - Id: 120004
-      - Id: 120005
-      - Id: 120006
-      - Id: 120007
-      - Id: 120008
-      - Id: 120009
-      - Id: 120010
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129002
-    Group: "AG_ADVENTURE"
-    Name: "Geffen Explorer"
-    Dependent:
-      - Id: 120011
-      - Id: 120012
-      - Id: 120013
-      - Id: 120014
-      - Id: 120015
-      - Id: 120016
-      - Id: 120017
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129003
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Explorer"
-    Dependent:
-      - Id: 120018
-      - Id: 120019
-      - Id: 120020
-      - Id: 120021
-      - Id: 120022
-      - Id: 120023
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129004
-    Group: "AG_ADVENTURE"
-    Name: "Payon Explorer"
-    Dependent:
-      - Id: 120024
-      - Id: 120025
-      - Id: 120026
-      - Id: 120027
-      - Id: 120028
-      - Id: 120029
-      - Id: 120030
-      - Id: 120031
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129005
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Explorer"
-    Dependent:
-      - Id: 120032
-      - Id: 120033
-      - Id: 120034
-      - Id: 120035
-      - Id: 120036
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129006
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Explorer"
-    Dependent:
-      - Id: 120037
-      - Id: 120038
-      - Id: 120039
-      - Id: 120040
-      - Id: 120041
-      - Id: 120042
-      - Id: 120043
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129007
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Explorer"
-    Dependent:
-      - Id: 120044
-      - Id: 120045
-      - Id: 120046
-      - Id: 120047
-      - Id: 120048
-      - Id: 120049
-      - Id: 120050
-      - Id: 120051
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129008
-    Group: "AG_ADVENTURE"
-    Name: "Rune-Midgarts Explorer"
-    Dependent:
-      - Id: 129001
-      - Id: 129002
-      - Id: 129003
-      - Id: 129004
-      - Id: 129005
-      - Id: 129006
-      - Id: 129007
-    Reward:
-      ItemID: 617
+  - Id: 129001
+    Group: Adventure
+    Name: Prontera Explorer
+    Dependents:
+      120001: true
+      120002: true
+      120003: true
+      120004: true
+      120005: true
+      120006: true
+      120007: true
+      120008: true
+      120009: true
+      120010: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129002
+    Group: Adventure
+    Name: Geffen Explorer
+    Dependents:
+      120011: true
+      120012: true
+      120013: true
+      120014: true
+      120015: true
+      120016: true
+      120017: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129003
+    Group: Adventure
+    Name: Sograt Desert Explorer
+    Dependents:
+      120018: true
+      120019: true
+      120020: true
+      120021: true
+      120022: true
+      120023: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129004
+    Group: Adventure
+    Name: Payon Explorer
+    Dependents:
+      120024: true
+      120025: true
+      120026: true
+      120027: true
+      120028: true
+      120029: true
+      120030: true
+      120031: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129005
+    Group: Adventure
+    Name: North Mjolnir Explorer
+    Dependents:
+      120032: true
+      120033: true
+      120034: true
+      120035: true
+      120036: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129006
+    Group: Adventure
+    Name: South Mjolnir Explorer
+    Dependents:
+      120037: true
+      120038: true
+      120039: true
+      120040: true
+      120041: true
+      120042: true
+      120043: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129007
+    Group: Adventure
+    Name: Comodo Explorer
+    Dependents:
+      120044: true
+      120045: true
+      120046: true
+      120047: true
+      120048: true
+      120049: true
+      120050: true
+      120051: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129008
+    Group: Adventure
+    Name: Rune-Midgarts Explorer
+    Dependents:
+      129001: true
+      129002: true
+      129003: true
+      129004: true
+      129005: true
+      129006: true
+      129007: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129009
-    Group: "AG_ADVENTURE"
-    Name: "Juno Explorer"
-    Dependent:
-      - Id: 120052
-      - Id: 120053
-      - Id: 120054
-      - Id: 120055
-      - Id: 120056
-      - Id: 120057
-      - Id: 120058
-      - Id: 120059
-      - Id: 120060
-      - Id: 120061
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129010
-    Group: "AG_ADVENTURE"
-    Name: "Hugel Explorer"
-    Dependent:
-      - Id: 120062
-      - Id: 120063
-      - Id: 120064
-      - Id: 120065
-      - Id: 120066
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129011
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Explorer"
-    Dependent:
-      - Id: 120067
-      - Id: 120068
-      - Id: 120069
-      - Id: 120070
-      - Id: 120071
-      - Id: 120072
-      - Id: 120073
-      - Id: 120074
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129012
-    Group: "AG_ADVENTURE"
-    Name: "Lighthalzen Explorer"
-    Dependent:
-      - Id: 120075
-      - Id: 120076
-      - Id: 120077
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129013
-    Group: "AG_ADVENTURE"
-    Name: "Schwarzwald Explorer"
-    Dependent:
-      - Id: 129009
-      - Id: 129010
-      - Id: 129011
-      - Id: 129012
-    Reward:
-      ItemID: 617
+  - Id: 129009
+    Group: Adventure
+    Name: Juno Explorer
+    Dependents:
+      120052: true
+      120053: true
+      120054: true
+      120055: true
+      120056: true
+      120057: true
+      120058: true
+      120059: true
+      120060: true
+      120061: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129010
+    Group: Adventure
+    Name: Hugel Explorer
+    Dependents:
+      120062: true
+      120063: true
+      120064: true
+      120065: true
+      120066: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129011
+    Group: Adventure
+    Name: Einbroch Explorer
+    Dependents:
+      120067: true
+      120068: true
+      120069: true
+      120070: true
+      120071: true
+      120072: true
+      120073: true
+      120074: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129012
+    Group: Adventure
+    Name: Lighthalzen Explorer
+    Dependents:
+      120075: true
+      120076: true
+      120077: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129013
+    Group: Adventure
+    Name: Schwarzwald Explorer
+    Dependents:
+      129009: true
+      129010: true
+      129011: true
+      129012: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129014
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Explorer"
-    Dependent:
-      - Id: 120078
-      - Id: 120079
-      - Id: 120080
-      - Id: 120081
-      - Id: 120082
-      - Id: 120083
-      - Id: 120084
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129015
-    Group: "AG_ADVENTURE"
-    Name: "Veins Explorer"
-    Dependent:
-      - Id: 120085
-      - Id: 120086
-      - Id: 120087
-      - Id: 120088
-      - Id: 120089
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129016
-    Group: "AG_ADVENTURE"
-    Name: "Arunafeltz Explorer"
-    Dependent:
-      - Id: 129014
-      - Id: 129015
-    Reward:
-      ItemID: 617
+  - Id: 129014
+    Group: Adventure
+    Name: Rachel Explorer
+    Dependents:
+      120078: true
+      120079: true
+      120080: true
+      120081: true
+      120082: true
+      120083: true
+      120084: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129015
+    Group: Adventure
+    Name: Veins Explorer
+    Dependents:
+      120085: true
+      120086: true
+      120087: true
+      120088: true
+      120089: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129016
+    Group: Adventure
+    Name: Arunafeltz Explorer
+    Dependents:
+      129014: true
+      129015: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129017
-    Group: "AG_ADVENTURE"
-    Name: "Laphine Explorer"
-    Dependent:
-      - Id: 120090
-      - Id: 120091
-      - Id: 120092
-      - Id: 120093
-      - Id: 120094
-      - Id: 120095
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129018
-    Group: "AG_ADVENTURE"
-    Name: "Manuk Explorer"
-    Dependent:
-      - Id: 120096
-      - Id: 120097
-      - Id: 120098
-      - Id: 120099
-      - Id: 120100
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129019
-    Group: "AG_ADVENTURE"
-    Name: "Eclage Explorer"
-    Dependent:
-      - Id: 129017
-      - Id: 129018
-    Reward:
-      ItemID: 617
+  - Id: 129017
+    Group: Adventure
+    Name: Laphine Explorer
+    Dependents:
+      120090: true
+      120091: true
+      120092: true
+      120093: true
+      120094: true
+      120095: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129018
+    Group: Adventure
+    Name: Manuk Explorer
+    Dependents:
+      120096: true
+      120097: true
+      120098: true
+      120099: true
+      120100: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129019
+    Group: Adventure
+    Name: Eclage Explorer
+    Dependents:
+      129017: true
+      129018: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129020
-    Group: "AG_ADVENTURE"
-    Name: "Localizing fields explorer"
-    Dependent:
-      - Id: 120101
-      - Id: 120102
-      - Id: 120103
-      - Id: 120104
-      - Id: 120105
-      - Id: 120106
-      - Id: 120107
-      - Id: 120108
-      - Id: 120109
-    Reward:
-      ItemID: 617
+  - Id: 129020
+    Group: Adventure
+    Name: Localizing fields explorer
+    Dependents:
+      120101: true
+      120102: true
+      120103: true
+      120104: true
+      120105: true
+      120106: true
+      120107: true
+      120108: true
+      120109: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129021
-    Group: "AG_BATTLE"
-    Name: "Glastheim Challenge Mode" # Complete 100 times?
-    Reward:
-      TitleID: 1045
-    Score: 10
-  - ID: 130000 # Talk to Prince NPC (npc/quests/quests_morocc.txt L5288)
-    Group: "AG_CHATTING"
-    Name: "Socialite debut"
-    Reward:
-      TitleID: 1034
-    Score: 10
-  - ID: 170000
-    Group: "AG_HEAR"
-    Name: "Song chamber is not an accident"
-    Score: 10
-  - ID: 190000
-    Group: "AG_CHATTING"
-    Name: "Alliance workers of merchant city"
+  - Id: 129021
+    Group: Battle
+    Name: Glastheim Challenge Mode # Complete 100 times?
+    Rewards:
+      TitleId: 1045
+    Score: 10
+  - Id: 130000
+    Group: Chatting
+    Name: Socialite debut
+    Targets:
+      - Id: 0
+        Count: 1
+      - Id: 1
+        Count: 1
+      - Id: 2
+        Count: 1
+      - Id: 3
+        Count: 1
+      - Id: 4
+        Count: 1
+      - Id: 5
+        Count: 1
+      - Id: 6
+        Count: 1
+    Rewards:
+      TitleId: 1034
+    Score: 10
+  - Id: 170000
+    Group: Chatting
+    Name: Song chamber is not an accident
+    Targets:
+      - Id: 0
+        Count: 1
+    Score: 10
+  - Id: 190000
+    Group: Chatting
+    Name: Alliance workers of merchant city
+    Targets:
+      - Id: 0
+        Count: 1
+      - Id: 1
+        Count: 10
+      - Id: 2
+        Count: 30
+      - Id: 3
+        Count: 100
     Score: 50
     Score: 50
-  - ID: 200000
-    Group: "AG_GOAL_LEVEL"
-    Name: "Acquire the first aura!"
+  - Id: 200000
+    Group: Goal_Level
+    Name: Acquire the first aura!
     Condition: " BaseLevel >= 99 "
     Condition: " BaseLevel >= 99 "
-    Reward:
-      ItemID: 12549
+    Rewards:
+      Item: White_Slim_Pot_Box2
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1000
+      TitleId: 1000
     Score: 50
     Score: 50
-  - ID: 200001
-    Group: "AG_GOAL_LEVEL"
-    Name: "Acquire the second aura!"
+  - Id: 200001
+    Group: Goal_Level
+    Name: Acquire the second aura!
     Condition: " BaseLevel >= 150 "
     Condition: " BaseLevel >= 150 "
-    Dependent:
-      - Id: 200000
-    Reward:
-      ItemID: 5364
+    Dependents:
+      200000: true
+    Rewards:
+      Item: Dark_Snake_Lord_Hat
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1001
+      TitleId: 1001
     Score: 60
     Score: 60
-  - ID: 200002
-    Group: "AG_GOAL_LEVEL"
-    Name: "Acquire the third aura!"
+  - Id: 200002
+    Group: Goal_Level
+    Name: Acquire the third aura!
     Condition: " BaseLevel >= 175 "
     Condition: " BaseLevel >= 175 "
-    Dependent:
-      - Id: 200001
-    Reward:
-    #  ItemID: 18880
+    Dependents:
+      200001: true
+    Rewards:
+    #  Item: BLACKDEATHKING_GOLDEN
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1002
+      TitleId: 1002
     Score: 70
     Score: 70
-  - ID: 200003
-    Group: "AG_GOAL_LEVEL"
-    Name: "Master Job level!"
+  - Id: 200003
+    Group: Goal_Level
+    Name: Master Job level!
     Condition: " JobLevel >= 50 "
     Condition: " JobLevel >= 50 "
-    Reward:
-      ItemID: 617
+    Rewards:
+      Item: Old_Violet_Box
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1003
+      TitleId: 1003
     Score: 30
     Score: 30
-  - ID: 200004
-    Group: "AG_GOAL_LEVEL"
-    Name: "Grandmaster Job level!"
+  - Id: 200004
+    Group: Goal_Level
+    Name: Grandmaster Job level!
     Condition: " JobLevel >= 70 "
     Condition: " JobLevel >= 70 "
-    Dependent:
-      - Id: 200003
-    Reward:
-    #  ItemID: 12817
+    Dependents:
+      200003: true
+    Rewards:
+    #  Item: Old_Card_Album_
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1004
+      TitleId: 1004
     Score: 50
     Score: 50
-  - ID: 200005
-    Group: "AG_JOB_CHANGE"
-    Name: "Official Adventurer"
+  - Id: 200005
+    Group: Job_Change
+    Name: Official Adventurer
     Condition: " Class >= JOB_SWORDMAN && Class <= JOB_THIEF "
     Condition: " Class >= JOB_SWORDMAN && Class <= JOB_THIEF "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 200006
-    Group: "AG_JOB_CHANGE"
-    Name: "First step of job change!"
+  - Id: 200006
+    Group: Job_Change
+    Name: First step of job change!
     Condition: " Class >= JOB_SWORDMAN && Class <= JOB_THIEF "
     Condition: " Class >= JOB_SWORDMAN && Class <= JOB_THIEF "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 20
     Score: 20
-  - ID: 200007
-    Group: "AG_JOB_CHANGE"
-    Name: "Veteran Adventurer! (1)"
+  - Id: 200007
+    Group: Job_Change
+    Name: Veteran Adventurer! (1)
     Condition: " Class >= JOB_KNIGHT && Class <= JOB_ASSASSIN "
     Condition: " Class >= JOB_KNIGHT && Class <= JOB_ASSASSIN "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 25
     Score: 25
-  - ID: 200008
-    Group: "AG_JOB_CHANGE"
-    Name: "Veteran Adventurer! (2)"
+  - Id: 200008
+    Group: Job_Change
+    Name: Veteran Adventurer! (2)
     Condition: " Class >= JOB_CRUSADER && Class <= JOB_DANCER "
     Condition: " Class >= JOB_CRUSADER && Class <= JOB_DANCER "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 25
     Score: 25
-  - ID: 200009
-    Group: "AG_JOB_CHANGE"
-    Name: "Warrior (1)"
+  - Id: 200009
+    Group: Job_Change
+    Name: Warrior (1)
     Condition: " Class >= JOB_LORD_KNIGHT && Class <= JOB_ASSASSIN_CROSS "
     Condition: " Class >= JOB_LORD_KNIGHT && Class <= JOB_ASSASSIN_CROSS "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 30
     Score: 30
-  - ID: 200010
-    Group: "AG_JOB_CHANGE"
-    Name: "Warrior (2)"
+  - Id: 200010
+    Group: Job_Change
+    Name: Warrior (2)
     Condition: " Class >= JOB_PALADIN && Class <= JOB_GYPSY "
     Condition: " Class >= JOB_PALADIN && Class <= JOB_GYPSY "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 30
     Score: 30
-  - ID: 200011
-    Group: "AG_JOB_CHANGE"
-    Name: "Elite Adventurer! (1)"
+  - Id: 200011
+    Group: Job_Change
+    Name: Elite Adventurer! (1)
     Condition: " Class >= JOB_RUNE_KNIGHT && Class <= JOB_GUILLOTINE_CROSS "
     Condition: " Class >= JOB_RUNE_KNIGHT && Class <= JOB_GUILLOTINE_CROSS "
-    Reward:
-    #  ItemID: 16483
+    Rewards:
+    #  Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 50
     Score: 50
-  - ID: 200012
-    Group: "AG_JOB_CHANGE"
-    Name: "Transcendentaler! (1)"
+  - Id: 200012
+    Group: Job_Change
+    Name: Transcendentaler! (1)
     Condition: " Class >= JOB_RUNE_KNIGHT_T && Class <= JOB_GUILLOTINE_CROSS_T "
     Condition: " Class >= JOB_RUNE_KNIGHT_T && Class <= JOB_GUILLOTINE_CROSS_T "
-    Reward:
-    #  ItemID: 16483
+    Rewards:
+    #  Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 60
     Score: 60
-  - ID: 200013
-    Group: "AG_JOB_CHANGE"
-    Name: "Elite Adventurer! (2)"
+  - Id: 200013
+    Group: Job_Change
+    Name: Elite Adventurer! (2)
     Condition: " Class >= JOB_ROYAL_GUARD && Class <= JOB_SHADOW_CHASER "
     Condition: " Class >= JOB_ROYAL_GUARD && Class <= JOB_SHADOW_CHASER "
-    Reward:
-    #  ItemID: 16483
+    Rewards:
+    #  Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 50
     Score: 50
-  - ID: 200014
-    Group: "AG_JOB_CHANGE"
-    Name: "Transcendentaler! (2)"
+  - Id: 200014
+    Group: Job_Change
+    Name: Transcendentaler! (2)
     Condition: " Class >= JOB_ROYAL_GUARD_T && Class <= JOB_SHADOW_CHASER_T "
     Condition: " Class >= JOB_ROYAL_GUARD_T && Class <= JOB_SHADOW_CHASER_T "
-    Reward:
-    #  ItemID: 16483
+    Rewards:
+    #  Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 60
     Score: 60
-  - ID: 200015
-    Group: "AG_JOB_CHANGE"
-    Name: "The way of exceptional character"
+  - Id: 200015
+    Group: Job_Change
+    Name: The way of exceptional character
     Condition: " Class == JOB_SUPER_NOVICE || Class == JOB_GUNSLINGER || Class == JOB_NINJA || Class == JOB_TAEKWON "
     Condition: " Class == JOB_SUPER_NOVICE || Class == JOB_GUNSLINGER || Class == JOB_NINJA || Class == JOB_TAEKWON "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 200016
-    Group: "AG_JOB_CHANGE"
-    Name: "This is My way!"
+  - Id: 200016
+    Group: Job_Change
+    Name: This is My way!
     Condition: " Class == JOB_STAR_GLADIATOR || Class == JOB_SOUL_LINKER || Class == JOB_KAGEROU || Class == JOB_OBORO || Class == JOB_REBELLION "
     Condition: " Class == JOB_STAR_GLADIATOR || Class == JOB_SOUL_LINKER || Class == JOB_KAGEROU || Class == JOB_OBORO || Class == JOB_REBELLION "
-    Reward:
-    #  ItemID: 16483
+    Rewards:
+    #  Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 20
     Score: 20
-  - ID: 200017
-    Group: "AG_GOAL_STATUS"
-    Name: "Bearish Power!"
+  - Id: 200017
+    Group: Goal_Status
+    Name: Bearish Power!
     Condition: " readparam(bStr) >= 90 "
     Condition: " readparam(bStr) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200018
-    Group: "AG_GOAL_STATUS"
-    Name: "Overflowing Magic!"
+  - Id: 200018
+    Group: Goal_Status
+    Name: Overflowing Magic!
     Condition: " readparam(bInt) >= 90 "
     Condition: " readparam(bInt) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200019
-    Group: "AG_GOAL_STATUS"
-    Name: "Healthy Body and Mental Health!"
+  - Id: 200019
+    Group: Goal_Status
+    Name: Healthy Body and Mental Health!
     Condition: " readparam(bVit) >= 90 "
     Condition: " readparam(bVit) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200020
-    Group: "AG_GOAL_STATUS"
-    Name: "Speed of Light"
+  - Id: 200020
+    Group: Goal_Status
+    Name: Speed of Light
     Condition: " readparam(bAgi) >= 90 "
     Condition: " readparam(bAgi) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200021
-    Group: "AG_GOAL_STATUS"
-    Name: "Hawk Eyes"
+  - Id: 200021
+    Group: Goal_Status
+    Name: Hawk Eyes
     Condition: " readparam(bDex) >= 90 "
     Condition: " readparam(bDex) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200022
-    Group: "AG_GOAL_STATUS"
-    Name: "Maximum Luck"
+  - Id: 200022
+    Group: Goal_Status
+    Name: Maximum Luck
     Condition: " readparam(bLuk) >= 90 "
     Condition: " readparam(bLuk) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200023
-    Group: "AG_GOAL_STATUS"
-    Name: "Dragonlike Power!"
+  - Id: 200023
+    Group: Goal_Status
+    Name: Dragonlike Power!
     Condition: " readparam(bStr) >= 125 "
     Condition: " readparam(bStr) >= 125 "
-    Reward:
+    Rewards:
       Script: " sc_start SC_GIANTGROWTH,180000,1; "
       Script: " sc_start SC_GIANTGROWTH,180000,1; "
     Score: 20
     Score: 20
-  - ID: 200024
-    Group: "AG_GOAL_STATUS"
-    Name: "Magic Insanity"
+  - Id: 200024
+    Group: Goal_Status
+    Name: Magic Insanity
     Condition: " readparam(bInt) >= 125 "
     Condition: " readparam(bInt) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_HASTEUP; bonus_script \"{ bonus2 bHPLossRate,100,10000; bonus bBaseAtk,20; bonus bAspdRate,25; }\",60,0,0,EFST_STEAMPACK; "
       Script: " specialeffect2 EF_HASTEUP; bonus_script \"{ bonus2 bHPLossRate,100,10000; bonus bBaseAtk,20; bonus bAspdRate,25; }\",60,0,0,EFST_STEAMPACK; "
     Score: 20
     Score: 20
-  - ID: 200025
-    Group: "AG_GOAL_STATUS"
-    Name: "Rock Alloy"
+  - Id: 200025
+    Group: Goal_Status
+    Name: Rock Alloy
     Condition: " readparam(bVit) >= 125 "
     Condition: " readparam(bVit) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_HEAL3; sc_start2 SC_S_LIFEPOTION,600000,-5,5; "
       Script: " specialeffect2 EF_HEAL3; sc_start2 SC_S_LIFEPOTION,600000,-5,5; "
     Score: 20
     Score: 20
-  - ID: 200026
-    Group: "AG_GOAL_STATUS"
-    Name: "Speed of Light"
+  - Id: 200026
+    Group: Goal_Status
+    Name: Speed of Light
     Condition: " readparam(bAgi) >= 125 "
     Condition: " readparam(bAgi) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_STEAL; sc_start SC_INCFLEE2,60000,20; "
       Script: " specialeffect2 EF_STEAL; sc_start SC_INCFLEE2,60000,20; "
     Score: 20
     Score: 20
-  - ID: 200027
-    Group: "AG_GOAL_STATUS"
-    Name: "Falcon's Eyes"
+  - Id: 200027
+    Group: Goal_Status
+    Name: Falcon's Eyes
     Condition: " readparam(bDex) >= 125 "
     Condition: " readparam(bDex) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_MAGICALATTHIT; sc_start SC_INCCRI,300000,30; "
       Script: " specialeffect2 EF_MAGICALATTHIT; sc_start SC_INCCRI,300000,30; "
     Score: 20
     Score: 20
-  - ID: 200028
-    Group: "AG_GOAL_STATUS"
-    Name: "Lucky Fever"
+  - Id: 200028
+    Group: Goal_Status
+    Name: Lucky Fever
     Condition: " readparam(bLuk) >= 125 "
     Condition: " readparam(bLuk) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_GLORIA; sc_start SC_GLORIA,15000,0; "
       Script: " specialeffect2 EF_GLORIA; sc_start SC_GLORIA,15000,0; "
     Score: 20
     Score: 20
-  - ID: 200029
-    Group: "AG_GOAL_STATUS"
-    Name: "Incarnation of Love and Hate"
+  - Id: 200029
+    Group: Goal_Status
+    Name: Incarnation of Love and Hate
     Condition: " BaseLevel == 99 && Class == JOB_NOVICE "
     Condition: " BaseLevel == 99 && Class == JOB_NOVICE "
-    Reward:
-    #  ItemID: 16483
+    Rewards:
+    #  Item: Abrasive_Box_10
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
     Score: 30
     Score: 30
-  - ID: 200030
-    Group: "AG_GOAL_STATUS"
-    Name: "I really love it!"
+  - Id: 200030
+    Group: Goal_Status
+    Name: I really love it!
     Condition: " BaseLevel == 99 && (Class >= JOB_SWORDMAN && Class <= JOB_THIEF) "
     Condition: " BaseLevel == 99 && (Class >= JOB_SWORDMAN && Class <= JOB_THIEF) "
-    Reward:
-    #  ItemID: 16504
+    Rewards:
+    #  Item: Bubble_Gum_Box_10
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
     Score: 30
     Score: 30
-  - ID: 200031
-    Group: "AG_JOB_CHANGE"
-    Name: "Reborn in Valhalla!"
+  - Id: 200031
+    Group: Job_Change
+    Name: Reborn in Valhalla!
     Condition: " Class == JOB_NOVICE_HIGH "
     Condition: " Class == JOB_NOVICE_HIGH "
-    Reward:
-    #  ItemID: 23575
+    Rewards:
+    #  Item: Adventurer_Box_1
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 200032
-    Group: "AG_GOAL_LEVEL"
-    Name: "The start of another adventure!"
+  - Id: 200032
+    Group: Goal_Level
+    Name: The start of another adventure!
     Condition: " BaseLevel == 100 "
     Condition: " BaseLevel == 100 "
-    #Reward:
-    #  ItemID: 23585
+    #Rewards:
+    #  Item: Rebeginer_Box_100
     Score: 10
     Score: 10
-  - ID: 200033
-    Group: "AG_GOAL_LEVEL"
-    Name: "With a new mind!(1)"
+  - Id: 200033
+    Group: Goal_Level
+    Name: With a new mind!(1)
     Condition: " BaseLevel == 170 && (Class >= JOB_RUNE_KNIGHT && Class <= JOB_GUILLOTINE_CROSS_T) "
     Condition: " BaseLevel == 170 && (Class >= JOB_RUNE_KNIGHT && Class <= JOB_GUILLOTINE_CROSS_T) "
-    #Reward:
-    #  ItemID: 6959
+    #Rewards:
+    #  Item: Costume_Ticket
     Score: 50
     Score: 50
-  - ID: 200034
-    Group: "AG_GOAL_LEVEL"
-    Name: "With a new mind!(2)"
+  - Id: 200034
+    Group: Goal_Level
+    Name: With a new mind!(2)
     Condition: " BaseLevel == 170 && (Class >= JOB_ROYAL_GUARD && Class <= JOB_SHADOW_CHASER_T) "
     Condition: " BaseLevel == 170 && (Class >= JOB_ROYAL_GUARD && Class <= JOB_SHADOW_CHASER_T) "
-    #Reward:
-    #  ItemID: 6959
+    #Rewards:
+    #  Item: Costume_Ticket
     Score: 50
     Score: 50
-  - ID: 220000
-    Group: "AG_CHATTING_CREATE"
-    Name: "Community begin"
+  - Id: 220000
+    Group: Chatting_Create
+    Name: Community begin
+    Condition: " ARG0 == 1 "
     Score: 10
     Score: 10
-  - ID: 220001
-    Group: "AG_CHATTING_DYING"
-    Name: "A mouth only moment"
+  - Id: 220001
+    Group: Chatting_Dying
+    Name: A mouth only moment
+    Condition: " ARG0 == 1 "
     Score: 10
     Score: 10
-  - ID: 220002
-    Group: "AG_CHATTING_COUNT"
-    Name: "Admiring the chatter"
+  - Id: 220002
+    Group: Chatting_Count
+    Name: Admiring the chatter
     Condition: " ARG0 == 20 "
     Condition: " ARG0 == 20 "
     Score: 10
     Score: 10
-  - ID: 220003
-    Group: "AG_ADD_FRIEND"
-    Name: "My friend's friend~"
+  - Id: 220003
+    Group: Add_Friend
+    Name: My friend's friend~
     Condition: " ARG0 >= 1 "
     Condition: " ARG0 >= 1 "
     Score: 10
     Score: 10
-  - ID: 220004
-    Group: "AG_ADD_FRIEND"
-    Name: "A competition of popularity"
+  - Id: 220004
+    Group: Add_Friend
+    Name: A competition of popularity
     Condition: " ARG0 >= 10 "
     Condition: " ARG0 >= 10 "
     Score: 10
     Score: 10
-  - ID: 220005
-    Group: "AG_PARTY"
-    Name: "Let's Party~"
+  - Id: 220005
+    Group: Party
+    Name: Let's Party~
+    Condition: " ARG0 == 1 "
     Score: 10
     Score: 10
-  - ID: 220006
-    Group: "AG_MARRY"
-    Name: "Married with who..?"
-    Reward:
-      TitleID: 1022
+  - Id: 220006
+    Group: Marry
+    Name: Married with who..?
+    Rewards:
+      TitleId: 1022
     Score: 20
     Score: 20
-  - ID: 220007
-    Group: "AG_BABY"
-    Name: "Can you grow?"
+  - Id: 220007
+    Group: Baby
+    Name: Can you grow?
     Condition: " ARG0 == 1 "
     Condition: " ARG0 == 1 "
-    Reward:
-      TitleID: 1032
+    Rewards:
+      TitleId: 1032
     Score: 20
     Score: 20
-  - ID: 220008
-    Group: "AG_BABY"
-    Name: "Being a parent"
+  - Id: 220008
+    Group: Baby
+    Name: Being a parent
     Condition: " ARG0 == 2 "
     Condition: " ARG0 == 2 "
-    Reward:
-      TitleID: 1033
+    Rewards:
+      TitleId: 1033
     Score: 20
     Score: 20
-  - ID: 220009
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (1)"
-    Condition: " ARG0 >= 10000 "
-    Target:
+  - Id: 220009
+    Group: Spend_Zeny
+    Name: Activating the market economy (1)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 10000
         Count: 10000
+    Condition: " ARG0 >= 10000 "
     Score: 10
     Score: 10
-  - ID: 220010
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (2)"
-    Condition: " ARG0 >= 100000 "
-    Target:
+  - Id: 220010
+    Group: Spend_Zeny
+    Name: Activating the market economy (2)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 100000
         Count: 100000
+    Condition: " ARG0 >= 100000 "
     Score: 15
     Score: 15
-  - ID: 220011
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (3)"
-    Condition: " ARG0 >= 500000 "
-    Target:
+  - Id: 220011
+    Group: Spend_Zeny
+    Name: Activating the market economy (3)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 500000
         Count: 500000
+    Condition: " ARG0 >= 500000 "
     Score: 20
     Score: 20
-  - ID: 220012
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (4)"
-    Condition: " ARG0 >= 1000000 "
-    Target:
+  - Id: 220012
+    Group: Spend_Zeny
+    Name: Activating the market economy (4)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 1000000
         Count: 1000000
+    Condition: " ARG0 >= 1000000 "
     Score: 30
     Score: 30
-  - ID: 220013
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (5)"
-    Condition: " ARG0 >= 5000000 "
-    Target:
+  - Id: 220013
+    Group: Spend_Zeny
+    Name: Activating the market economy (5)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 5000000
         Count: 5000000
+    Condition: " ARG0 >= 5000000 "
     Score: 50
     Score: 50
-  - ID: 220014
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (1)"
+  - Id: 220014
+    Group: Enchant_Success
+    Name: I can't quit from refining! (1)
     Condition: " ARG0 == 1 && ARG1 >= 7 "
     Condition: " ARG0 == 1 && ARG1 >= 7 "
     Score: 10
     Score: 10
-  - ID: 220015
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (2)"
+  - Id: 220015
+    Group: Enchant_Success
+    Name: I can't quit from refining! (2)
     Condition: " ARG0 == 1 && ARG1 >= 12 "
     Condition: " ARG0 == 1 && ARG1 >= 12 "
     Score: 15
     Score: 15
-  - ID: 220016
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (3)"
+  - Id: 220016
+    Group: Enchant_Success
+    Name: I can't quit from refining! (3)
     Condition: " ARG0 == 2 && ARG1 >= 7 "
     Condition: " ARG0 == 2 && ARG1 >= 7 "
     Score: 10
     Score: 10
-  - ID: 220017
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (4)"
+  - Id: 220017
+    Group: Enchant_Success
+    Name: I can't quit from refining! (4)
     Condition: " ARG0 == 2 && ARG1 >= 12 "
     Condition: " ARG0 == 2 && ARG1 >= 12 "
     Score: 15
     Score: 15
-  - ID: 220018
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (5)"
+  - Id: 220018
+    Group: Enchant_Success
+    Name: I can't quit from refining! (5)
     Condition: " ARG0 == 3 && ARG1 >= 7 "
     Condition: " ARG0 == 3 && ARG1 >= 7 "
     Score: 15
     Score: 15
-  - ID: 220019
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (6)"
+  - Id: 220019
+    Group: Enchant_Success
+    Name: I can't quit from refining! (6)
     Condition: " ARG0 == 3 && ARG1 >= 12 "
     Condition: " ARG0 == 3 && ARG1 >= 12 "
     Score: 20
     Score: 20
-  - ID: 220020
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (7)"
+  - Id: 220020
+    Group: Enchant_Success
+    Name: I can't quit from refining! (7)
     Condition: " ARG0 == 4 && ARG1 >= 7 "
     Condition: " ARG0 == 4 && ARG1 >= 7 "
     Score: 20
     Score: 20
-  - ID: 220021
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (8)"
+  - Id: 220021
+    Group: Enchant_Success
+    Name: I can't quit from refining! (8)
     Condition: " ARG0 == 4 && ARG1 >= 12 "
     Condition: " ARG0 == 4 && ARG1 >= 12 "
     Score: 30
     Score: 30
-  - ID: 220022
-    Group: "AG_ENCHANT_FAIL"
-    Name: "Human's greed has no ending.."
+  - Id: 220022
+    Group: Enchant_Fail
+    Name: Human's greed has no ending..
+    Condition: " ARG0 == 1 "
     Score: 10
     Score: 10
-  - ID: 220023
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (1)"
+  - Id: 220023
+    Group: Get_Item
+    Name: I found it! (1)
     Condition: " ARG0 >= 100 "
     Condition: " ARG0 >= 100 "
     Score: 10
     Score: 10
-  - ID: 220024
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (2)"
+  - Id: 220024
+    Group: Get_Item
+    Name: I found it! (2)
     Condition: " ARG0 >= 1000 "
     Condition: " ARG0 >= 1000 "
     Score: 10
     Score: 10
-  - ID: 220025
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (3)"
+  - Id: 220025
+    Group: Get_Item
+    Name: I found it! (3)
     Condition: " ARG0 >= 5000 "
     Condition: " ARG0 >= 5000 "
     Score: 15
     Score: 15
-  - ID: 220026
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (4)"
+  - Id: 220026
+    Group: Get_Item
+    Name: I found it! (4)
     Condition: " ARG0 >= 10000 "
     Condition: " ARG0 >= 10000 "
     Score: 15
     Score: 15
-  - ID: 220027
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (5)"
+  - Id: 220027
+    Group: Get_Item
+    Name: I found it! (5)
     Condition: " ARG0 >= 50000 "
     Condition: " ARG0 >= 50000 "
     Score: 20
     Score: 20
-  - ID: 220028
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (6)"
+  - Id: 220028
+    Group: Get_Item
+    Name: I found it! (6)
     Condition: " ARG0 >= 100000 "
     Condition: " ARG0 >= 100000 "
     Score: 20
     Score: 20
-  - ID: 220029
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (7)"
+  - Id: 220029
+    Group: Get_Item
+    Name: I found it! (7)
     Condition: " ARG0 >= 150000 "
     Condition: " ARG0 >= 150000 "
     Score: 30
     Score: 30
-  - ID: 220030
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (1)"
+  - Id: 220030
+    Group: Get_Zeny
+    Name: Rich King (1)
     Condition: " ARG0 >= 10000 "
     Condition: " ARG0 >= 10000 "
     Score: 10
     Score: 10
-  - ID: 220031
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (2)"
+  - Id: 220031
+    Group: Get_Zeny
+    Name: Rich King (2)
     Condition: " ARG0 >= 100000 "
     Condition: " ARG0 >= 100000 "
     Score: 15
     Score: 15
-  - ID: 220032
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (3)"
+  - Id: 220032
+    Group: Get_Zeny
+    Name: Rich King (3)
     Condition: " ARG0 >= 1000000 "
     Condition: " ARG0 >= 1000000 "
     Score: 20
     Score: 20
-  - ID: 220033
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (4)"
+  - Id: 220033
+    Group: Get_Zeny
+    Name: Rich King (4)
     Condition: " ARG0 >= 10000000 "
     Condition: " ARG0 >= 10000000 "
     Score: 25
     Score: 25
-  - ID: 220034
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (5)"
+  - Id: 220034
+    Group: Get_Zeny
+    Name: Rich King (5)
     Condition: " ARG0 >= 100000000 "
     Condition: " ARG0 >= 100000000 "
     Score: 30
     Score: 30
-  - ID: 220035
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (6)"
+  - Id: 220035
+    Group: Get_Zeny
+    Name: Rich King (6)
     Condition: " ARG0 >= 1000000000 "
     Condition: " ARG0 >= 1000000000 "
     Score: 40
     Score: 40
-  - ID: 230100
-    Group: "AG_TAMING"
-    Name: "Poring is Love"
-    Dependent:
-      - Id: 230101
-      - Id: 230102
-      - Id: 230103
-      - Id: 230104
-    Reward:
+  - Id: 230100
+    Group: Taming
+    Name: Poring is Love
+    Dependents:
+      230101: true
+      230102: true
+      230103: true
+      230104: true
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1025
+      TitleId: 1025
     Score: 50
     Score: 50
-  - ID: 230110
-    Group: "AG_TAMING"
-    Name: "Entomologist"
-    Dependent:
-      - Id: 230111
-      - Id: 230112
-      - Id: 230113
-      - Id: 230114
-      - Id: 230115
-      - Id: 230116
-    Reward:
+  - Id: 230110
+    Group: Taming
+    Name: Entomologist
+    Dependents:
+      230111: true
+      230112: true
+      230113: true
+      230114: true
+      230115: true
+      230116: true
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1026
+      TitleId: 1026
     Score: 50
     Score: 50
-  - ID: 230120
-    Group: "AG_TAMING"
-    Name: "Animals are also our friend"
-    Dependent:
-      - Id: 230121
-      - Id: 230122
-      - Id: 230123
-      - Id: 230124
-      - Id: 230125
-      - Id: 230126
-      - Id: 230127
-      - Id: 230128
-    Reward:
+  - Id: 230120
+    Group: Taming
+    Name: Animals are also our friend
+    Dependents:
+      230121: true
+      230122: true
+      230123: true
+      230124: true
+      230125: true
+      230126: true
+      230127: true
+      230128: true
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1027
+      TitleId: 1027
     Score: 50
     Score: 50
-  - ID: 230140
-    Group: "AG_TAMING"
-    Name: "Monster Girls Unite!!"
-    Dependent:
-      - Id: 230141
-      - Id: 230142
-      - Id: 230143
-      - Id: 230144
-      - Id: 230145
-      - Id: 230146
-      - Id: 230147
-    Reward:
+  - Id: 230140
+    Group: Taming
+    Name: Monster Girls Unite!!
+    Dependents:
+      230141: true
+      230142: true
+      230143: true
+      230144: true
+      230145: true
+      230146: true
+      230147: true
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1029
+      TitleId: 1029
     Score: 50
     Score: 50
-  - ID: 230101
-    Group: "AG_TAMING"
-    Name: "Poring - taming"
-    Target:
+  - Id: 230101
+    Group: Taming
+    Name: Poring - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1002
-        Count: 1
+        Mob: PORING
     Score: 10
     Score: 10
-  - ID: 230102
-    Group: "AG_TAMING"
-    Name: "Drops - taming"
-    Target:
+  - Id: 230102
+    Group: Taming
+    Name: Drops - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1113
-        Count: 1
+        Mob: DROPS
     Score: 10
     Score: 10
-  - ID: 230103
-    Group: "AG_TAMING"
-    Name: "Poporing - taming"
-    Target:
+  - Id: 230103
+    Group: Taming
+    Name: Poporing - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1031
-        Count: 1
+        Mob: POPORING
     Score: 10
     Score: 10
-  - ID: 230104
-    Group: "AG_TAMING"
-    Name: "Novice Poring - taming"
-    #Target:
+  - Id: 230104
+    Group: Taming
+    Name: Novice Poring - taming
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 2398
-    #    Count: 1
+    #    Mob: LITTLE_PORING
     Score: 10
     Score: 10
-  - ID: 230111
-    Group: "AG_TAMING"
-    Name: "Chonchon - taming"
-    Target:
+  - Id: 230111
+    Group: Taming
+    Name: Chonchon - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1011
-        Count: 1
+        Mob: CHONCHON
     Score: 10
     Score: 10
-  - ID: 230112
-    Group: "AG_TAMING"
-    Name: "Steel Chonchon - taming"
-    Target:
+  - Id: 230112
+    Group: Taming
+    Name: Steel Chonchon - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1042
-        Count: 1
+        Mob: STEEL_CHONCHON
     Score: 10
     Score: 10
-  - ID: 230113
-    Group: "AG_TAMING"
-    Name: "Hunter Fly - taming"
-    Target:
+  - Id: 230113
+    Group: Taming
+    Name: Hunter Fly - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1035
-        Count: 1
+        Mob: HUNTER_FLY
     Score: 10
     Score: 10
-  - ID: 230114
-    Group: "AG_TAMING"
-    Name: "Rocker - taming"
-    Target:
+  - Id: 230114
+    Group: Taming
+    Name: Rocker - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1052
-        Count: 1
+        Mob: ROCKER
     Score: 10
     Score: 10
-  - ID: 230115
-    Group: "AG_TAMING"
-    Name: "Spore - taming"
-    Target:
+  - Id: 230115
+    Group: Taming
+    Name: Spore - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1014
-        Count: 1
+        Mob: SPORE
     Score: 10
     Score: 10
-  - ID: 230116
-    Group: "AG_TAMING"
-    Name: "Poison Spore - taming"
-    Target:
+  - Id: 230116
+    Group: Taming
+    Name: Poison Spore - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1077
-        Count: 1
+        Mob: POISON_SPORE
     Score: 10
     Score: 10
-  - ID: 230121
-    Group: "AG_TAMING"
-    Name: "Lunatic - taming"
-    Target:
+  - Id: 230121
+    Group: Taming
+    Name: Lunatic - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1063
-        Count: 1
+        Mob: LUNATIC
     Score: 10
     Score: 10
-  - ID: 230122
-    Group: "AG_TAMING"
-    Name: "Picky - taming"
-    Target:
+  - Id: 230122
+    Group: Taming
+    Name: Picky - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1049
-        Count: 1
+        Mob: PICKY
     Score: 10
     Score: 10
-  - ID: 230123
-    Group: "AG_TAMING"
-    Name: "Savage Bebe - taming"
-    Target:
+  - Id: 230123
+    Group: Taming
+    Name: Savage Bebe - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1167
-        Count: 1
+        Mob: SAVAGE_BABE
     Score: 10
     Score: 10
-  - ID: 230124
-    Group: "AG_TAMING"
-    Name: "Baby Desert Wolf - taming"
-    Target:
+  - Id: 230124
+    Group: Taming
+    Name: Baby Desert Wolf - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1107
-        Count: 1
+        Mob: DESERT_WOLF_B
     Score: 10
     Score: 10
-  - ID: 230125
-    Group: "AG_TAMING"
-    Name: "Smokie - taming"
-    Target:
+  - Id: 230125
+    Group: Taming
+    Name: Smokie - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1056
-        Count: 1
+        Mob: SMOKIE
     Score: 10
     Score: 10
-  - ID: 230126
-    Group: "AG_TAMING"
-    Name: "Yoyo - taming"
-    Target:
+  - Id: 230126
+    Group: Taming
+    Name: Yoyo - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1057
-        Count: 1
+        Mob: YOYO
     Score: 10
     Score: 10
-  - ID: 230127
-    Group: "AG_TAMING"
-    Name: "Peco Peco - taming"
-    Target:
+  - Id: 230127
+    Group: Taming
+    Name: Peco Peco - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1019
-        Count: 1
+        Mob: PECOPECO
     Score: 10
     Score: 10
-  - ID: 230128
-    Group: "AG_TAMING"
-    Name: "Petite - taming"
-    Target:
+  - Id: 230128
+    Group: Taming
+    Name: Petite - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1155
-        Count: 1
+        Mob: PETIT
     Score: 10
     Score: 10
-  - ID: 230141
-    Group: "AG_TAMING"
-    Name: "Munak - taming"
-    Target:
+  - Id: 230141
+    Group: Taming
+    Name: Munak - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1026
-        Count: 1
+        Mob: MUNAK
     Score: 10
     Score: 10
-  - ID: 230142
-    Group: "AG_TAMING"
-    Name: "Isis - taming"
-    Target:
+  - Id: 230142
+    Group: Taming
+    Name: Isis - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1029
-        Count: 1
+        Mob: ISIS
     Score: 10
     Score: 10
-  - ID: 230143
-    Group: "AG_TAMING"
-    Name: "Sohee - taming"
-    Target:
+  - Id: 230143
+    Group: Taming
+    Name: Sohee - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1170
-        Count: 1
+        Mob: SOHEE
     Score: 10
     Score: 10
-  - ID: 230144
-    Group: "AG_TAMING"
-    Name: "Zherlthsh - taming"
-    Target:
+  - Id: 230144
+    Group: Taming
+    Name: Zherlthsh - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1200
-        Count: 1
+        Mob: ZHERLTHSH
     Score: 10
     Score: 10
-  - ID: 230145
-    Group: "AG_TAMING"
-    Name: "Alice - taming"
-    Target:
+  - Id: 230145
+    Group: Taming
+    Name: Alice - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1275
-        Count: 1
+        Mob: ALICE
     Score: 10
     Score: 10
-  - ID: 230146
-    Group: "AG_TAMING"
-    Name: "Succubus - taming"
-    Target:
+  - Id: 230146
+    Group: Taming
+    Name: Succubus - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1370
-        Count: 1
+        Mob: SUCCUBUS
     Score: 10
     Score: 10
-  - ID: 230147
-    Group: "AG_TAMING"
-    Name: "Loli Ruri - taming"
-    Target:
+  - Id: 230147
+    Group: Taming
+    Name: Loli Ruri - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1505
-        Count: 1
-    Score: 10
-  - ID: 230200
-    Group: "AG_BATTLE"
-    Name: "Poring seeker"
-    Dependent:
-      - Id: 230201
-      - Id: 230202
-      - Id: 230203
-    Score: 10
-  - ID: 230201
-    Group: "AG_BATTLE"
-    Name: "Exploring Poring's life (1)"
-    Target:
+        Mob: LOLI_RURI
+    Score: 10
+  - Id: 230200
+    Group: Battle
+    Name: Poring seeker
+    Dependents:
+      230201: true
+      230202: true
+      230203: true
+    Score: 10
+  - Id: 230201
+    Group: Battle
+    Name: Exploring Poring's life (1)
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1002
+        Mob: PORING
         Count: 10
         Count: 10
     #  - Id: 1
     #  - Id: 1
-    #    MobID: 2398
+    #    Mob: LITTLE_PORING
     #    Count: 10
     #    Count: 10
       - Id: 2
       - Id: 2
-        MobID: 1113
+        Mob: DROPS
         Count: 10
         Count: 10
       - Id: 3
       - Id: 3
-        MobID: 1031
+        Mob: POPORING
         Count: 10
         Count: 10
       - Id: 4
       - Id: 4
-        MobID: 1242
+        Mob: MARIN
         Count: 10
         Count: 10
     Score: 10
     Score: 10
-  - ID: 230202
-    Group: "AG_BATTLE"
-    Name: "Exploring Poring's life (2)"
-    Target:
+  - Id: 230202
+    Group: Battle
+    Name: Exploring Poring's life (2)
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1090
-        Count: 1
+        Mob: MASTERING
       - Id: 1
       - Id: 1
-        MobID: 1582
-        Count: 1
+        Mob: DEVILING
       - Id: 2
       - Id: 2
-        MobID: 1096
-        Count: 1
+        Mob: ANGELING
       - Id: 3
       - Id: 3
-        MobID: 1388
-        Count: 1
+        Mob: ARCHANGELING
       - Id: 4
       - Id: 4
-        MobID: 1120
-        Count: 1
+        Mob: GHOSTRING
     Score: 20
     Score: 20
-  - ID: 230203
-    Group: "AG_BATTLE"
-    Name: "Exploring Poring's life (3)"
-    Target:
+  - Id: 230203
+    Group: Battle
+    Name: Exploring Poring's life (3)
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1613
+        Mob: METALING
         Count: 5
         Count: 5
       - Id: 1
       - Id: 1
-        MobID: 1977
+        Mob: HEAVY_METALING
         Count: 5
         Count: 5
       - Id: 2
       - Id: 2
-        MobID: 1836
+        Mob: MAGMARING
         Count: 5
         Count: 5
     Score: 20
     Score: 20
-  - ID: 240000
-    Group: "AG_GOAL_LEVEL"
-    Name: "First Login after the introduction of Achievement Tasks"
-    Score: 10
+  - Id: 240000
+    Group: Goal_Level
+    Name: First Login after the introduction of Achievement Tasks
     Condition: " true "
     Condition: " true "
-  - ID: 240001
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 1"
+    Score: 10
+  - Id: 240001
+    Group: Goal_Achieve
+    Name: Reaching Level 1
     Condition: " AchievementLevel >= 1 "
     Condition: " AchievementLevel >= 1 "
-    Reward:
-      ItemID: 644
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240002
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 2"
+  - Id: 240002
+    Group: Goal_Achieve
+    Name: Reaching Level 2
     Condition: " AchievementLevel >= 2 "
     Condition: " AchievementLevel >= 2 "
-    Dependent:
-      - Id: 240001
-    Reward:
-      ItemID: 644
+    Dependents:
+      240001: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240003
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 3"
+  - Id: 240003
+    Group: Goal_Achieve
+    Name: Reaching Level 3
     Condition: " AchievementLevel >= 3 "
     Condition: " AchievementLevel >= 3 "
-    Dependent:
-      - Id: 240002
-    Reward:
-      ItemID: 644
+    Dependents:
+      240002: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240004
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 4"
+  - Id: 240004
+    Group: Goal_Achieve
+    Name: Reaching Level 4
     Condition: " AchievementLevel >= 4 "
     Condition: " AchievementLevel >= 4 "
-    Dependent:
-      - Id: 240003
-    Reward:
-      ItemID: 644
+    Dependents:
+      240003: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240005
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 5"
+  - Id: 240005
+    Group: Goal_Achieve
+    Name: Reaching Level 5
     Condition: " AchievementLevel >= 5 "
     Condition: " AchievementLevel >= 5 "
-    Dependent:
-      - Id: 240004
-    Reward:
-      ItemID: 644
+    Dependents:
+      240004: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240006
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 6"
+  - Id: 240006
+    Group: Goal_Achieve
+    Name: Reaching Level 6
     Condition: " AchievementLevel >= 6 "
     Condition: " AchievementLevel >= 6 "
-    Dependent:
-      - Id: 240005
-    Reward:
-      ItemID: 644
+    Dependents:
+      240005: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240007
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 7"
+  - Id: 240007
+    Group: Goal_Achieve
+    Name: Reaching Level 7
     Condition: " AchievementLevel >= 7 "
     Condition: " AchievementLevel >= 7 "
-    Dependent:
-      - Id: 240006
-    Reward:
-      ItemID: 644
+    Dependents:
+      240006: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240008
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 8"
+  - Id: 240008
+    Group: Goal_Achieve
+    Name: Reaching Level 8
     Condition: " AchievementLevel >= 8 "
     Condition: " AchievementLevel >= 8 "
-    Dependent:
-      - Id: 240007
-    Reward:
-      ItemID: 644
+    Dependents:
+      240007: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240009
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 9"
+  - Id: 240009
+    Group: Goal_Achieve
+    Name: Reaching Level 9
     Condition: " AchievementLevel >= 9 "
     Condition: " AchievementLevel >= 9 "
-    Dependent:
-      - Id: 240008
-    Reward:
-      ItemID: 644
+    Dependents:
+      240008: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240010
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 10"
+  - Id: 240010
+    Group: Goal_Achieve
+    Name: Reaching Level 10
     Condition: " AchievementLevel >= 10 "
     Condition: " AchievementLevel >= 10 "
-    Dependent:
-      - Id: 240009
-    Reward:
-      ItemID: 644
+    Dependents:
+      240009: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1023
+      TitleId: 1023
     Score: 10
     Score: 10
-  - ID: 240011
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 11"
+  - Id: 240011
+    Group: Goal_Achieve
+    Name: Reaching Level 11
     Condition: " AchievementLevel >= 11 "
     Condition: " AchievementLevel >= 11 "
-    Dependent:
-      - Id: 240010
-    Reward:
-      ItemID: 644
+    Dependents:
+      240010: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240012
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 12"
+  - Id: 240012
+    Group: Goal_Achieve
+    Name: Reaching Level 12
     Condition: " AchievementLevel >= 12 "
     Condition: " AchievementLevel >= 12 "
-    Dependent:
-      - Id: 240011
-    Reward:
-      ItemID: 644
+    Dependents:
+      240011: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240013
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 13"
+  - Id: 240013
+    Group: Goal_Achieve
+    Name: Reaching Level 13
     Condition: " AchievementLevel >= 13 "
     Condition: " AchievementLevel >= 13 "
-    Dependent:
-      - Id: 240012
-    Reward:
-      ItemID: 644
+    Dependents:
+      240012: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240014
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 14"
+  - Id: 240014
+    Group: Goal_Achieve
+    Name: Reaching Level 14
     Condition: " AchievementLevel >= 14 "
     Condition: " AchievementLevel >= 14 "
-    Dependent:
-      - Id: 240013
-    Reward:
-      ItemID: 644
+    Dependents:
+      240013: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240015
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 15"
+  - Id: 240015
+    Group: Goal_Achieve
+    Name: Reaching Level 15
     Condition: " AchievementLevel >= 15 "
     Condition: " AchievementLevel >= 15 "
-    Dependent:
-      - Id: 240014
-    Reward:
-      ItemID: 644
+    Dependents:
+      240014: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240016
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 16"
+  - Id: 240016
+    Group: Goal_Achieve
+    Name: Reaching Level 16
     Condition: " AchievementLevel >= 16 "
     Condition: " AchievementLevel >= 16 "
-    Dependent:
-      - Id: 240015
-    Reward:
-      ItemID: 644
+    Dependents:
+      240015: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240017
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 17"
+  - Id: 240017
+    Group: Goal_Achieve
+    Name: Reaching Level 17
     Condition: " AchievementLevel >= 17 "
     Condition: " AchievementLevel >= 17 "
-    Dependent:
-      - Id: 240016
-    Reward:
-      ItemID: 644
+    Dependents:
+      240016: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240018
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 18"
+  - Id: 240018
+    Group: Goal_Achieve
+    Name: Reaching Level 18
     Condition: " AchievementLevel >= 18 "
     Condition: " AchievementLevel >= 18 "
-    Dependent:
-      - Id: 240017
-    Reward:
-      ItemID: 644
+    Dependents:
+      240017: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240019
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 19"
+  - Id: 240019
+    Group: Goal_Achieve
+    Name: Reaching Level 19
     Condition: " AchievementLevel >= 19 "
     Condition: " AchievementLevel >= 19 "
-    Dependent:
-      - Id: 240018
-    Reward:
-      ItemID: 644
+    Dependents:
+      240018: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240020
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 20"
+  - Id: 240020
+    Group: Goal_Achieve
+    Name: Reaching Level 20
     Condition: " AchievementLevel >= 20 "
     Condition: " AchievementLevel >= 20 "
-    Dependent:
-      - Id: 240019
-    Reward:
-      ItemID: 644
+    Dependents:
+      240019: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1024
+      TitleId: 1024
     Score: 10
     Score: 10

+ 3 - 4
db/pre-re/achievement_level_db.yml

@@ -16,15 +16,14 @@
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 #
 #
 ###########################################################################
 ###########################################################################
-# Pre-Renewal Achievement Level Database
+# Achievement Level Database
 ###########################################################################
 ###########################################################################
 #
 #
 # Achievement Level Settings
 # Achievement Level Settings
 #
 #
 ###########################################################################
 ###########################################################################
-# Level - Achievement Level
-###########################################################################
-# Points - Required total scoring points to reach this level.
+# - Level     Achievement Level.
+#   Points    Required total scoring points to reach this level.
 ###########################################################################
 ###########################################################################
 
 
 Header:
 Header:

+ 2253 - 2221
db/re/achievement_db.yml

@@ -16,2710 +16,2742 @@
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 #
 #
 ###########################################################################
 ###########################################################################
-# Renewal Achievement Database
+# Achievement Database
 ###########################################################################
 ###########################################################################
 #
 #
 # Achievement Settings
 # Achievement Settings
 #
 #
 ###########################################################################
 ###########################################################################
-# ID - Unique achievement ID.
-###########################################################################
-# Group - Achievement group type. Each achievement type calls a specific
-# objective check.
-# Valid groups:
-#  AG_ADD_FRIEND
-#  AG_ADVENTURE
-#  AG_BABY
-#  AG_BATTLE
-#  AG_CHATTING
-#  AG_CHATTING_COUNT
-#  AG_CHATTING_CREATE
-#  AG_CHATTING_DYING
-#  AG_EAT
-#  AG_GET_ITEM
-#  AG_GET_ZENY
-#  AG_GOAL_ACHIEVE
-#  AG_GOAL_LEVEL
-#  AG_GOAL_STATUS
-#  AG_HEAR
-#  AG_JOB_CHANGE
-#  AG_MARRY
-#  AG_PARTY
-#  AG_ENCHANT_FAIL
-#  AG_ENCHANT_SUCCESS
-#  AG_SEE
-#  AG_SPEND_ZENY
-#  AG_TAMING
-###########################################################################
-# Name - Achievement name. Used when sending rewards through RODEX.
-###########################################################################
-# Target - A list of monster ID and count values that the achievement
-# requires. The target count can also be used for achievements that keep
-# a counter while not being related to monster kills.
-# Capped at MAX_ACHIEVEMENT_OBJECTIVES.
-###########################################################################
-# Condition - A conditional statement that must be met for the achievement
-# to be considered complete.
-###########################################################################
-# Map - A map name that is used for the AG_CHATTING type which increments
-# the counter based on the player's map.
-###########################################################################
-# Dependent: - A list of achievement IDs that need to be completed before
-# this achievement is considered complete.
-###########################################################################
-# Reward - A list of rewards that are given on completion. All fields are
-# optional.
-#   ItemID: Item ID
-#   Amount:  Amount of Item ID (default 1)
-#   Script: Bonus Script
-#   TitleID: Title ID
-###########################################################################
-# Score - Achievement points that are given on completion.
+# - Id                  Achievement ID.
+#   Group               Achievement group type. (Defaut: None)
+#   Name                Achievement name.
+#   Targets:            List of targets the achievement requires. (Default: null)
+#     - Id              Index value used for import methods.
+#       Mob             Target mob. (Default: 0)
+#       Count           Target count. (Default: 1)
+#   Condition           Conditional statement that must be met for the achievement to be considered complete. (Default: null)
+#   Map                 Map name that is used for the AG_CHATTING type. (Default: -1)
+#   Dependents:         List of achievements that need to be completed before this achievement is considered complete. (Default: null)
+#     - Id: <bool>      Achievement ID pre-requisite.
+#   Rewards:            List of rewards that are given on completion. (Default: null)
+#     Item              Item name.
+#     Amount            Amount of item. (Default: 1)
+#     Script            Bonus Script. (Default: null)
+#     TitleId           Title ID. (Default: 0)
+#   Score               Achievement points that are given on completion. (Default: 0)
 ###########################################################################
 ###########################################################################
 
 
 Header:
 Header:
   Type: ACHIEVEMENT_DB
   Type: ACHIEVEMENT_DB
-  Version: 1
+  Version: 2
 
 
 Body:
 Body:
-  - ID: 110000
-    Group: "AG_EAT"
-    Name: "At this time I live to eat"
-    Score: 10
-  - ID: 110001
-    Group: "AG_SEE"
-    Name: "A fan of this polarity"
-    Score: 10
-  - ID: 120001
-    Group: "AG_ADVENTURE"
-    Name: "North Prontera Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120002
-    Group: "AG_ADVENTURE"
-    Name: "North Prontera Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120003
-    Group: "AG_ADVENTURE"
-    Name: "North Prontera Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120004
-    Group: "AG_ADVENTURE"
-    Name: "West Prontera Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120005
-    Group: "AG_ADVENTURE"
-    Name: "West Prontera Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120006
-    Group: "AG_ADVENTURE"
-    Name: "East Prontera Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120007
-    Group: "AG_ADVENTURE"
-    Name: "South Prontera Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120008
-    Group: "AG_ADVENTURE"
-    Name: "South Prontera Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120009
-    Group: "AG_ADVENTURE"
-    Name: "South Prontera Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120010
-    Group: "AG_ADVENTURE"
-    Name: "South Prontera Field Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120011
-    Group: "AG_ADVENTURE"
-    Name: "East Geffen Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120012
-    Group: "AG_ADVENTURE"
-    Name: "Southeast Geffen Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120013
-    Group: "AG_ADVENTURE"
-    Name: "Northwest Geffen Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120014
-    Group: "AG_ADVENTURE"
-    Name: "Northwest Geffen Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120015
-    Group: "AG_ADVENTURE"
-    Name: "Northwest Geffen Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120016
-    Group: "AG_ADVENTURE"
-    Name: "South Geffen Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120017
-    Group: "AG_ADVENTURE"
-    Name: "South Geffen Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120018
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120019
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120020
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120021
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120022
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(5)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120023
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Field Exploration(6)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120024
-    Group: "AG_ADVENTURE"
-    Name: "Southwest Payon Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120025
-    Group: "AG_ADVENTURE"
-    Name: "Southwest Payon Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120026
-    Group: "AG_ADVENTURE"
-    Name: "Southwest Payon Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120027
-    Group: "AG_ADVENTURE"
-    Name: "Southwest Payon Field Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120028
-    Group: "AG_ADVENTURE"
-    Name: "East Payon Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120029
-    Group: "AG_ADVENTURE"
-    Name: "East Payon Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120030
-    Group: "AG_ADVENTURE"
-    Name: "East Payon Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120031
-    Group: "AG_ADVENTURE"
-    Name: "East Payon Field Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120032
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120033
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120034
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120035
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120036
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Field Exploration(5)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120037
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120038
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120039
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120040
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120041
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(5)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120042
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Field Exploration(6)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120043
-    Group: "AG_ADVENTURE"
-    Name: "South Aldebaran Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120044
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120045
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120046
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120047
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120048
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(5)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120049
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(6)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120050
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(7)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120051
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Field Exploration(8)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120052
-    Group: "AG_ADVENTURE"
-    Name: "Border Checkpoint Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120053
-    Group: "AG_ADVENTURE"
-    Name: "Border Checkpoint Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120054
-    Group: "AG_ADVENTURE"
-    Name: "Kiel Hyre Mansion Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120055
-    Group: "AG_ADVENTURE"
-    Name: "El Mes Plateau Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120056
-    Group: "AG_ADVENTURE"
-    Name: "El Mes Plateau Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120057
-    Group: "AG_ADVENTURE"
-    Name: "El Mes Plateau Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120058
-    Group: "AG_ADVENTURE"
-    Name: "El Mes Gorge Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120059
-    Group: "AG_ADVENTURE"
-    Name: "Kiel Hyre Academy Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120060
-    Group: "AG_ADVENTURE"
-    Name: "Guard Camp Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120061
-    Group: "AG_ADVENTURE"
-    Name: "Juno Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120062
-    Group: "AG_ADVENTURE"
-    Name: "Front of Thanatos Tower Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120063
-    Group: "AG_ADVENTURE"
-    Name: "Hugel Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120064
-    Group: "AG_ADVENTURE"
-    Name: "Hugel Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120065
-    Group: "AG_ADVENTURE"
-    Name: "Hugel Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120066
-    Group: "AG_ADVENTURE"
-    Name: "Abyss Lake Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120067
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120068
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120069
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120070
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120071
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(5)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120072
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(6)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120073
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(7)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120074
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Field Exploration(8)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120075
-    Group: "AG_ADVENTURE"
-    Name: "Lighthalzen Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120076
-    Group: "AG_ADVENTURE"
-    Name: "Lighthalzen Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120077
-    Group: "AG_ADVENTURE"
-    Name: "Lighthalzen Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120078
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Audhumbla Plains Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120079
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Plains Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120080
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Plains Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120081
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Plains Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120082
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Audhumbla Grassland Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120083
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Audhumbla Grassland Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120084
-    Group: "AG_ADVENTURE"
-    Name: "Portus Luna Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120085
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120086
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120087
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120088
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120089
-    Group: "AG_ADVENTURE"
-    Name: "Veins Field Exploration(5)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120090
-    Group: "AG_ADVENTURE"
-    Name: "Eclage Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120091
-    Group: "AG_ADVENTURE"
-    Name: "North Bitfrost Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120092
-    Group: "AG_ADVENTURE"
-    Name: "South Bitfrost Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120093
-    Group: "AG_ADVENTURE"
-    Name: "Splendide Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120094
-    Group: "AG_ADVENTURE"
-    Name: "Splendide Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120095
-    Group: "AG_ADVENTURE"
-    Name: "Splendide Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120096
-    Group: "AG_ADVENTURE"
-    Name: "Manuk Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120097
-    Group: "AG_ADVENTURE"
-    Name: "Manuk Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120098
-    Group: "AG_ADVENTURE"
-    Name: "Manuk Field Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120099
-    Group: "AG_ADVENTURE"
-    Name: "Outskirts of Kamidal Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120100
-    Group: "AG_ADVENTURE"
-    Name: "Outskirts of Kamidal Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120101
-    Group: "AG_ADVENTURE"
-    Name: "Amatsu Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120102
-    Group: "AG_ADVENTURE"
-    Name: "Kunlun Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120103
-    Group: "AG_ADVENTURE"
-    Name: "Kunlun Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120104
-    Group: "AG_ADVENTURE"
-    Name: "Ayothaya Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120105
-    Group: "AG_ADVENTURE"
-    Name: "Moscovia Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120106
-    Group: "AG_ADVENTURE"
-    Name: "Brasilis Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120107
-    Group: "AG_ADVENTURE"
-    Name: "Dewata Field Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120108
-    Group: "AG_ADVENTURE"
-    Name: "Malaya Field Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120109
-    Group: "AG_ADVENTURE"
-    Name: "Malaya Field Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 10
-  - ID: 120110
-    Group: "AG_ADVENTURE"
-    Name: "Abbey Underground Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120111
-    Group: "AG_ADVENTURE"
-    Name: "Abyss Lake Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120112
-    Group: "AG_ADVENTURE"
-    Name: "Clock Tower Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120113
-    Group: "AG_ADVENTURE"
-    Name: "Amatsu Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120114
-    Group: "AG_ADVENTURE"
-    Name: "Ant Hell Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120115
-    Group: "AG_ADVENTURE"
-    Name: "Ayothaya Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120116
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120117
-    Group: "AG_ADVENTURE"
-    Name: "Brasilis Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120118
-    Group: "AG_ADVENTURE"
-    Name: "Clock Tower Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120119
-    Group: "AG_ADVENTURE"
-    Name: "Istana Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120120
-    Group: "AG_ADVENTURE"
-    Name: "Scaraba Hole Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120121
-    Group: "AG_ADVENTURE"
-    Name: "Bitfrost Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120122
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120123
-    Group: "AG_ADVENTURE"
-    Name: "Geffen Underground Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120124
-    Group: "AG_ADVENTURE"
-    Name: "Glastheim Dungeon Exploration(1)"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120125
-    Group: "AG_ADVENTURE"
-    Name: "Glastheim Dungeon Exploration(2)"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120126
-    Group: "AG_ADVENTURE"
-    Name: "Glastheim Dungeon Exploration(3)"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120127
-    Group: "AG_ADVENTURE"
-    Name: "Glastheim Dungeon Exploration(4)"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120128
-    Group: "AG_ADVENTURE"
-    Name: "Kunlun Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120129
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120130
-    Group: "AG_ADVENTURE"
-    Name: "Sphinx Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120131
-    Group: "AG_ADVENTURE"
-    Name: "Izlude Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120132
-    Group: "AG_ADVENTURE"
-    Name: "Robot Factory Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120133
-    Group: "AG_ADVENTURE"
-    Name: "Bio Lab Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120134
-    Group: "AG_ADVENTURE"
-    Name: "Kunlun Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120135
-    Group: "AG_ADVENTURE"
-    Name: "Nogg Road Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120136
-    Group: "AG_ADVENTURE"
-    Name: "Coal Mine Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120137
-    Group: "AG_ADVENTURE"
-    Name: "Pyramid Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120138
-    Group: "AG_ADVENTURE"
-    Name: "Orc Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120139
-    Group: "AG_ADVENTURE"
-    Name: "Payon Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120140
-    Group: "AG_ADVENTURE"
-    Name: "Labyrinth Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120141
-    Group: "AG_ADVENTURE"
-    Name: "Undersea Tunnel Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120142
-    Group: "AG_ADVENTURE"
-    Name: "Thanatos Tower Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120143
-    Group: "AG_ADVENTURE"
-    Name: "Thor Volcano Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120144
-    Group: "AG_ADVENTURE"
-    Name: "Sunken Ship Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120145
-    Group: "AG_ADVENTURE"
-    Name: "Turtle Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 120146
-    Group: "AG_ADVENTURE"
-    Name: "Toy Factory Dungeon Exploration"
-    Reward:
-      ItemID: 22876
-    Score: 20
-  - ID: 127001
-    Group: "AG_CHATTING"
-    Name: "Prontera Contribution"
-    Map: "prontera"
-    Target:
+  - Id: 110000
+    Group: Eat
+    Name: At this time I live to eat
+    Score: 10
+  - Id: 110001
+    Group: Chatting
+    Name: A fan of this polarity
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 1
+      - Id: 1
+        Count: 1
+      - Id: 2
+        Count: 1
+      - Id: 3
+        Count: 1
+      - Id: 4
+        Count: 1
+      - Id: 5
+        Count: 1
+      - Id: 6
+        Count: 1
+    Score: 10
+  - Id: 120001
+    Group: Adventure
+    Name: North Prontera Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120002
+    Group: Adventure
+    Name: North Prontera Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120003
+    Group: Adventure
+    Name: North Prontera Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120004
+    Group: Adventure
+    Name: West Prontera Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120005
+    Group: Adventure
+    Name: West Prontera Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120006
+    Group: Adventure
+    Name: East Prontera Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120007
+    Group: Adventure
+    Name: South Prontera Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120008
+    Group: Adventure
+    Name: South Prontera Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120009
+    Group: Adventure
+    Name: South Prontera Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120010
+    Group: Adventure
+    Name: South Prontera Field Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120011
+    Group: Adventure
+    Name: East Geffen Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120012
+    Group: Adventure
+    Name: Southeast Geffen Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120013
+    Group: Adventure
+    Name: Northwest Geffen Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120014
+    Group: Adventure
+    Name: Northwest Geffen Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120015
+    Group: Adventure
+    Name: Northwest Geffen Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120016
+    Group: Adventure
+    Name: South Geffen Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120017
+    Group: Adventure
+    Name: South Geffen Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120018
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120019
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120020
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120021
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120022
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(5)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120023
+    Group: Adventure
+    Name: Sograt Desert Field Exploration(6)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120024
+    Group: Adventure
+    Name: Southwest Payon Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120025
+    Group: Adventure
+    Name: Southwest Payon Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120026
+    Group: Adventure
+    Name: Southwest Payon Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120027
+    Group: Adventure
+    Name: Southwest Payon Field Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120028
+    Group: Adventure
+    Name: East Payon Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120029
+    Group: Adventure
+    Name: East Payon Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120030
+    Group: Adventure
+    Name: East Payon Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120031
+    Group: Adventure
+    Name: East Payon Field Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120032
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120033
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120034
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120035
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120036
+    Group: Adventure
+    Name: North Mjolnir Field Exploration(5)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120037
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120038
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120039
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120040
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120041
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(5)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120042
+    Group: Adventure
+    Name: South Mjolnir Field Exploration(6)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120043
+    Group: Adventure
+    Name: South Aldebaran Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120044
+    Group: Adventure
+    Name: Comodo Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120045
+    Group: Adventure
+    Name: Comodo Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120046
+    Group: Adventure
+    Name: Comodo Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120047
+    Group: Adventure
+    Name: Comodo Field Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120048
+    Group: Adventure
+    Name: Comodo Field Exploration(5)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120049
+    Group: Adventure
+    Name: Comodo Field Exploration(6)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120050
+    Group: Adventure
+    Name: Comodo Field Exploration(7)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120051
+    Group: Adventure
+    Name: Comodo Field Exploration(8)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120052
+    Group: Adventure
+    Name: Border Checkpoint Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120053
+    Group: Adventure
+    Name: Border Checkpoint Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120054
+    Group: Adventure
+    Name: Kiel Hyre Mansion Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120055
+    Group: Adventure
+    Name: El Mes Plateau Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120056
+    Group: Adventure
+    Name: El Mes Plateau Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120057
+    Group: Adventure
+    Name: El Mes Plateau Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120058
+    Group: Adventure
+    Name: El Mes Gorge Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120059
+    Group: Adventure
+    Name: Kiel Hyre Academy Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120060
+    Group: Adventure
+    Name: Guard Camp Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120061
+    Group: Adventure
+    Name: Juno Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120062
+    Group: Adventure
+    Name: Front of Thanatos Tower Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120063
+    Group: Adventure
+    Name: Hugel Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120064
+    Group: Adventure
+    Name: Hugel Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120065
+    Group: Adventure
+    Name: Hugel Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120066
+    Group: Adventure
+    Name: Abyss Lake Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120067
+    Group: Adventure
+    Name: Einbroch Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120068
+    Group: Adventure
+    Name: Einbroch Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120069
+    Group: Adventure
+    Name: Einbroch Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120070
+    Group: Adventure
+    Name: Einbroch Field Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120071
+    Group: Adventure
+    Name: Einbroch Field Exploration(5)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120072
+    Group: Adventure
+    Name: Einbroch Field Exploration(6)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120073
+    Group: Adventure
+    Name: Einbroch Field Exploration(7)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120074
+    Group: Adventure
+    Name: Einbroch Field Exploration(8)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120075
+    Group: Adventure
+    Name: Lighthalzen Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120076
+    Group: Adventure
+    Name: Lighthalzen Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120077
+    Group: Adventure
+    Name: Lighthalzen Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120078
+    Group: Adventure
+    Name: Rachel Audhumbla Plains Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120079
+    Group: Adventure
+    Name: Rachel Plains Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120080
+    Group: Adventure
+    Name: Rachel Plains Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120081
+    Group: Adventure
+    Name: Rachel Plains Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120082
+    Group: Adventure
+    Name: Rachel Audhumbla Grassland Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120083
+    Group: Adventure
+    Name: Rachel Audhumbla Grassland Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120084
+    Group: Adventure
+    Name: Portus Luna Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120085
+    Group: Adventure
+    Name: Veins Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120086
+    Group: Adventure
+    Name: Veins Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120087
+    Group: Adventure
+    Name: Veins Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120088
+    Group: Adventure
+    Name: Veins Field Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120089
+    Group: Adventure
+    Name: Veins Field Exploration(5)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120090
+    Group: Adventure
+    Name: Eclage Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120091
+    Group: Adventure
+    Name: North Bitfrost Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120092
+    Group: Adventure
+    Name: South Bitfrost Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120093
+    Group: Adventure
+    Name: Splendide Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120094
+    Group: Adventure
+    Name: Splendide Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120095
+    Group: Adventure
+    Name: Splendide Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120096
+    Group: Adventure
+    Name: Manuk Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120097
+    Group: Adventure
+    Name: Manuk Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120098
+    Group: Adventure
+    Name: Manuk Field Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120099
+    Group: Adventure
+    Name: Outskirts of Kamidal Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120100
+    Group: Adventure
+    Name: Outskirts of Kamidal Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120101
+    Group: Adventure
+    Name: Amatsu Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120102
+    Group: Adventure
+    Name: Kunlun Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120103
+    Group: Adventure
+    Name: Kunlun Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120104
+    Group: Adventure
+    Name: Ayothaya Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120105
+    Group: Adventure
+    Name: Moscovia Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120106
+    Group: Adventure
+    Name: Brasilis Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120107
+    Group: Adventure
+    Name: Dewata Field Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120108
+    Group: Adventure
+    Name: Malaya Field Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120109
+    Group: Adventure
+    Name: Malaya Field Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 10
+  - Id: 120110
+    Group: Adventure
+    Name: Abbey Underground Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120111
+    Group: Adventure
+    Name: Abyss Lake Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120112
+    Group: Adventure
+    Name: Clock Tower Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120113
+    Group: Adventure
+    Name: Amatsu Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120114
+    Group: Adventure
+    Name: Ant Hell Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120115
+    Group: Adventure
+    Name: Ayothaya Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120116
+    Group: Adventure
+    Name: Comodo Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120117
+    Group: Adventure
+    Name: Brasilis Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120118
+    Group: Adventure
+    Name: Clock Tower Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120119
+    Group: Adventure
+    Name: Istana Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120120
+    Group: Adventure
+    Name: Scaraba Hole Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120121
+    Group: Adventure
+    Name: Bitfrost Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120122
+    Group: Adventure
+    Name: Einbroch Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120123
+    Group: Adventure
+    Name: Geffen Underground Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120124
+    Group: Adventure
+    Name: Glastheim Dungeon Exploration(1)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120125
+    Group: Adventure
+    Name: Glastheim Dungeon Exploration(2)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120126
+    Group: Adventure
+    Name: Glastheim Dungeon Exploration(3)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120127
+    Group: Adventure
+    Name: Glastheim Dungeon Exploration(4)
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120128
+    Group: Adventure
+    Name: Kunlun Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120129
+    Group: Adventure
+    Name: Rachel Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120130
+    Group: Adventure
+    Name: Sphinx Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120131
+    Group: Adventure
+    Name: Izlude Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120132
+    Group: Adventure
+    Name: Robot Factory Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120133
+    Group: Adventure
+    Name: Bio Lab Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120134
+    Group: Adventure
+    Name: Kunlun Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120135
+    Group: Adventure
+    Name: Nogg Road Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120136
+    Group: Adventure
+    Name: Coal Mine Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120137
+    Group: Adventure
+    Name: Pyramid Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120138
+    Group: Adventure
+    Name: Orc Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120139
+    Group: Adventure
+    Name: Payon Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120140
+    Group: Adventure
+    Name: Labyrinth Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120141
+    Group: Adventure
+    Name: Undersea Tunnel Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120142
+    Group: Adventure
+    Name: Thanatos Tower Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120143
+    Group: Adventure
+    Name: Thor Volcano Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120144
+    Group: Adventure
+    Name: Sunken Ship Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120145
+    Group: Adventure
+    Name: Turtle Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 120146
+    Group: Adventure
+    Name: Toy Factory Dungeon Exploration
+    Rewards:
+      Item: Shabby_Purse
+    Score: 20
+  - Id: 127001
+    Group: Chatting
+    Name: Prontera Contribution
+    Targets:
+      - Id: 0
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: prontera
     Score: 10
     Score: 10
-  - ID: 127002
-    Group: "AG_CHATTING"
-    Name: "Geffen Contribution"
-    Map: "geffen"
-    Target:
+  - Id: 127002
+    Group: Chatting
+    Name: Geffen Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: geffen
     Score: 10
     Score: 10
-  - ID: 127003
-    Group: "AG_CHATTING"
-    Name: "Morocc Contribution"
-    Map: "morocc"
-    Target:
+  - Id: 127003
+    Group: Chatting
+    Name: Morocc Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: morocc
     Score: 10
     Score: 10
-  - ID: 127004
-    Group: "AG_CHATTING"
-    Name: "Payon Contribution"
-    Map: "payon"
-    Target:
+  - Id: 127004
+    Group: Chatting
+    Name: Payon Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: payon
     Score: 10
     Score: 10
-  - ID: 127005
-    Group: "AG_CHATTING"
-    Name: "Juno Contribution"
-    Map: "yuno"
-    Target:
+  - Id: 127005
+    Group: Chatting
+    Name: Juno Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: yuno
     Score: 10
     Score: 10
-  - ID: 127006
-    Group: "AG_CHATTING"
-    Name: "Lighthalzen Contribution"
-    Map: "lighthalzen"
-    Target:
+  - Id: 127006
+    Group: Chatting
+    Name: Lighthalzen Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: lighthalzen
     Score: 10
     Score: 10
-  - ID: 127007
-    Group: "AG_CHATTING"
-    Name: "Einbroch Contribution"
-    Map: "einbroch"
-    Target:
+  - Id: 127007
+    Group: Chatting
+    Name: Einbroch Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: einbroch
     Score: 10
     Score: 10
-  - ID: 127008
-    Group: "AG_CHATTING"
-    Name: "Rachel Contribution"
-    Map: "rachel"
-    Target:
+  - Id: 127008
+    Group: Chatting
+    Name: Rachel Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: rachel
     Score: 10
     Score: 10
-  - ID: 127009
-    Group: "AG_CHATTING"
-    Name: "Veins Contribution"
-    Map: "veins"
-    Target:
+  - Id: 127009
+    Group: Chatting
+    Name: Veins Contribution
+    Targets:
       - Id: 0
       - Id: 0
-        Count: 100000
+        Count: 3000
+      - Id: 1
+        Count: 6000
+      - Id: 2
+        Count: 12000
+      - Id: 3
+        Count: 20000
+      - Id: 4
+        Count: 1000
+    Map: veins
     Score: 10
     Score: 10
-  - ID: 128000
-    Group: "AG_BATTLE"
-    Name: "Uninvited Guest"
-    Target:
+  - Id: 128000
+    Group: Battle
+    Name: Uninvited Guest
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2996
-        Count: 1
+        Mob: XM_CELINE_KIMI
     Score: 10
     Score: 10
-  - ID: 128001
-    Group: "AG_BATTLE"
-    Name: "Strange Guest"
-    Target:
+  - Id: 128001
+    Group: Battle
+    Name: Strange Guest
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2996
+        Mob: XM_CELINE_KIMI
         Count: 10
         Count: 10
     Score: 10
     Score: 10
-  - ID: 128002
-    Group: "AG_BATTLE"
-    Name: "Get along with map..."
-    Target:
+  - Id: 128002
+    Group: Battle
+    Name: Get along with map...
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2996
+        Mob: XM_CELINE_KIMI
         Count: 25
         Count: 25
     Score: 20
     Score: 20
-  - ID: 128003
-    Group: "AG_BATTLE"
-    Name: "Welcomed Guest"
-    Target:
+  - Id: 128003
+    Group: Battle
+    Name: Welcomed Guest
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2996
+        Mob: XM_CELINE_KIMI
         Count: 50
         Count: 50
     Score: 30
     Score: 30
-  - ID: 128004
-    Group: "AG_BATTLE"
-    Name: "Kimmy's best friend"
-    Target:
+  - Id: 128004
+    Group: Battle
+    Name: Kimmy's best friend
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2996
+        Mob: XM_CELINE_KIMI
         Count: 100
         Count: 100
     Score: 50
     Score: 50
-  - ID: 128005
-    Group: "AG_BATTLE"
-    Name: "Novice Angler"
-    Target:
+  - Id: 128005
+    Group: Battle
+    Name: Novice Angler
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2322
-        Count: 1
+        Mob: BAKONAWA_3
     Score: 10
     Score: 10
-  - ID: 128006
-    Group: "AG_BATTLE"
-    Name: "Juicy Hunter"
-    Target:
+  - Id: 128006
+    Group: Battle
+    Name: Juicy Hunter
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2322
+        Mob: BAKONAWA_3
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128007
-    Group: "AG_BATTLE"
-    Name: "Rhythm Master"
-    Target:
+  - Id: 128007
+    Group: Battle
+    Name: Rhythm Master
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2322
+        Mob: BAKONAWA_3
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128008
-    Group: "AG_BATTLE"
-    Name: "Bold Adventurer"
-    Target:
+  - Id: 128008
+    Group: Battle
+    Name: Bold Adventurer
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1929
-        Count: 1
+        Mob: BAPHOMET_I
     Score: 10
     Score: 10
-  - ID: 128009
-    Group: "AG_BATTLE"
-    Name: "Baphomet Hatred"
-    Target:
+  - Id: 128009
+    Group: Battle
+    Name: Baphomet Hatred
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1929
+        Mob: BAPHOMET_I
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128010
-    Group: "AG_BATTLE"
-    Name: "Goat's Nemesis"
-    Target:
+  - Id: 128010
+    Group: Battle
+    Name: Goat's Nemesis
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1929
+        Mob: BAPHOMET_I
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128011
-    Group: "AG_BATTLE"
-    Name: "Ordinary Tourist"
-    Target:
+  - Id: 128011
+    Group: Battle
+    Name: Ordinary Tourist
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3029
-        Count: 1
+        Mob: GRIM_REAPER_ANKOU
     Score: 10
     Score: 10
-  - ID: 128012
-    Group: "AG_BATTLE"
-    Name: "Backcountry Expert"
-    Target:
+  - Id: 128012
+    Group: Battle
+    Name: Backcountry Expert
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3029
+        Mob: GRIM_REAPER_ANKOU
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128013
-    Group: "AG_BATTLE"
-    Name: "Able to eat more like this"
-    Target:
+  - Id: 128013
+    Group: Battle
+    Name: Able to eat more like this
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3029
+        Mob: GRIM_REAPER_ANKOU
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128014
-    Group: "AG_BATTLE"
-    Name: "Digest hard meat"
-    Target:
+  - Id: 128014
+    Group: Battle
+    Name: Digest hard meat
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2319
-        Count: 1
+        Mob: BUWAYA
     Score: 10
     Score: 10
-  - ID: 128015
-    Group: "AG_BATTLE"
-    Name: "Master of Escape"
-    Target:
+  - Id: 128015
+    Group: Battle
+    Name: Master of Escape
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2319
+        Mob: BUWAYA
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128016
-    Group: "AG_BATTLE"
-    Name: "Immortal Hunter"
-    Target:
+  - Id: 128016
+    Group: Battle
+    Name: Immortal Hunter
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2319
+        Mob: BUWAYA
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128017
-    Group: "AG_BATTLE"
-    Name: "Stood up and overcame despair"
-    #Target:
+  - Id: 128017
+    Group: Battle
+    Name: Stood up and overcame despair
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
-    #    Count: 1
+    #    Mob: MM_MOROCC_ADT
     Score: 10
     Score: 10
-  - ID: 128018
-    Group: "AG_BATTLE"
-    Name: "Ember of Hope"
-    #Target:
+  - Id: 128018
+    Group: Battle
+    Name: Ember of Hope
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
+    #    Mob: MM_MOROCC_ADT
     #    Count: 10
     #    Count: 10
     Score: 10
     Score: 10
-  - ID: 128019
-    Group: "AG_BATTLE"
-    Name: "Pouring Aurora"
-    #Target:
+  - Id: 128019
+    Group: Battle
+    Name: Pouring Aurora
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
+    #    Mob: MM_MOROCC_ADT
     #    Count: 25
     #    Count: 25
     Score: 20
     Score: 20
-  - ID: 128020
-    Group: "AG_BATTLE"
-    Name: "Who is desperate? I am hopeless!"
-    #Target:
+  - Id: 128020
+    Group: Battle
+    Name: Who is desperate? I am hopeless!
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
+    #    Mob: MM_MOROCC_ADT
     #    Count: 50
     #    Count: 50
     Score: 30
     Score: 30
-  - ID: 128021
-    Group: "AG_BATTLE"
-    Name: "I know god will save the world"
-    #Target:
+  - Id: 128021
+    Group: Battle
+    Name: I know god will save the world
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3097
+    #    Mob: MM_MOROCC_ADT
     #    Count: 100
     #    Count: 100
     Score: 50
     Score: 50
-  - ID: 128022
-    Group: "AG_BATTLE"
-    Name: "There was mercy in Morocc army"
-    Target:
+  - Id: 128022
+    Group: Battle
+    Name: There was mercy in Morocc army
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3000
-        Count: 1
+        Mob: EP14_MORS_BOSSB
     Score: 10
     Score: 10
-  - ID: 128023
-    Group: "AG_BATTLE"
-    Name: "There was fear in Morocc army"
-    Target:
+  - Id: 128023
+    Group: Battle
+    Name: There was fear in Morocc army
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3000
+        Mob: EP14_MORS_BOSSB
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128024
-    Group: "AG_BATTLE"
-    Name: "Guard of weak army"
-    Target:
+  - Id: 128024
+    Group: Battle
+    Name: Guard of weak army
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3000
+        Mob: EP14_MORS_BOSSB
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128025
-    Group: "AG_BATTLE"
-    Name: "Audience with the queen"
-    Target:
+  - Id: 128025
+    Group: Battle
+    Name: Audience with the queen
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2529
-        Count: 1
+        Mob: FACEWORM_QUEEN
     Score: 10
     Score: 10
-  - ID: 128026
-    Group: "AG_BATTLE"
-    Name: "Warm earth"
-    Target:
+  - Id: 128026
+    Group: Battle
+    Name: Warm earth
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2533
-        Count: 1
+        Mob: FACEWORM_QUEEN_G
     Score: 10
     Score: 10
-  - ID: 128027
-    Group: "AG_BATTLE"
-    Name: "Water is very good exactly"
-    Target:
+  - Id: 128027
+    Group: Battle
+    Name: Water is very good exactly
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2534
-        Count: 1
+        Mob: FACEWORM_QUEEN_B
     Score: 10
     Score: 10
-  - ID: 128028
-    Group: "AG_BATTLE"
-    Name: "Pleasant breeze"
-    Target:
+  - Id: 128028
+    Group: Battle
+    Name: Pleasant breeze
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2535
-        Count: 1
+        Mob: FACEWORM_QUEEN_Y
     Score: 10
     Score: 10
-  - ID: 128029
-    Group: "AG_BATTLE"
-    Name: "Visitor of old castle"
-    Target:
+  - Id: 128029
+    Group: Battle
+    Name: Visitor of old castle
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2476
-        Count: 1
+        Mob: MG_AMDARAIS
     Score: 10
     Score: 10
-  - ID: 128030
-    Group: "AG_BATTLE"
-    Name: "Lord of old castle"
-    Target:
+  - Id: 128030
+    Group: Battle
+    Name: Lord of old castle
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2476
+        Mob: MG_AMDARAIS
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128031
-    Group: "AG_BATTLE"
-    Name: "Conqueror of old castle"
-    Target:
+  - Id: 128031
+    Group: Battle
+    Name: Conqueror of old castle
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2476
+        Mob: MG_AMDARAIS
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128032
-    Group: "AG_BATTLE"
-    Name: "Haggard sucker"
-    #Target:
+  - Id: 128032
+    Group: Battle
+    Name: Haggard sucker
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3150
-    #    Count: 1
+    #    Mob: MG_AMDARAIS_H
     Score: 10
     Score: 10
-  - ID: 128033
-    Group: "AG_BATTLE"
-    Name: "Hope of the Knight"
-    #Target:
+  - Id: 128033
+    Group: Battle
+    Name: Hope of the Knight
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3150
+    #    Mob: MG_AMDARAIS_H
     #    Count: 10
     #    Count: 10
     Score: 20
     Score: 20
-  - ID: 128034
-    Group: "AG_BATTLE"
-    Name: "Guardian of the Dawn"
-    #Target:
+  - Id: 128034
+    Group: Battle
+    Name: Guardian of the Dawn
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3150
+    #    Mob: MG_AMDARAIS_H
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128035
-    Group: "AG_BATTLE"
-    Name: "Time Traveler"
-    Target:
+  - Id: 128035
+    Group: Battle
+    Name: Time Traveler
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3190
-        Count: 1
+        Mob: MM_SARAH
     Score: 10
     Score: 10
-  - ID: 128036
-    Group: "AG_BATTLE"
-    Name: "Restore ancient relic"
-    Target:
+  - Id: 128036
+    Group: Battle
+    Name: Restore ancient relic
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3190
+        Mob: MM_SARAH
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128037
-    Group: "AG_BATTLE"
-    Name: "Master of relic transport"
-    Target:
+  - Id: 128037
+    Group: Battle
+    Name: Master of relic transport
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3190
+        Mob: MM_SARAH
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128038
-    Group: "AG_BATTLE"
-    Name: "Show Jailbreak to the captain"
-    Target:
+  - Id: 128038
+    Group: Battle
+    Name: Show Jailbreak to the captain
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3181
-        Count: 1
+        Mob: E1_FELOCK
     Score: 10
     Score: 10
-  - ID: 128039
-    Group: "AG_BATTLE"
-    Name: "Show Jailbreak to the weak captain"
-    #Target:
+  - Id: 128039
+    Group: Battle
+    Name: Show Jailbreak to the weak captain
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3188
-    #    Count: 1
+    #    Mob: E2_FELOCK
     Score: 10
     Score: 10
-  - ID: 128040
-    Group: "AG_BATTLE"
-    Name: "Riot on board"
-    Target:
+  - Id: 128040
+    Group: Battle
+    Name: Riot on board
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3181
-        Count: 1
+        Mob: E1_FELOCK
     Score: 20
     Score: 20
-  - ID: 128041
-    Group: "AG_BATTLE"
-    Name: "Turmoil on board"
-    Target:
+  - Id: 128041
+    Group: Battle
+    Name: Turmoil on board
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3181
+        Mob: E1_FELOCK
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128042
-    Group: "AG_BATTLE"
-    Name: "Rebellion on board"
-    Target:
+  - Id: 128042
+    Group: Battle
+    Name: Rebellion on board
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 3181
+        Mob: E1_FELOCK
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128043
-    Group: "AG_BATTLE"
-    Name: "Revolt of Riot"
-    #Target:
+  - Id: 128043
+    Group: Battle
+    Name: Revolt of Riot
+    #Targets:
     #  - Id: 0
     #  - Id: 0
-    #    MobID: 3188
+    #    Mob: E2_FELOCK
     #    Count: 50
     #    Count: 50
     Score: 50
     Score: 50
-  - ID: 128044
-    Group: "AG_BATTLE"
-    Name: "Magic tournament champion"
-    Target:
+  - Id: 128044
+    Group: Battle
+    Name: Magic tournament champion
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2564
-        Count: 1
+        Mob: GEFFEN_FENRIR
     Score: 10
     Score: 10
-  - ID: 128045
-    Group: "AG_BATTLE"
-    Name: "Gladiator of Coliseum"
-    Target:
+  - Id: 128045
+    Group: Battle
+    Name: Gladiator of Coliseum
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2564
+        Mob: GEFFEN_FENRIR
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128046
-    Group: "AG_BATTLE"
-    Name: "Slayer of Colosseum"
-    Target:
+  - Id: 128046
+    Group: Battle
+    Name: Slayer of Colosseum
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2564
+        Mob: GEFFEN_FENRIR
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128047
-    Group: "AG_BATTLE"
-    Name: "Endless Tower challenger"
-    Target:
+  - Id: 128047
+    Group: Battle
+    Name: Endless Tower challenger
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1956
-        Count: 1
+        Mob: NAGHT_SIEGER
     Score: 10
     Score: 10
-  - ID: 128048
-    Group: "AG_BATTLE"
-    Name: "Endless Tower Slayer"
-    Target:
+  - Id: 128048
+    Group: Battle
+    Name: Endless Tower Slayer
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1956
+        Mob: NAGHT_SIEGER
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128049
-    Group: "AG_BATTLE"
-    Name: "Lord of the tower"
-    Target:
+  - Id: 128049
+    Group: Battle
+    Name: Lord of the tower
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1956
+        Mob: NAGHT_SIEGER
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 128050
-    Group: "AG_BATTLE"
-    Name: "Novice Exorcist"
-    Target:
+  - Id: 128050
+    Group: Battle
+    Name: Novice Exorcist
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2327
-        Count: 1
+        Mob: BANGUNGOT_3
     Score: 10
     Score: 10
-  - ID: 128051
-    Group: "AG_BATTLE"
-    Name: "Experienced Exorcist"
-    Target:
+  - Id: 128051
+    Group: Battle
+    Name: Experienced Exorcist
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2327
+        Mob: BANGUNGOT_3
         Count: 10
         Count: 10
     Score: 20
     Score: 20
-  - ID: 128052
-    Group: "AG_BATTLE"
-    Name: "Legendary Exorcist"
-    Target:
+  - Id: 128052
+    Group: Battle
+    Name: Legendary Exorcist
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2327
+        Mob: BANGUNGOT_3
         Count: 50
         Count: 50
     Score: 50
     Score: 50
-  - ID: 129001
-    Group: "AG_ADVENTURE"
-    Name: "Prontera Explorer"
-    Dependent:
-      - Id: 120001
-      - Id: 120002
-      - Id: 120003
-      - Id: 120004
-      - Id: 120005
-      - Id: 120006
-      - Id: 120007
-      - Id: 120008
-      - Id: 120009
-      - Id: 120010
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129002
-    Group: "AG_ADVENTURE"
-    Name: "Geffen Explorer"
-    Dependent:
-      - Id: 120011
-      - Id: 120012
-      - Id: 120013
-      - Id: 120014
-      - Id: 120015
-      - Id: 120016
-      - Id: 120017
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129003
-    Group: "AG_ADVENTURE"
-    Name: "Sograt Desert Explorer"
-    Dependent: 
-      - Id: 120018
-      - Id: 120019
-      - Id: 120020
-      - Id: 120021
-      - Id: 120022
-      - Id: 120023
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129004
-    Group: "AG_ADVENTURE"
-    Name: "Payon Explorer"
-    Dependent:
-      - Id: 120024
-      - Id: 120025
-      - Id: 120026
-      - Id: 120027
-      - Id: 120028
-      - Id: 120029
-      - Id: 120030
-      - Id: 120031
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129005
-    Group: "AG_ADVENTURE"
-    Name: "North Mjolnir Explorer"
-    Dependent:
-      - Id: 120032
-      - Id: 120033
-      - Id: 120034
-      - Id: 120035
-      - Id: 120036
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129006
-    Group: "AG_ADVENTURE"
-    Name: "South Mjolnir Explorer"
-    Dependent:
-      - Id: 120037
-      - Id: 120038
-      - Id: 120039
-      - Id: 120040
-      - Id: 120041
-      - Id: 120042
-      - Id: 120043
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129007
-    Group: "AG_ADVENTURE"
-    Name: "Comodo Explorer"
-    Dependent:
-      - Id: 120044
-      - Id: 120045
-      - Id: 120046
-      - Id: 120047
-      - Id: 120048
-      - Id: 120049
-      - Id: 120050
-      - Id: 120051
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129008
-    Group: "AG_ADVENTURE"
-    Name: "Rune-Midgarts Explorer"
-    Dependent:
-      - Id: 129001
-      - Id: 129002
-      - Id: 129003
-      - Id: 129004
-      - Id: 129005
-      - Id: 129006
-      - Id: 129007
-    Reward:
-      ItemID: 617
+  - Id: 129001
+    Group: Adventure
+    Name: Prontera Explorer
+    Dependents:
+      120001: true
+      120002: true
+      120003: true
+      120004: true
+      120005: true
+      120006: true
+      120007: true
+      120008: true
+      120009: true
+      120010: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129002
+    Group: Adventure
+    Name: Geffen Explorer
+    Dependents:
+      120011: true
+      120012: true
+      120013: true
+      120014: true
+      120015: true
+      120016: true
+      120017: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129003
+    Group: Adventure
+    Name: Sograt Desert Explorer
+    Dependents:
+      120018: true
+      120019: true
+      120020: true
+      120021: true
+      120022: true
+      120023: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129004
+    Group: Adventure
+    Name: Payon Explorer
+    Dependents:
+      120024: true
+      120025: true
+      120026: true
+      120027: true
+      120028: true
+      120029: true
+      120030: true
+      120031: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129005
+    Group: Adventure
+    Name: North Mjolnir Explorer
+    Dependents:
+      120032: true
+      120033: true
+      120034: true
+      120035: true
+      120036: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129006
+    Group: Adventure
+    Name: South Mjolnir Explorer
+    Dependents:
+      120037: true
+      120038: true
+      120039: true
+      120040: true
+      120041: true
+      120042: true
+      120043: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129007
+    Group: Adventure
+    Name: Comodo Explorer
+    Dependents:
+      120044: true
+      120045: true
+      120046: true
+      120047: true
+      120048: true
+      120049: true
+      120050: true
+      120051: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129008
+    Group: Adventure
+    Name: Rune-Midgarts Explorer
+    Dependents:
+      129001: true
+      129002: true
+      129003: true
+      129004: true
+      129005: true
+      129006: true
+      129007: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129009
-    Group: "AG_ADVENTURE"
-    Name: "Juno Explorer"
-    Dependent:
-      - Id: 120052
-      - Id: 120053
-      - Id: 120054
-      - Id: 120055
-      - Id: 120056
-      - Id: 120057
-      - Id: 120058
-      - Id: 120059
-      - Id: 120060
-      - Id: 120061
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129010
-    Group: "AG_ADVENTURE"
-    Name: "Hugel Explorer"
-    Dependent:
-      - Id: 120062
-      - Id: 120063
-      - Id: 120064
-      - Id: 120065
-      - Id: 120066
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129011
-    Group: "AG_ADVENTURE"
-    Name: "Einbroch Explorer"
-    Dependent:
-      - Id: 120067
-      - Id: 120068
-      - Id: 120069
-      - Id: 120070
-      - Id: 120071
-      - Id: 120072
-      - Id: 120073
-      - Id: 120074
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129012
-    Group: "AG_ADVENTURE"
-    Name: "Lighthalzen Explorer"
-    Dependent:
-      - Id: 120075
-      - Id: 120076
-      - Id: 120077
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129013
-    Group: "AG_ADVENTURE"
-    Name: "Schwarzwald Explorer"
-    Dependent:
-      - Id: 129009
-      - Id: 129010
-      - Id: 129011
-      - Id: 129012
-    Reward:
-      ItemID: 617
+  - Id: 129009
+    Group: Adventure
+    Name: Juno Explorer
+    Dependents:
+      120052: true
+      120053: true
+      120054: true
+      120055: true
+      120056: true
+      120057: true
+      120058: true
+      120059: true
+      120060: true
+      120061: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129010
+    Group: Adventure
+    Name: Hugel Explorer
+    Dependents:
+      120062: true
+      120063: true
+      120064: true
+      120065: true
+      120066: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129011
+    Group: Adventure
+    Name: Einbroch Explorer
+    Dependents:
+      120067: true
+      120068: true
+      120069: true
+      120070: true
+      120071: true
+      120072: true
+      120073: true
+      120074: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129012
+    Group: Adventure
+    Name: Lighthalzen Explorer
+    Dependents:
+      120075: true
+      120076: true
+      120077: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129013
+    Group: Adventure
+    Name: Schwarzwald Explorer
+    Dependents:
+      129009: true
+      129010: true
+      129011: true
+      129012: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129014
-    Group: "AG_ADVENTURE"
-    Name: "Rachel Explorer"
-    Dependent:
-      - Id: 120078
-      - Id: 120079
-      - Id: 120080
-      - Id: 120081
-      - Id: 120082
-      - Id: 120083
-      - Id: 120084
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129015
-    Group: "AG_ADVENTURE"
-    Name: "Veins Explorer"
-    Dependent:
-      - Id: 120085
-      - Id: 120086
-      - Id: 120087
-      - Id: 120088
-      - Id: 120089
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129016
-    Group: "AG_ADVENTURE"
-    Name: "Arunafeltz Explorer"
-    Dependent:
-      - Id: 129014
-      - Id: 129015
-    Reward:
-      ItemID: 617
+  - Id: 129014
+    Group: Adventure
+    Name: Rachel Explorer
+    Dependents:
+      120078: true
+      120079: true
+      120080: true
+      120081: true
+      120082: true
+      120083: true
+      120084: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129015
+    Group: Adventure
+    Name: Veins Explorer
+    Dependents:
+      120085: true
+      120086: true
+      120087: true
+      120088: true
+      120089: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129016
+    Group: Adventure
+    Name: Arunafeltz Explorer
+    Dependents:
+      129014: true
+      129015: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129017
-    Group: "AG_ADVENTURE"
-    Name: "Laphine Explorer"
-    Dependent:
-      - Id: 120090
-      - Id: 120091
-      - Id: 120092
-      - Id: 120093
-      - Id: 120094
-      - Id: 120095
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129018
-    Group: "AG_ADVENTURE"
-    Name: "Manuk Explorer"
-    Dependent:
-      - Id: 120096
-      - Id: 120097
-      - Id: 120098
-      - Id: 120099
-      - Id: 120100
-    Reward:
-      ItemID: 644
-    Score: 20
-  - ID: 129019
-    Group: "AG_ADVENTURE"
-    Name: "Eclage Explorer"
-    Dependent:
-      - Id: 129017
-      - Id: 129018
-    Reward:
-      ItemID: 617
+  - Id: 129017
+    Group: Adventure
+    Name: Laphine Explorer
+    Dependents:
+      120090: true
+      120091: true
+      120092: true
+      120093: true
+      120094: true
+      120095: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129018
+    Group: Adventure
+    Name: Manuk Explorer
+    Dependents:
+      120096: true
+      120097: true
+      120098: true
+      120099: true
+      120100: true
+    Rewards:
+      Item: Gift_Box
+    Score: 20
+  - Id: 129019
+    Group: Adventure
+    Name: Eclage Explorer
+    Dependents:
+      129017: true
+      129018: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129020
-    Group: "AG_ADVENTURE"
-    Name: "Localizing fields explorer"
-    Dependent:
-      - Id: 120101
-      - Id: 120102
-      - Id: 120103
-      - Id: 120104
-      - Id: 120105
-      - Id: 120106
-      - Id: 120107
-      - Id: 120108
-      - Id: 120109
-    Reward:
-      ItemID: 617
+  - Id: 129020
+    Group: Adventure
+    Name: Localizing fields explorer
+    Dependents:
+      120101: true
+      120102: true
+      120103: true
+      120104: true
+      120105: true
+      120106: true
+      120107: true
+      120108: true
+      120109: true
+    Rewards:
+      Item: Old_Violet_Box
     Score: 50
     Score: 50
-  - ID: 129021
-    Group: "AG_BATTLE"
-    Name: "Glastheim Challenge Mode" # Complete 100 times?
-    Reward:
-      TitleID: 1045
-    Score: 10
-  - ID: 130000 # Talk to Prince NPC (npc/quests/quests_morocc.txt L5288)
-    Group: "AG_CHATTING"
-    Name: "Socialite debut"
-    Reward:
-      TitleID: 1034
-    Score: 10
-  - ID: 170000
-    Group: "AG_HEAR"
-    Name: "Song chamber is not an accident"
-    Score: 10
-  - ID: 190000
-    Group: "AG_CHATTING"
-    Name: "Alliance workers of merchant city"
+  - Id: 129021
+    Group: Battle
+    Name: Glastheim Challenge Mode # Complete 100 times?
+    Rewards:
+      TitleId: 1045
+    Score: 10
+  - Id: 130000
+    Group: Chatting
+    Name: Socialite debut
+    Targets:
+      - Id: 0
+        Count: 1
+      - Id: 1
+        Count: 1
+      - Id: 2
+        Count: 1
+      - Id: 3
+        Count: 1
+      - Id: 4
+        Count: 1
+      - Id: 5
+        Count: 1
+      - Id: 6
+        Count: 1
+    Rewards:
+      TitleId: 1034
+    Score: 10
+  - Id: 170000
+    Group: Chatting
+    Name: Song chamber is not an accident
+    Targets:
+      - Id: 0
+        Count: 1
+    Score: 10
+  - Id: 190000
+    Group: Chatting
+    Name: Alliance workers of merchant city
+    Targets:
+      - Id: 0
+        Count: 1
+      - Id: 1
+        Count: 10
+      - Id: 2
+        Count: 30
+      - Id: 3
+        Count: 100
     Score: 50
     Score: 50
-  - ID: 200000
-    Group: "AG_GOAL_LEVEL"
-    Name: "Acquire the first aura!"
+  - Id: 200000
+    Group: Goal_Level
+    Name: Acquire the first aura!
     Condition: " BaseLevel >= 99 "
     Condition: " BaseLevel >= 99 "
-    Reward:
-      ItemID: 12549
+    Rewards:
+      Item: White_Slim_Pot_Box2
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1000
+      TitleId: 1000
     Score: 50
     Score: 50
-  - ID: 200001
-    Group: "AG_GOAL_LEVEL"
-    Name: "Acquire the second aura!"
+  - Id: 200001
+    Group: Goal_Level
+    Name: Acquire the second aura!
     Condition: " BaseLevel >= 150 "
     Condition: " BaseLevel >= 150 "
-    Dependent:
-      - Id: 200000
-    Reward:
-      ItemID: 5364
+    Dependents:
+      200000: true
+    Rewards:
+      Item: Dark_Snake_Lord_Hat
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1001
+      TitleId: 1001
     Score: 60
     Score: 60
-  - ID: 200002
-    Group: "AG_GOAL_LEVEL"
-    Name: "Acquire the third aura!"
+  - Id: 200002
+    Group: Goal_Level
+    Name: Acquire the third aura!
     Condition: " BaseLevel >= 175 "
     Condition: " BaseLevel >= 175 "
-    Dependent:
-      - Id: 200001
-    Reward:
-      ItemID: 18880
+    Dependents:
+      200001: true
+    Rewards:
+      Item: BLACKDEATHKING_GOLDEN
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1002
+      TitleId: 1002
     Score: 70
     Score: 70
-  - ID: 200003
-    Group: "AG_GOAL_LEVEL"
-    Name: "Master Job level!"
+  - Id: 200003
+    Group: Goal_Level
+    Name: Master Job level!
     Condition: " JobLevel >= 50 "
     Condition: " JobLevel >= 50 "
-    Reward:
-      ItemID: 617
+    Rewards:
+      Item: Old_Violet_Box
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1003
+      TitleId: 1003
     Score: 30
     Score: 30
-  - ID: 200004
-    Group: "AG_GOAL_LEVEL"
-    Name: "Grandmaster Job level!"
+  - Id: 200004
+    Group: Goal_Level
+    Name: Grandmaster Job level!
     Condition: " JobLevel >= 70 "
     Condition: " JobLevel >= 70 "
-    Dependent:
-      - Id: 200003
-    Reward:
-      ItemID: 12817
+    Dependents:
+      200003: true
+    Rewards:
+      Item: Old_Card_Album_
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
-      TitleID: 1004
+      TitleId: 1004
     Score: 50
     Score: 50
-  - ID: 200005
-    Group: "AG_JOB_CHANGE"
-    Name: "Official Adventurer"
+  - Id: 200005
+    Group: Job_Change
+    Name: Official Adventurer
     Condition: " Class >= JOB_SWORDMAN && Class <= JOB_THIEF "
     Condition: " Class >= JOB_SWORDMAN && Class <= JOB_THIEF "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 200006
-    Group: "AG_JOB_CHANGE"
-    Name: "First step of job change!"
+  - Id: 200006
+    Group: Job_Change
+    Name: First step of job change!
     Condition: " Class >= JOB_SWORDMAN && Class <= JOB_THIEF "
     Condition: " Class >= JOB_SWORDMAN && Class <= JOB_THIEF "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 20
     Score: 20
-  - ID: 200007
-    Group: "AG_JOB_CHANGE"
-    Name: "Veteran Adventurer! (1)"
+  - Id: 200007
+    Group: Job_Change
+    Name: Veteran Adventurer! (1)
     Condition: " Class >= JOB_KNIGHT && Class <= JOB_ASSASSIN "
     Condition: " Class >= JOB_KNIGHT && Class <= JOB_ASSASSIN "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 25
     Score: 25
-  - ID: 200008
-    Group: "AG_JOB_CHANGE"
-    Name: "Veteran Adventurer! (2)"
+  - Id: 200008
+    Group: Job_Change
+    Name: Veteran Adventurer! (2)
     Condition: " Class >= JOB_CRUSADER && Class <= JOB_DANCER "
     Condition: " Class >= JOB_CRUSADER && Class <= JOB_DANCER "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 25
     Score: 25
-  - ID: 200009
-    Group: "AG_JOB_CHANGE"
-    Name: "Warrior (1)"
+  - Id: 200009
+    Group: Job_Change
+    Name: Warrior (1)
     Condition: " Class >= JOB_LORD_KNIGHT && Class <= JOB_ASSASSIN_CROSS "
     Condition: " Class >= JOB_LORD_KNIGHT && Class <= JOB_ASSASSIN_CROSS "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 30
     Score: 30
-  - ID: 200010
-    Group: "AG_JOB_CHANGE"
-    Name: "Warrior (2)"
+  - Id: 200010
+    Group: Job_Change
+    Name: Warrior (2)
     Condition: " Class >= JOB_PALADIN && Class <= JOB_GYPSY "
     Condition: " Class >= JOB_PALADIN && Class <= JOB_GYPSY "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 30
     Score: 30
-  - ID: 200011
-    Group: "AG_JOB_CHANGE"
-    Name: "Elite Adventurer! (1)"
+  - Id: 200011
+    Group: Job_Change
+    Name: Elite Adventurer! (1)
     Condition: " Class >= JOB_RUNE_KNIGHT && Class <= JOB_GUILLOTINE_CROSS "
     Condition: " Class >= JOB_RUNE_KNIGHT && Class <= JOB_GUILLOTINE_CROSS "
-    Reward:
-      ItemID: 16483
+    Rewards:
+      Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 50
     Score: 50
-  - ID: 200012
-    Group: "AG_JOB_CHANGE"
-    Name: "Transcendentaler! (1)"
+  - Id: 200012
+    Group: Job_Change
+    Name: Transcendentaler! (1)
     Condition: " Class >= JOB_RUNE_KNIGHT_T && Class <= JOB_GUILLOTINE_CROSS_T "
     Condition: " Class >= JOB_RUNE_KNIGHT_T && Class <= JOB_GUILLOTINE_CROSS_T "
-    Reward:
-      ItemID: 16483
+    Rewards:
+      Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 60
     Score: 60
-  - ID: 200013
-    Group: "AG_JOB_CHANGE"
-    Name: "Elite Adventurer! (2)"
+  - Id: 200013
+    Group: Job_Change
+    Name: Elite Adventurer! (2)
     Condition: " Class >= JOB_ROYAL_GUARD && Class <= JOB_SHADOW_CHASER "
     Condition: " Class >= JOB_ROYAL_GUARD && Class <= JOB_SHADOW_CHASER "
-    Reward:
-      ItemID: 16483
+    Rewards:
+      Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 50
     Score: 50
-  - ID: 200014
-    Group: "AG_JOB_CHANGE"
-    Name: "Transcendentaler! (2)"
+  - Id: 200014
+    Group: Job_Change
+    Name: Transcendentaler! (2)
     Condition: " Class >= JOB_ROYAL_GUARD_T && Class <= JOB_SHADOW_CHASER_T "
     Condition: " Class >= JOB_ROYAL_GUARD_T && Class <= JOB_SHADOW_CHASER_T "
-    Reward:
-      ItemID: 16483
+    Rewards:
+      Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 60
     Score: 60
-  - ID: 200015
-    Group: "AG_JOB_CHANGE"
-    Name: "The way of exceptional character"
+  - Id: 200015
+    Group: Job_Change
+    Name: The way of exceptional character
     Condition: " Class == JOB_SUPER_NOVICE || Class == JOB_GUNSLINGER || Class == JOB_NINJA || Class == JOB_TAEKWON "
     Condition: " Class == JOB_SUPER_NOVICE || Class == JOB_GUNSLINGER || Class == JOB_NINJA || Class == JOB_TAEKWON "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 200016
-    Group: "AG_JOB_CHANGE"
-    Name: "This is My way!"
+  - Id: 200016
+    Group: Job_Change
+    Name: This is My way!
     Condition: " Class == JOB_STAR_GLADIATOR || Class == JOB_SOUL_LINKER || Class == JOB_KAGEROU || Class == JOB_OBORO || Class == JOB_REBELLION "
     Condition: " Class == JOB_STAR_GLADIATOR || Class == JOB_SOUL_LINKER || Class == JOB_KAGEROU || Class == JOB_OBORO || Class == JOB_REBELLION "
-    Reward:
-      ItemID: 16483
+    Rewards:
+      Item: Abrasive_Box_10
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 20
     Score: 20
-  - ID: 200017
-    Group: "AG_GOAL_STATUS"
-    Name: "Bearish Power!"
+  - Id: 200017
+    Group: Goal_Status
+    Name: Bearish Power!
     Condition: " readparam(bStr) >= 90 "
     Condition: " readparam(bStr) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200018
-    Group: "AG_GOAL_STATUS"
-    Name: "Overflowing Magic!"
+  - Id: 200018
+    Group: Goal_Status
+    Name: Overflowing Magic!
     Condition: " readparam(bInt) >= 90 "
     Condition: " readparam(bInt) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200019
-    Group: "AG_GOAL_STATUS"
-    Name: "Healthy Body and Mental Health!"
+  - Id: 200019
+    Group: Goal_Status
+    Name: Healthy Body and Mental Health!
     Condition: " readparam(bVit) >= 90 "
     Condition: " readparam(bVit) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200020
-    Group: "AG_GOAL_STATUS"
-    Name: "Speed of Light"
+  - Id: 200020
+    Group: Goal_Status
+    Name: Speed of Light
     Condition: " readparam(bAgi) >= 90 "
     Condition: " readparam(bAgi) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200021
-    Group: "AG_GOAL_STATUS"
-    Name: "Hawk Eyes"
+  - Id: 200021
+    Group: Goal_Status
+    Name: Hawk Eyes
     Condition: " readparam(bDex) >= 90 "
     Condition: " readparam(bDex) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200022
-    Group: "AG_GOAL_STATUS"
-    Name: "Maximum Luck"
+  - Id: 200022
+    Group: Goal_Status
+    Name: Maximum Luck
     Condition: " readparam(bLuk) >= 90 "
     Condition: " readparam(bLuk) >= 90 "
     Score: 10
     Score: 10
-  - ID: 200023
-    Group: "AG_GOAL_STATUS"
-    Name: "Dragonlike Power!"
+  - Id: 200023
+    Group: Goal_Status
+    Name: Dragonlike Power!
     Condition: " readparam(bStr) >= 125 "
     Condition: " readparam(bStr) >= 125 "
-    Reward:
+    Rewards:
       Script: " sc_start SC_GIANTGROWTH,180000,1; "
       Script: " sc_start SC_GIANTGROWTH,180000,1; "
     Score: 20
     Score: 20
-  - ID: 200024
-    Group: "AG_GOAL_STATUS"
-    Name: "Magic Insanity"
+  - Id: 200024
+    Group: Goal_Status
+    Name: Magic Insanity
     Condition: " readparam(bInt) >= 125 "
     Condition: " readparam(bInt) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_HASTEUP; bonus_script \"{ bonus2 bHPLossRate,100,10000; bonus bBaseAtk,20; bonus bAspdRate,25; }\",60,0,0,EFST_STEAMPACK; "
       Script: " specialeffect2 EF_HASTEUP; bonus_script \"{ bonus2 bHPLossRate,100,10000; bonus bBaseAtk,20; bonus bAspdRate,25; }\",60,0,0,EFST_STEAMPACK; "
     Score: 20
     Score: 20
-  - ID: 200025
-    Group: "AG_GOAL_STATUS"
-    Name: "Rock Alloy"
+  - Id: 200025
+    Group: Goal_Status
+    Name: Rock Alloy
     Condition: " readparam(bVit) >= 125 "
     Condition: " readparam(bVit) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_HEAL3; sc_start2 SC_S_LIFEPOTION,600000,-5,5; "
       Script: " specialeffect2 EF_HEAL3; sc_start2 SC_S_LIFEPOTION,600000,-5,5; "
     Score: 20
     Score: 20
-  - ID: 200026
-    Group: "AG_GOAL_STATUS"
-    Name: "Speed of Light"
+  - Id: 200026
+    Group: Goal_Status
+    Name: Speed of Light
     Condition: " readparam(bAgi) >= 125 "
     Condition: " readparam(bAgi) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_STEAL; sc_start SC_INCFLEE2,60000,20; "
       Script: " specialeffect2 EF_STEAL; sc_start SC_INCFLEE2,60000,20; "
     Score: 20
     Score: 20
-  - ID: 200027
-    Group: "AG_GOAL_STATUS"
-    Name: "Falcon's Eyes"
+  - Id: 200027
+    Group: Goal_Status
+    Name: Falcon's Eyes
     Condition: " readparam(bDex) >= 125 "
     Condition: " readparam(bDex) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_MAGICALATTHIT; sc_start SC_INCCRI,300000,30; "
       Script: " specialeffect2 EF_MAGICALATTHIT; sc_start SC_INCCRI,300000,30; "
     Score: 20
     Score: 20
-  - ID: 200028
-    Group: "AG_GOAL_STATUS"
-    Name: "Lucky Fever"
+  - Id: 200028
+    Group: Goal_Status
+    Name: Lucky Fever
     Condition: " readparam(bLuk) >= 125 "
     Condition: " readparam(bLuk) >= 125 "
-    Reward:
+    Rewards:
       Script: " specialeffect2 EF_GLORIA; sc_start SC_GLORIA,15000,0; "
       Script: " specialeffect2 EF_GLORIA; sc_start SC_GLORIA,15000,0; "
     Score: 20
     Score: 20
-  - ID: 200029
-    Group: "AG_GOAL_STATUS"
-    Name: "Incarnation of Love and Hate"
+  - Id: 200029
+    Group: Goal_Status
+    Name: Incarnation of Love and Hate
     Condition: " BaseLevel == 99 && Class == JOB_NOVICE "
     Condition: " BaseLevel == 99 && Class == JOB_NOVICE "
-    Reward:
-      ItemID: 16483
+    Rewards:
+      Item: Abrasive_Box_10
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
     Score: 30
     Score: 30
-  - ID: 200030
-    Group: "AG_GOAL_STATUS"
-    Name: "I really love it!"
+  - Id: 200030
+    Group: Goal_Status
+    Name: I really love it!
     Condition: " BaseLevel == 99 && (Class >= JOB_SWORDMAN && Class <= JOB_THIEF) "
     Condition: " BaseLevel == 99 && (Class >= JOB_SWORDMAN && Class <= JOB_THIEF) "
-    Reward:
-      ItemID: 16504
+    Rewards:
+      Item: Bubble_Gum_Box_10
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
       Script: " specialeffect2 EF_BLESSING; sc_start SC_BLESSING,30000,10; "
     Score: 30
     Score: 30
-  - ID: 200031
-    Group: "AG_JOB_CHANGE"
-    Name: "Reborn in Valhalla!"
+  - Id: 200031
+    Group: Job_Change
+    Name: Reborn in Valhalla!
     Condition: " Class == JOB_NOVICE_HIGH "
     Condition: " Class == JOB_NOVICE_HIGH "
-    Reward:
-    #  ItemID: 23575
+    Rewards:
+    #  Item: Adventurer_Box_1
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 200032
-    Group: "AG_GOAL_LEVEL"
-    Name: "The start of another adventure!"
+  - Id: 200032
+    Group: Goal_Level
+    Name: The start of another adventure!
     Condition: " BaseLevel == 100 "
     Condition: " BaseLevel == 100 "
-    #Reward:
-    #  ItemID: 23585
+    #Rewards:
+    #  Item: Rebeginer_Box_100
     Score: 10
     Score: 10
-  - ID: 200033
-    Group: "AG_GOAL_LEVEL"
-    Name: "With a new mind!(1)"
+  - Id: 200033
+    Group: Goal_Level
+    Name: With a new mind!(1)
     Condition: " BaseLevel == 170 && (Class >= JOB_RUNE_KNIGHT && Class <= JOB_GUILLOTINE_CROSS_T) "
     Condition: " BaseLevel == 170 && (Class >= JOB_RUNE_KNIGHT && Class <= JOB_GUILLOTINE_CROSS_T) "
-    #Reward:
-    #  ItemID: 6959
+    #Rewards:
+    #  Item: Costume_Ticket
     Score: 50
     Score: 50
-  - ID: 200034
-    Group: "AG_GOAL_LEVEL"
-    Name: "With a new mind!(2)"
+  - Id: 200034
+    Group: Goal_Level
+    Name: With a new mind!(2)
     Condition: " BaseLevel == 170 && (Class >= JOB_ROYAL_GUARD && Class <= JOB_SHADOW_CHASER_T) "
     Condition: " BaseLevel == 170 && (Class >= JOB_ROYAL_GUARD && Class <= JOB_SHADOW_CHASER_T) "
-    #Reward:
-    #  ItemID: 6959
+    #Rewards:
+    #  Item: Costume_Ticket
     Score: 50
     Score: 50
-  - ID: 220000
-    Group: "AG_CHATTING_CREATE"
-    Name: "Community begin"
+  - Id: 220000
+    Group: Chatting_Create
+    Name: Community begin
+    Condition: " ARG0 == 1 "
     Score: 10
     Score: 10
-  - ID: 220001
-    Group: "AG_CHATTING_DYING"
-    Name: "A mouth only moment"
+  - Id: 220001
+    Group: Chatting_Dying
+    Name: A mouth only moment
+    Condition: " ARG0 == 1 "
     Score: 10
     Score: 10
-  - ID: 220002
-    Group: "AG_CHATTING_COUNT"
-    Name: "Admiring the chatter"
+  - Id: 220002
+    Group: Chatting_Count
+    Name: Admiring the chatter
     Condition: " ARG0 == 20 "
     Condition: " ARG0 == 20 "
     Score: 10
     Score: 10
-  - ID: 220003
-    Group: "AG_ADD_FRIEND"
-    Name: "My friend's friend~"
+  - Id: 220003
+    Group: Add_Friend
+    Name: My friend's friend~
     Condition: " ARG0 >= 1 "
     Condition: " ARG0 >= 1 "
     Score: 10
     Score: 10
-  - ID: 220004
-    Group: "AG_ADD_FRIEND"
-    Name: "A competition of popularity"
+  - Id: 220004
+    Group: Add_Friend
+    Name: A competition of popularity
     Condition: " ARG0 >= 10 "
     Condition: " ARG0 >= 10 "
     Score: 10
     Score: 10
-  - ID: 220005
-    Group: "AG_PARTY"
-    Name: "Let's Party~"
+  - Id: 220005
+    Group: Party
+    Name: Let's Party~
+    Condition: " ARG0 == 1 "
     Score: 10
     Score: 10
-  - ID: 220006
-    Group: "AG_MARRY"
-    Name: "Married with who..?"
-    Reward:
-      TitleID: 1022
+  - Id: 220006
+    Group: Marry
+    Name: Married with who..?
+    Rewards:
+      TitleId: 1022
     Score: 20
     Score: 20
-  - ID: 220007
-    Group: "AG_BABY"
-    Name: "Can you grow?"
+  - Id: 220007
+    Group: Baby
+    Name: Can you grow?
     Condition: " ARG0 == 1 "
     Condition: " ARG0 == 1 "
-    Reward:
-      TitleID: 1032
+    Rewards:
+      TitleId: 1032
     Score: 20
     Score: 20
-  - ID: 220008
-    Group: "AG_BABY"
-    Name: "Being a parent"
+  - Id: 220008
+    Group: Baby
+    Name: Being a parent
     Condition: " ARG0 == 2 "
     Condition: " ARG0 == 2 "
-    Reward:
-      TitleID: 1033
+    Rewards:
+      TitleId: 1033
     Score: 20
     Score: 20
-  - ID: 220009
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (1)"
-    Condition: " ARG0 >= 10000 "
-    Target:
+  - Id: 220009
+    Group: Spend_Zeny
+    Name: Activating the market economy (1)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 10000
         Count: 10000
+    Condition: " ARG0 >= 10000 "
     Score: 10
     Score: 10
-  - ID: 220010
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (2)"
-    Condition: " ARG0 >= 100000 "
-    Target:
+  - Id: 220010
+    Group: Spend_Zeny
+    Name: Activating the market economy (2)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 100000
         Count: 100000
+    Condition: " ARG0 >= 100000 "
     Score: 15
     Score: 15
-  - ID: 220011
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (3)"
-    Condition: " ARG0 >= 500000 "
-    Target:
+  - Id: 220011
+    Group: Spend_Zeny
+    Name: Activating the market economy (3)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 500000
         Count: 500000
+    Condition: " ARG0 >= 500000 "
     Score: 20
     Score: 20
-  - ID: 220012
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (4)"
-    Condition: " ARG0 >= 1000000 "
-    Target:
+  - Id: 220012
+    Group: Spend_Zeny
+    Name: Activating the market economy (4)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 1000000
         Count: 1000000
+    Condition: " ARG0 >= 1000000 "
     Score: 30
     Score: 30
-  - ID: 220013
-    Group: "AG_SPEND_ZENY"
-    Name: "Activating the market economy (5)"
-    Condition: " ARG0 >= 5000000 "
-    Target:
+  - Id: 220013
+    Group: Spend_Zeny
+    Name: Activating the market economy (5)
+    Targets:
       - Id: 0
       - Id: 0
         Count: 5000000
         Count: 5000000
+    Condition: " ARG0 >= 5000000 "
     Score: 50
     Score: 50
-  - ID: 220014
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (1)"
+  - Id: 220014
+    Group: Enchant_Success
+    Name: I can't quit from refining! (1)
     Condition: " ARG0 == 1 && ARG1 >= 7 "
     Condition: " ARG0 == 1 && ARG1 >= 7 "
     Score: 10
     Score: 10
-  - ID: 220015
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (2)"
+  - Id: 220015
+    Group: Enchant_Success
+    Name: I can't quit from refining! (2)
     Condition: " ARG0 == 1 && ARG1 >= 12 "
     Condition: " ARG0 == 1 && ARG1 >= 12 "
     Score: 15
     Score: 15
-  - ID: 220016
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (3)"
+  - Id: 220016
+    Group: Enchant_Success
+    Name: I can't quit from refining! (3)
     Condition: " ARG0 == 2 && ARG1 >= 7 "
     Condition: " ARG0 == 2 && ARG1 >= 7 "
     Score: 10
     Score: 10
-  - ID: 220017
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (4)"
+  - Id: 220017
+    Group: Enchant_Success
+    Name: I can't quit from refining! (4)
     Condition: " ARG0 == 2 && ARG1 >= 12 "
     Condition: " ARG0 == 2 && ARG1 >= 12 "
     Score: 15
     Score: 15
-  - ID: 220018
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (5)"
+  - Id: 220018
+    Group: Enchant_Success
+    Name: I can't quit from refining! (5)
     Condition: " ARG0 == 3 && ARG1 >= 7 "
     Condition: " ARG0 == 3 && ARG1 >= 7 "
     Score: 15
     Score: 15
-  - ID: 220019
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (6)"
+  - Id: 220019
+    Group: Enchant_Success
+    Name: I can't quit from refining! (6)
     Condition: " ARG0 == 3 && ARG1 >= 12 "
     Condition: " ARG0 == 3 && ARG1 >= 12 "
     Score: 20
     Score: 20
-  - ID: 220020
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (7)"
+  - Id: 220020
+    Group: Enchant_Success
+    Name: I can't quit from refining! (7)
     Condition: " ARG0 == 4 && ARG1 >= 7 "
     Condition: " ARG0 == 4 && ARG1 >= 7 "
     Score: 20
     Score: 20
-  - ID: 220021
-    Group: "AG_ENCHANT_SUCCESS"
-    Name: "I can't quit from refining! (8)"
+  - Id: 220021
+    Group: Enchant_Success
+    Name: I can't quit from refining! (8)
     Condition: " ARG0 == 4 && ARG1 >= 12 "
     Condition: " ARG0 == 4 && ARG1 >= 12 "
     Score: 30
     Score: 30
-  - ID: 220022
-    Group: "AG_ENCHANT_FAIL"
-    Name: "Human's greed has no ending.."
+  - Id: 220022
+    Group: Enchant_Fail
+    Name: Human's greed has no ending..
+    Condition: " ARG0 == 1 "
     Score: 10
     Score: 10
-  - ID: 220023
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (1)"
+  - Id: 220023
+    Group: Get_Item
+    Name: I found it! (1)
     Condition: " ARG0 >= 100 "
     Condition: " ARG0 >= 100 "
     Score: 10
     Score: 10
-  - ID: 220024
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (2)"
+  - Id: 220024
+    Group: Get_Item
+    Name: I found it! (2)
     Condition: " ARG0 >= 1000 "
     Condition: " ARG0 >= 1000 "
     Score: 10
     Score: 10
-  - ID: 220025
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (3)"
+  - Id: 220025
+    Group: Get_Item
+    Name: I found it! (3)
     Condition: " ARG0 >= 5000 "
     Condition: " ARG0 >= 5000 "
     Score: 15
     Score: 15
-  - ID: 220026
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (4)"
+  - Id: 220026
+    Group: Get_Item
+    Name: I found it! (4)
     Condition: " ARG0 >= 10000 "
     Condition: " ARG0 >= 10000 "
     Score: 15
     Score: 15
-  - ID: 220027
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (5)"
+  - Id: 220027
+    Group: Get_Item
+    Name: I found it! (5)
     Condition: " ARG0 >= 50000 "
     Condition: " ARG0 >= 50000 "
     Score: 20
     Score: 20
-  - ID: 220028
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (6)"
+  - Id: 220028
+    Group: Get_Item
+    Name: I found it! (6)
     Condition: " ARG0 >= 100000 "
     Condition: " ARG0 >= 100000 "
     Score: 20
     Score: 20
-  - ID: 220029
-    Group: "AG_GET_ITEM"
-    Name: "I found it! (7)"
+  - Id: 220029
+    Group: Get_Item
+    Name: I found it! (7)
     Condition: " ARG0 >= 150000 "
     Condition: " ARG0 >= 150000 "
     Score: 30
     Score: 30
-  - ID: 220030
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (1)"
+  - Id: 220030
+    Group: Get_Zeny
+    Name: Rich King (1)
     Condition: " ARG0 >= 10000 "
     Condition: " ARG0 >= 10000 "
     Score: 10
     Score: 10
-  - ID: 220031
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (2)"
+  - Id: 220031
+    Group: Get_Zeny
+    Name: Rich King (2)
     Condition: " ARG0 >= 100000 "
     Condition: " ARG0 >= 100000 "
     Score: 15
     Score: 15
-  - ID: 220032
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (3)"
+  - Id: 220032
+    Group: Get_Zeny
+    Name: Rich King (3)
     Condition: " ARG0 >= 1000000 "
     Condition: " ARG0 >= 1000000 "
     Score: 20
     Score: 20
-  - ID: 220033
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (4)"
+  - Id: 220033
+    Group: Get_Zeny
+    Name: Rich King (4)
     Condition: " ARG0 >= 10000000 "
     Condition: " ARG0 >= 10000000 "
     Score: 25
     Score: 25
-  - ID: 220034
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (5)"
+  - Id: 220034
+    Group: Get_Zeny
+    Name: Rich King (5)
     Condition: " ARG0 >= 100000000 "
     Condition: " ARG0 >= 100000000 "
     Score: 30
     Score: 30
-  - ID: 220035
-    Group: "AG_GET_ZENY"
-    Name: "Rich King (6)"
+  - Id: 220035
+    Group: Get_Zeny
+    Name: Rich King (6)
     Condition: " ARG0 >= 1000000000 "
     Condition: " ARG0 >= 1000000000 "
     Score: 40
     Score: 40
-  - ID: 230100
-    Group: "AG_TAMING"
-    Name: "Poring is Love"
-    Dependent:
-      - Id: 230101
-      - Id: 230102
-      - Id: 230103
-      - Id: 230104
-    Reward:
+  - Id: 230100
+    Group: Taming
+    Name: Poring is Love
+    Dependents:
+      230101: true
+      230102: true
+      230103: true
+      230104: true
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1025
+      TitleId: 1025
     Score: 50
     Score: 50
-  - ID: 230110
-    Group: "AG_TAMING"
-    Name: "Entomologist"
-    Dependent:
-      - Id: 230111
-      - Id: 230112
-      - Id: 230113
-      - Id: 230114
-      - Id: 230115
-      - Id: 230116
-    Reward:
+  - Id: 230110
+    Group: Taming
+    Name: Entomologist
+    Dependents:
+      230111: true
+      230112: true
+      230113: true
+      230114: true
+      230115: true
+      230116: true
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1026
+      TitleId: 1026
     Score: 50
     Score: 50
-  - ID: 230120
-    Group: "AG_TAMING"
-    Name: "Animals are also our friend"
-    Dependent:
-      - Id: 230121
-      - Id: 230122
-      - Id: 230123
-      - Id: 230124
-      - Id: 230125
-      - Id: 230126
-      - Id: 230127
-      - Id: 230128
-    Reward:
+  - Id: 230120
+    Group: Taming
+    Name: Animals are also our friend
+    Dependents:
+      230121: true
+      230122: true
+      230123: true
+      230124: true
+      230125: true
+      230126: true
+      230127: true
+      230128: true
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1027
+      TitleId: 1027
     Score: 50
     Score: 50
-  - ID: 230140
-    Group: "AG_TAMING"
-    Name: "Monster Girls Unite!!"
-    Dependent:
-      - Id: 230141
-      - Id: 230142
-      - Id: 230143
-      - Id: 230144
-      - Id: 230145
-      - Id: 230146
-      - Id: 230147
-    Reward:
+  - Id: 230140
+    Group: Taming
+    Name: Monster Girls Unite!!
+    Dependents:
+      230141: true
+      230142: true
+      230143: true
+      230144: true
+      230145: true
+      230146: true
+      230147: true
+    Rewards:
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1029
+      TitleId: 1029
     Score: 50
     Score: 50
-  - ID: 230101
-    Group: "AG_TAMING"
-    Name: "Poring - taming"
-    Target:
+  - Id: 230101
+    Group: Taming
+    Name: Poring - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1002
-        Count: 1
+        Mob: PORING
     Score: 10
     Score: 10
-  - ID: 230102
-    Group: "AG_TAMING"
-    Name: "Drops - taming"
-    Target:
+  - Id: 230102
+    Group: Taming
+    Name: Drops - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1113
-        Count: 1
+        Mob: DROPS
     Score: 10
     Score: 10
-  - ID: 230103
-    Group: "AG_TAMING"
-    Name: "Poporing - taming"
-    Target:
+  - Id: 230103
+    Group: Taming
+    Name: Poporing - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1031
-        Count: 1
+        Mob: POPORING
     Score: 10
     Score: 10
-  - ID: 230104
-    Group: "AG_TAMING"
-    Name: "Novice Poring - taming"
-    Target:
+  - Id: 230104
+    Group: Taming
+    Name: Novice Poring - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 2398
-        Count: 1
+        Mob: LITTLE_PORING
     Score: 10
     Score: 10
-  - ID: 230111
-    Group: "AG_TAMING"
-    Name: "Chonchon - taming"
-    Target:
+  - Id: 230111
+    Group: Taming
+    Name: Chonchon - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1011
-        Count: 1
+        Mob: CHONCHON
     Score: 10
     Score: 10
-  - ID: 230112
-    Group: "AG_TAMING"
-    Name: "Steel Chonchon - taming"
-    Target:
+  - Id: 230112
+    Group: Taming
+    Name: Steel Chonchon - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1042
-        Count: 1
+        Mob: STEEL_CHONCHON
     Score: 10
     Score: 10
-  - ID: 230113
-    Group: "AG_TAMING"
-    Name: "Hunter Fly - taming"
-    Target:
+  - Id: 230113
+    Group: Taming
+    Name: Hunter Fly - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1035
-        Count: 1
+        Mob: HUNTER_FLY
     Score: 10
     Score: 10
-  - ID: 230114
-    Group: "AG_TAMING"
-    Name: "Rocker - taming"
-    Target:
+  - Id: 230114
+    Group: Taming
+    Name: Rocker - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1052
-        Count: 1
+        Mob: ROCKER
     Score: 10
     Score: 10
-  - ID: 230115
-    Group: "AG_TAMING"
-    Name: "Spore - taming"
-    Target:
+  - Id: 230115
+    Group: Taming
+    Name: Spore - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1014
-        Count: 1
+        Mob: SPORE
     Score: 10
     Score: 10
-  - ID: 230116
-    Group: "AG_TAMING"
-    Name: "Poison Spore - taming"
-    Target:
+  - Id: 230116
+    Group: Taming
+    Name: Poison Spore - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1077
-        Count: 1
+        Mob: POISON_SPORE
     Score: 10
     Score: 10
-  - ID: 230121
-    Group: "AG_TAMING"
-    Name: "Lunatic - taming"
-    Target:
+  - Id: 230121
+    Group: Taming
+    Name: Lunatic - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1063
-        Count: 1
+        Mob: LUNATIC
     Score: 10
     Score: 10
-  - ID: 230122
-    Group: "AG_TAMING"
-    Name: "Picky - taming"
-    Target:
+  - Id: 230122
+    Group: Taming
+    Name: Picky - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1049
-        Count: 1
+        Mob: PICKY
     Score: 10
     Score: 10
-  - ID: 230123
-    Group: "AG_TAMING"
-    Name: "Savage Bebe - taming"
-    Target:
+  - Id: 230123
+    Group: Taming
+    Name: Savage Bebe - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1167
-        Count: 1
+        Mob: SAVAGE_BABE
     Score: 10
     Score: 10
-  - ID: 230124
-    Group: "AG_TAMING"
-    Name: "Baby Desert Wolf - taming"
-    Target:
+  - Id: 230124
+    Group: Taming
+    Name: Baby Desert Wolf - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1107
-        Count: 1
+        Mob: DESERT_WOLF_B
     Score: 10
     Score: 10
-  - ID: 230125
-    Group: "AG_TAMING"
-    Name: "Smokie - taming"
-    Target:
+  - Id: 230125
+    Group: Taming
+    Name: Smokie - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1056
-        Count: 1
+        Mob: SMOKIE
     Score: 10
     Score: 10
-  - ID: 230126
-    Group: "AG_TAMING"
-    Name: "Yoyo - taming"
-    Target:
+  - Id: 230126
+    Group: Taming
+    Name: Yoyo - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1057
-        Count: 1
+        Mob: YOYO
     Score: 10
     Score: 10
-  - ID: 230127
-    Group: "AG_TAMING"
-    Name: "Peco Peco - taming"
-    Target:
+  - Id: 230127
+    Group: Taming
+    Name: Peco Peco - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1019
-        Count: 1
+        Mob: PECOPECO
     Score: 10
     Score: 10
-  - ID: 230128
-    Group: "AG_TAMING"
-    Name: "Petite - taming"
-    Target:
+  - Id: 230128
+    Group: Taming
+    Name: Petite - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1155
-        Count: 1
+        Mob: PETIT
     Score: 10
     Score: 10
-  - ID: 230141
-    Group: "AG_TAMING"
-    Name: "Munak - taming"
-    Target:
+  - Id: 230141
+    Group: Taming
+    Name: Munak - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1026
-        Count: 1
+        Mob: MUNAK
     Score: 10
     Score: 10
-  - ID: 230142
-    Group: "AG_TAMING"
-    Name: "Isis - taming"
-    Target:
+  - Id: 230142
+    Group: Taming
+    Name: Isis - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1029
-        Count: 1
+        Mob: ISIS
     Score: 10
     Score: 10
-  - ID: 230143
-    Group: "AG_TAMING"
-    Name: "Sohee - taming"
-    Target:
+  - Id: 230143
+    Group: Taming
+    Name: Sohee - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1170
-        Count: 1
+        Mob: SOHEE
     Score: 10
     Score: 10
-  - ID: 230144
-    Group: "AG_TAMING"
-    Name: "Zherlthsh - taming"
-    Target:
+  - Id: 230144
+    Group: Taming
+    Name: Zherlthsh - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1200
-        Count: 1
+        Mob: ZHERLTHSH
     Score: 10
     Score: 10
-  - ID: 230145
-    Group: "AG_TAMING"
-    Name: "Alice - taming"
-    Target:
+  - Id: 230145
+    Group: Taming
+    Name: Alice - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1275
-        Count: 1
+        Mob: ALICE
     Score: 10
     Score: 10
-  - ID: 230146
-    Group: "AG_TAMING"
-    Name: "Succubus - taming"
-    Target:
+  - Id: 230146
+    Group: Taming
+    Name: Succubus - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1370
-        Count: 1
+        Mob: SUCCUBUS
     Score: 10
     Score: 10
-  - ID: 230147
-    Group: "AG_TAMING"
-    Name: "Loli Ruri - taming"
-    Target:
+  - Id: 230147
+    Group: Taming
+    Name: Loli Ruri - taming
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1505
-        Count: 1
+        Mob: LOLI_RURI
     Score: 10
     Score: 10
-  - ID: 230200
-    Group: "AG_BATTLE"
-    Name: "Poring seeker"
-    Dependent:
-      - Id: 230201
-      - Id: 230202
-      - Id: 230203
+  - Id: 230200
+    Group: Battle
+    Name: Poring seeker
+    Dependents:
+      230201: true
+      230202: true
+      230203: true
     Score: 10
     Score: 10
-  - ID: 230201
-    Group: "AG_BATTLE"
-    Name: "Exploring Poring's life (1)"
-    Target:
+  - Id: 230201
+    Group: Battle
+    Name: Exploring Poring's life (1)
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1002
+        Mob: PORING
         Count: 10
         Count: 10
       - Id: 1
       - Id: 1
-        MobID: 2398
+        Mob: LITTLE_PORING
         Count: 10
         Count: 10
       - Id: 2
       - Id: 2
-        MobID: 1113
+        Mob: DROPS
         Count: 10
         Count: 10
       - Id: 3
       - Id: 3
-        MobID: 1031
+        Mob: POPORING
         Count: 10
         Count: 10
       - Id: 4
       - Id: 4
-        MobID: 1242
+        Mob: MARIN
         Count: 10
         Count: 10
     Score: 10
     Score: 10
-  - ID: 230202
-    Group: "AG_BATTLE"
-    Name: "Exploring Poring's life (2)"
-    Target:
+  - Id: 230202
+    Group: Battle
+    Name: Exploring Poring's life (2)
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1090
-        Count: 1
+        Mob: MASTERING
       - Id: 1
       - Id: 1
-        MobID: 1582
-        Count: 1
+        Mob: DEVILING
       - Id: 2
       - Id: 2
-        MobID: 1096
-        Count: 1
+        Mob: ANGELING
       - Id: 3
       - Id: 3
-        MobID: 1388
-        Count: 1
+        Mob: ARCHANGELING
       - Id: 4
       - Id: 4
-        MobID: 1120
-        Count: 1
+        Mob: GHOSTRING
     Score: 20
     Score: 20
-  - ID: 230203
-    Group: "AG_BATTLE"
-    Name: "Exploring Poring's life (3)"
-    Target:
+  - Id: 230203
+    Group: Battle
+    Name: Exploring Poring's life (3)
+    Targets:
       - Id: 0
       - Id: 0
-        MobID: 1613
+        Mob: METALING
         Count: 5
         Count: 5
       - Id: 1
       - Id: 1
-        MobID: 1977
+        Mob: HEAVY_METALING
         Count: 5
         Count: 5
       - Id: 2
       - Id: 2
-        MobID: 1836
+        Mob: MAGMARING
         Count: 5
         Count: 5
     Score: 20
     Score: 20
-  - ID: 240000
-    Group: "AG_GOAL_LEVEL"
-    Name: "First Login after the introduction of Achievement Tasks"
-    Score: 10
+  - Id: 240000
+    Group: Goal_Level
+    Name: First Login after the introduction of Achievement Tasks
     Condition: " true "
     Condition: " true "
-  - ID: 240001
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 1"
+    Score: 10
+  - Id: 240001
+    Group: Goal_Achieve
+    Name: Reaching Level 1
     Condition: " AchievementLevel >= 1 "
     Condition: " AchievementLevel >= 1 "
-    Reward:
-      ItemID: 644
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240002
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 2"
+  - Id: 240002
+    Group: Goal_Achieve
+    Name: Reaching Level 2
     Condition: " AchievementLevel >= 2 "
     Condition: " AchievementLevel >= 2 "
-    Dependent:
-      - Id: 240001
-    Reward:
-      ItemID: 644
+    Dependents:
+      240001: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240003
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 3"
+  - Id: 240003
+    Group: Goal_Achieve
+    Name: Reaching Level 3
     Condition: " AchievementLevel >= 3 "
     Condition: " AchievementLevel >= 3 "
-    Dependent:
-      - Id: 240002
-    Reward:
-      ItemID: 644
+    Dependents:
+      240002: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240004
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 4"
+  - Id: 240004
+    Group: Goal_Achieve
+    Name: Reaching Level 4
     Condition: " AchievementLevel >= 4 "
     Condition: " AchievementLevel >= 4 "
-    Dependent:
-      - Id: 240003
-    Reward:
-      ItemID: 644
+    Dependents:
+      240003: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240005
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 5"
+  - Id: 240005
+    Group: Goal_Achieve
+    Name: Reaching Level 5
     Condition: " AchievementLevel >= 5 "
     Condition: " AchievementLevel >= 5 "
-    Dependent:
-      - Id: 240004
-    Reward:
-      ItemID: 644
+    Dependents:
+      240004: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240006
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 6"
+  - Id: 240006
+    Group: Goal_Achieve
+    Name: Reaching Level 6
     Condition: " AchievementLevel >= 6 "
     Condition: " AchievementLevel >= 6 "
-    Dependent:
-      - Id: 240005
-    Reward:
-      ItemID: 644
+    Dependents:
+      240005: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240007
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 7"
+  - Id: 240007
+    Group: Goal_Achieve
+    Name: Reaching Level 7
     Condition: " AchievementLevel >= 7 "
     Condition: " AchievementLevel >= 7 "
-    Dependent:
-      - Id: 240006
-    Reward:
-      ItemID: 644
+    Dependents:
+      240006: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240008
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 8"
+  - Id: 240008
+    Group: Goal_Achieve
+    Name: Reaching Level 8
     Condition: " AchievementLevel >= 8 "
     Condition: " AchievementLevel >= 8 "
-    Dependent:
-      - Id: 240007
-    Reward:
-      ItemID: 644
+    Dependents:
+      240007: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240009
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 9"
+  - Id: 240009
+    Group: Goal_Achieve
+    Name: Reaching Level 9
     Condition: " AchievementLevel >= 9 "
     Condition: " AchievementLevel >= 9 "
-    Dependent:
-      - Id: 240008
-    Reward:
-      ItemID: 644
+    Dependents:
+      240008: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240010
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 10"
+  - Id: 240010
+    Group: Goal_Achieve
+    Name: Reaching Level 10
     Condition: " AchievementLevel >= 10 "
     Condition: " AchievementLevel >= 10 "
-    Dependent:
-      - Id: 240009
-    Reward:
-      ItemID: 644
+    Dependents:
+      240009: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1023
+      TitleId: 1023
     Score: 10
     Score: 10
-  - ID: 240011
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 11"
+  - Id: 240011
+    Group: Goal_Achieve
+    Name: Reaching Level 11
     Condition: " AchievementLevel >= 11 "
     Condition: " AchievementLevel >= 11 "
-    Dependent:
-      - Id: 240010
-    Reward:
-      ItemID: 644
+    Dependents:
+      240010: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240012
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 12"
+  - Id: 240012
+    Group: Goal_Achieve
+    Name: Reaching Level 12
     Condition: " AchievementLevel >= 12 "
     Condition: " AchievementLevel >= 12 "
-    Dependent:
-      - Id: 240011
-    Reward:
-      ItemID: 644
+    Dependents:
+      240011: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240013
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 13"
+  - Id: 240013
+    Group: Goal_Achieve
+    Name: Reaching Level 13
     Condition: " AchievementLevel >= 13 "
     Condition: " AchievementLevel >= 13 "
-    Dependent:
-      - Id: 240012
-    Reward:
-      ItemID: 644
+    Dependents:
+      240012: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240014
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 14"
+  - Id: 240014
+    Group: Goal_Achieve
+    Name: Reaching Level 14
     Condition: " AchievementLevel >= 14 "
     Condition: " AchievementLevel >= 14 "
-    Dependent:
-      - Id: 240013
-    Reward:
-      ItemID: 644
+    Dependents:
+      240013: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240015
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 15"
+  - Id: 240015
+    Group: Goal_Achieve
+    Name: Reaching Level 15
     Condition: " AchievementLevel >= 15 "
     Condition: " AchievementLevel >= 15 "
-    Dependent:
-      - Id: 240014
-    Reward:
-      ItemID: 644
+    Dependents:
+      240014: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240016
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 16"
+  - Id: 240016
+    Group: Goal_Achieve
+    Name: Reaching Level 16
     Condition: " AchievementLevel >= 16 "
     Condition: " AchievementLevel >= 16 "
-    Dependent:
-      - Id: 240015
-    Reward:
-      ItemID: 644
+    Dependents:
+      240015: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240017
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 17"
+  - Id: 240017
+    Group: Goal_Achieve
+    Name: Reaching Level 17
     Condition: " AchievementLevel >= 17 "
     Condition: " AchievementLevel >= 17 "
-    Dependent:
-      - Id: 240016
-    Reward:
-      ItemID: 644
+    Dependents:
+      240016: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240018
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 18"
+  - Id: 240018
+    Group: Goal_Achieve
+    Name: Reaching Level 18
     Condition: " AchievementLevel >= 18 "
     Condition: " AchievementLevel >= 18 "
-    Dependent:
-      - Id: 240017
-    Reward:
-      ItemID: 644
+    Dependents:
+      240017: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240019
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 19"
+  - Id: 240019
+    Group: Goal_Achieve
+    Name: Reaching Level 19
     Condition: " AchievementLevel >= 19 "
     Condition: " AchievementLevel >= 19 "
-    Dependent:
-      - Id: 240018
-    Reward:
-      ItemID: 644
+    Dependents:
+      240018: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
     Score: 10
     Score: 10
-  - ID: 240020
-    Group: "AG_GOAL_ACHIEVE"
-    Name: "Reaching Level 20"
+  - Id: 240020
+    Group: Goal_Achieve
+    Name: Reaching Level 20
     Condition: " AchievementLevel >= 20 "
     Condition: " AchievementLevel >= 20 "
-    Dependent:
-      - Id: 240019
-    Reward:
-      ItemID: 644
+    Dependents:
+      240019: true
+    Rewards:
+      Item: Gift_Box
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
       Script: " specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,30000,10; "
-      TitleID: 1024
+      TitleId: 1024
     Score: 10
     Score: 10

+ 3 - 4
db/re/achievement_level_db.yml

@@ -16,15 +16,14 @@
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 # along with this program. If not, see <http://www.gnu.org/licenses/>.
 #
 #
 ###########################################################################
 ###########################################################################
-# Renewal Achievement Level Database
+# Achievement Level Database
 ###########################################################################
 ###########################################################################
 #
 #
 # Achievement Level Settings
 # Achievement Level Settings
 #
 #
 ###########################################################################
 ###########################################################################
-# Level - Achievement Level
-###########################################################################
-# Points - Required total scoring points to reach this level.
+# - Level     Achievement Level.
+#   Points    Required total scoring points to reach this level.
 ###########################################################################
 ###########################################################################
 
 
 Header:
 Header:

+ 12 - 14
db/readme.md

@@ -18,20 +18,18 @@ We want to add our own custom achievement that can be given to a player via an N
 
 
 #### /db/import/achievement_db.yml
 #### /db/import/achievement_db.yml
 
 
-
-    Achievements:
-      - ID: 280000
-        Group: "AG_GOAL_ACHIEVE"
-        Name: "Emperio"
-        Reward:
-          TitleID: 1035
-        Score: 50
-      - ID: 280001
-        Group: "AG_GOAL_ACHIEVE"
-        Name: "Staff"
-        Reward:
-          TitleID: 1036
-        Score: 50
+    - Id: 280000
+      Group: None
+      Name: Emperio
+      Reward:
+        TitleId: 1035
+      Score: 50
+    - Id: 280001
+      Group: None
+      Name: Staff
+      Reward:
+        TitleId: 1036
+      Score: 50
 
 
 
 
 ### Instances
 ### Instances

+ 49 - 37
doc/achievements.txt

@@ -3,59 +3,60 @@
 //===== By: ==================================================
 //===== By: ==================================================
 //= rAthena Dev Team
 //= rAthena Dev Team
 //===== Last Updated: ========================================
 //===== Last Updated: ========================================
-//= 20190226
+//= 20200220
 //===== Description: =========================================
 //===== Description: =========================================
 //= Explanation of the achievements_db.yml file and structure.
 //= Explanation of the achievements_db.yml file and structure.
 //============================================================
 //============================================================
 
 
 ---------------------------------------
 ---------------------------------------
 
 
-ID: Unique achievement ID.
+Id: Unique achievement ID.
 
 
 ---------------------------------------
 ---------------------------------------
 
 
 Group: Achievement group type. Each achievement type calls a specific objective check.
 Group: Achievement group type. Each achievement type calls a specific objective check.
 Valid groups:
 Valid groups:
-	AG_ADD_FRIEND - Triggered when a player adds a friend.
-	AG_ADVENTURE - Does not trigger automatically. These are triggered by the achievementcomplete script command.
-	AG_BABY - Triggered when a player becomes a baby job.
-	AG_BATTLE - Triggered when a player kills a monster.
-	AG_CHATTING - Unknown.
-	AG_CHATTING_COUNT - Triggered when a player has a chatroom open and others join.
-	AG_CHATTING_CREATE - Triggered when a player creates a chatroom.
-	AG_CHATTING_DYING - Triggered when a player creates a chatroom and dies with it open.
-	AG_EAT - Unknown.
-	AG_GET_ITEM - Triggered when a player gets an item that has a specific sell value.
-	AG_GET_ZENY - Triggered when a player gets a specific amount of zeny at once.
-	AG_GOAL_ACHIEVE - Triggered when a player's achievement rank levels up.
-	AG_GOAL_LEVEL - Triggered when a player's base level or job level changes.
-	AG_GOAL_STATUS - Triggered when a player's base stats changes.
-	AG_HEAR - Unknown.
-	AG_JOB_CHANGE - Triggered when a player's job changes.
-	AG_MARRY - Triggered when two players get married.
-	AG_PARTY - Triggered when a player creates a party.
-	AG_ENCHANT_FAIL - Triggered when a player fails to refine an equipment.
-	AG_ENCHANT_SUCCESS - Triggered when a player successfully refines an equipment.
-	AG_SEE - Unknown.
-	AG_SPEND_ZENY - Triggered when a player spends any amount of zeny on vendors.
-	AG_TAMING - Triggered when a player tames a monster.
+	None - Can be used for custom achievements that are given through a script with no trigger events.
+	Add_Friend - Triggered when a player adds a friend.
+	Adventure - Does not trigger automatically. These are triggered by the achievementcomplete script command.
+	Baby - Triggered when a player becomes a baby job.
+	Battle - Triggered when a player kills a monster.
+	Chatting - Aegis uses this when talking to a NPC. These are triggered by the achievementupdate script command.
+	Chatting_Count - Triggered when a player has a chatroom open and others join.
+	Chatting_Create - Triggered when a player creates a chatroom.
+	Chatting_Dying - Triggered when a player creates a chatroom and dies with it open.
+	Eat - Unknown.
+	Get_Item - Triggered when a player gets an item that has a specific sell value.
+	Get_Zeny - Triggered when a player gets a specific amount of zeny at once.
+	Goal_Achieve - Triggered when a player's achievement rank levels up.
+	Goal_Level - Triggered when a player's base level or job level changes.
+	Goal_Status - Triggered when a player's base stats changes.
+	Job_Change - Triggered when a player's job changes.
+	Marry - Triggered when two players get married.
+	Party - Triggered when a player creates a party.
+	Enchant_Fail - Triggered when a player fails to refine an equipment.
+	Enchant_Success - Triggered when a player successfully refines an equipment.
+	Spend_Zeny - Triggered when a player spends any amount of zeny on vendors.
+	Taming - Triggered when a player tames a monster.
 
 
 ---------------------------------------
 ---------------------------------------
 
 
-Name: Achievement name. Not read into source but used for quick look ups.
+Name: Achievement name. Used when sending rewards through RODEX.
 
 
 ---------------------------------------
 ---------------------------------------
 
 
-Target: A list of monster ID and count values that the achievement requires.
+Targets: A list of monster names and count values that the achievement requires.
 		The target count can also be used for achievements that keep a counter while not being related to monster kills.
 		The target count can also be used for achievements that keep a counter while not being related to monster kills.
 		Capped at MAX_ACHIEVEMENT_OBJECTIVES.
 		Capped at MAX_ACHIEVEMENT_OBJECTIVES.
 
 
 Example:
 Example:
   // Player must kill 5 Scorpions and 10 Poring.
   // Player must kill 5 Scorpions and 10 Poring.
-  Target:
-    - MobID: 1001
+  Targets:
+    - Id: 0
+      Mob: SCORPION
       Count: 5
       Count: 5
-    - MobID: 1002
+    - Id: 1
+      Mob: PORING
       Count: 10
       Count: 10
 
 
 Example 2:
 Example 2:
@@ -63,7 +64,7 @@ Example 2:
   // and not checked for a total (UI_Type = 1).
   // and not checked for a total (UI_Type = 1).
   // IE: In the achievement_list.lub file, UI_Type 0 is displayed as non-incremental while 1 shows a progress bar of completion for the achievement.
   // IE: In the achievement_list.lub file, UI_Type 0 is displayed as non-incremental while 1 shows a progress bar of completion for the achievement.
   Condition: " ARG0 >= 100 "
   Condition: " ARG0 >= 100 "
-  Target:
+  Targets:
     - Id: 0 // Array index value
     - Id: 0 // Array index value
       Count: 100
       Count: 100
 
 
@@ -84,19 +85,30 @@ Example 2:
 
 
 ---------------------------------------
 ---------------------------------------
 
 
-Map: A map name that is used for the AG_CHATTING type which increments the counter based on the player's map.
+Map: A map name that is used for the Chatting group which increments the counter based on the player's map.
+NOTICE: This option is currently disabled until the official behavior is confirmed.
 
 
 ---------------------------------------
 ---------------------------------------
 
 
-Dependent: A list of achievement IDs that need to be completed before this achievement is considered complete.
+Dependents: A list of achievement IDs that need to be completed before this achievement is considered complete.
+
+Example:
+  // Player must complete achievements 10001 and 10002 first.
+  Dependents:
+    10001: true
+    10002: true
+
+  // Used with the import, dependent achievements can be disabled. The player now only requires completion of achievement 10001.
+  Dependents:
+    10002: false
 
 
 ---------------------------------------
 ---------------------------------------
 
 
-Reward: A list of rewards that are given on completion. All fields are optional.
-  ItemID: Item ID
-  Amount:	Amount of Item ID (default 1)
+Rewards: A list of rewards that are given on completion. All fields are optional.
+  Item: Item Name
+  Amount: Amount of Item (Default: 1)
   Script: Bonus Script
   Script: Bonus Script
-  TitleID: Title ID
+  TitleId: Title ID
 
 
 ---------------------------------------
 ---------------------------------------
 
 

+ 25 - 0
doc/yaml/db/achievement_db.yml

@@ -0,0 +1,25 @@
+###########################################################################
+# Achievement Database
+###########################################################################
+#
+# Achievement Settings
+#
+###########################################################################
+# - Id                  Achievement ID.
+#   Group               Achievement group type. (Defaut: None)
+#   Name                Achievement name.
+#   Targets:            List of targets the achievement requires. (Default: null)
+#     - Id              Index value used for import methods.
+#       Mob             Target mob. (Default: 0)
+#       Count           Target count. (Default: 1)
+#   Condition           Conditional statement that must be met for the achievement to be considered complete. (Default: null)
+#   Map                 Map name that is used for the AG_CHATTING type. (Default: -1)
+#   Dependents:         List of achievements that need to be completed before this achievement is considered complete. (Default: null)
+#     - Id: <bool>      Achievement ID pre-requisite.
+#   Rewards:            List of rewards that are given on completion. (Default: null)
+#     Item              Item name.
+#     Amount            Amount of item. (Default: 1)
+#     Script            Bonus Script. (Default: null)
+#     TitleId           Title ID. (Default: 0)
+#   Score               Achievement points that are given on completion. (Default: 0)
+###########################################################################

+ 15 - 0
rAthena.sln

@@ -83,6 +83,12 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "yaml2sql", "src\tool\yaml2s
 		{352B45B3-FE88-4431-9D89-48CF811446DB} = {352B45B3-FE88-4431-9D89-48CF811446DB}
 		{352B45B3-FE88-4431-9D89-48CF811446DB} = {352B45B3-FE88-4431-9D89-48CF811446DB}
 	EndProjectSection
 	EndProjectSection
 EndProject
 EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "yamlupgrade", "src\tool\yamlupgrade.vcxproj", "{9115C6D1-520A-4540-B4FE-95F3C923FE2C}"
+	ProjectSection(ProjectDependencies) = postProject
+		{61D6A599-6BED-4154-A9FC-40553BD972E0} = {61D6A599-6BED-4154-A9FC-40553BD972E0}
+		{352B45B3-FE88-4431-9D89-48CF811446DB} = {352B45B3-FE88-4431-9D89-48CF811446DB}
+	EndProjectSection
+EndProject
 Global
 Global
 	GlobalSection(SolutionConfigurationPlatforms) = preSolution
 	GlobalSection(SolutionConfigurationPlatforms) = preSolution
 		Debug|Win32 = Debug|Win32
 		Debug|Win32 = Debug|Win32
@@ -171,6 +177,14 @@ Global
 		{CDBBB260-B245-44EC-80FB-3F9421885E40}.Release|Win32.Build.0 = Release|Win32
 		{CDBBB260-B245-44EC-80FB-3F9421885E40}.Release|Win32.Build.0 = Release|Win32
 		{CDBBB260-B245-44EC-80FB-3F9421885E40}.Release|x64.ActiveCfg = Release|x64
 		{CDBBB260-B245-44EC-80FB-3F9421885E40}.Release|x64.ActiveCfg = Release|x64
 		{CDBBB260-B245-44EC-80FB-3F9421885E40}.Release|x64.Build.0 = Release|x64
 		{CDBBB260-B245-44EC-80FB-3F9421885E40}.Release|x64.Build.0 = Release|x64
+		{9115C6D1-520A-4540-B4FE-95F3C923FE2C}.Debug|Win32.ActiveCfg = Debug|Win32
+		{9115C6D1-520A-4540-B4FE-95F3C923FE2C}.Debug|Win32.Build.0 = Debug|Win32
+		{9115C6D1-520A-4540-B4FE-95F3C923FE2C}.Debug|x64.ActiveCfg = Debug|x64
+		{9115C6D1-520A-4540-B4FE-95F3C923FE2C}.Debug|x64.Build.0 = Debug|x64
+		{9115C6D1-520A-4540-B4FE-95F3C923FE2C}.Release|Win32.ActiveCfg = Release|Win32
+		{9115C6D1-520A-4540-B4FE-95F3C923FE2C}.Release|Win32.Build.0 = Release|Win32
+		{9115C6D1-520A-4540-B4FE-95F3C923FE2C}.Release|x64.ActiveCfg = Release|x64
+		{9115C6D1-520A-4540-B4FE-95F3C923FE2C}.Release|x64.Build.0 = Release|x64
 	EndGlobalSection
 	EndGlobalSection
 	GlobalSection(SolutionProperties) = preSolution
 	GlobalSection(SolutionProperties) = preSolution
 		HideSolutionNode = FALSE
 		HideSolutionNode = FALSE
@@ -187,6 +201,7 @@ Global
 		{61D6A599-6BED-4154-A9FC-40553BD972E0} = {6ABA1767-6242-4CA0-BA22-A30972DC8918}
 		{61D6A599-6BED-4154-A9FC-40553BD972E0} = {6ABA1767-6242-4CA0-BA22-A30972DC8918}
 		{5A9059F2-4933-49A2-BEE6-CC67F66FA070} = {9F328FE9-129D-4C0C-820B-BE4AA5996652}
 		{5A9059F2-4933-49A2-BEE6-CC67F66FA070} = {9F328FE9-129D-4C0C-820B-BE4AA5996652}
 		{CDBBB260-B245-44EC-80FB-3F9421885E40} = {9F328FE9-129D-4C0C-820B-BE4AA5996652}
 		{CDBBB260-B245-44EC-80FB-3F9421885E40} = {9F328FE9-129D-4C0C-820B-BE4AA5996652}
+		{9115C6D1-520A-4540-B4FE-95F3C923FE2C} = {9F328FE9-129D-4C0C-820B-BE4AA5996652}
 	EndGlobalSection
 	EndGlobalSection
 	GlobalSection(ExtensibilityGlobals) = postSolution
 	GlobalSection(ExtensibilityGlobals) = postSolution
 		SolutionGuid = {026DA20F-820C-40AA-983E-0E231EA90AD5}
 		SolutionGuid = {026DA20F-820C-40AA-983E-0E231EA90AD5}

+ 164 - 116
src/map/achievement.cpp

@@ -50,8 +50,7 @@ const std::string AchievementDatabase::getDefaultLocation(){
 uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 	uint32 achievement_id;
 	uint32 achievement_id;
 
 
-	// TODO: doesnt match camel case
-	if( !this->asUInt32( node, "ID", achievement_id ) ){
+	if( !this->asUInt32( node, "Id", achievement_id ) ){
 		return 0;
 		return 0;
 	}
 	}
 
 
@@ -59,11 +58,7 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 	bool exists = achievement != nullptr;
 	bool exists = achievement != nullptr;
 
 
 	if( !exists ){
 	if( !exists ){
-		if( !this->nodeExists( node, "Group" ) ){
-			return 0;
-		}
-
-		if( !this->nodeExists( node, "Name" ) ){
+		if( !this->nodesExist( node, { "Name" } ) ){
 			return 0;
 			return 0;
 		}
 		}
 
 
@@ -78,14 +73,18 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 			return 0;
 			return 0;
 		}
 		}
 
 
+		std::string group_name_constant = "AG_" + group_name;
 		int64 constant;
 		int64 constant;
 
 
-		if( !script_get_constant( group_name.c_str(), &constant ) ){
-			this->invalidWarning( node, "achievement_read_db_sub: Invalid group %s for achievement %d, skipping.\n", group_name.c_str(), achievement_id );
+		if( !script_get_constant( group_name_constant.c_str(), &constant ) ){
+			this->invalidWarning( node, "Invalid Group %s for achievement %d, skipping.\n", group_name.c_str(), achievement_id );
 			return 0;
 			return 0;
 		}
 		}
 
 
 		achievement->group = (e_achievement_group)constant;
 		achievement->group = (e_achievement_group)constant;
+	} else {
+		if (!exists)
+			achievement->group = AG_NONE;
 	}
 	}
 
 
 	if( this->nodeExists( node, "Name" ) ){
 	if( this->nodeExists( node, "Name" ) ){
@@ -98,15 +97,10 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 		achievement->name = name;
 		achievement->name = name;
 	}
 	}
 
 
-	if( this->nodeExists( node, "Target" ) ){
-		const YAML::Node& targets = node["Target"];
+	if( this->nodeExists( node, "Targets" ) ){
+		const YAML::Node& targets = node["Targets"];
 
 
 		for( const YAML::Node& targetNode : targets ){
 		for( const YAML::Node& targetNode : targets ){
-			if( achievement->targets.size() >= MAX_ACHIEVEMENT_OBJECTIVES ){
-				this->invalidWarning( targetNode, "Node \"Target\" list exceeds the maximum of %d, skipping.\n", MAX_ACHIEVEMENT_OBJECTIVES );
-				return 0;
-			}
-
 			uint16 targetId;
 			uint16 targetId;
 
 
 			if( !this->asUInt16( targetNode, "Id", targetId ) ){
 			if( !this->asUInt16( targetNode, "Id", targetId ) ){
@@ -114,16 +108,16 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 			}
 			}
 
 
 			if( targetId >= MAX_ACHIEVEMENT_OBJECTIVES ){
 			if( targetId >= MAX_ACHIEVEMENT_OBJECTIVES ){
-				this->invalidWarning( targetNode["Id"], "Node \"Id\" is out of valid range [0,%d], skipping.\n", MAX_ACHIEVEMENT_OBJECTIVES );
-				return 0;
+				this->invalidWarning( targetNode["Id"], "Target Id is out of valid range [0,%d], skipping.\n", MAX_ACHIEVEMENT_OBJECTIVES );
+				continue;
 			}
 			}
 
 
 			std::shared_ptr<achievement_target> target = rathena::util::map_find( achievement->targets, targetId );
 			std::shared_ptr<achievement_target> target = rathena::util::map_find( achievement->targets, targetId );
 			bool targetExists = target != nullptr;
 			bool targetExists = target != nullptr;
 
 
 			if( !targetExists ){
 			if( !targetExists ){
-				if( !this->nodeExists( targetNode, "Count" ) && !this->nodeExists( targetNode, "MobID" ) ){
-					this->invalidWarning( targetNode, "Node \"Target\" has no data specified, skipping.\n" );
+				if( !this->nodeExists( targetNode, "Count" ) && !this->nodeExists( targetNode, "Mob" ) ){
+					this->invalidWarning( targetNode, "Target has no data specified, skipping.\n" );
 					return 0;
 					return 0;
 				}
 				}
 
 
@@ -137,31 +131,44 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 					return 0;
 					return 0;
 				}
 				}
 
 
+				if( count == 0 ){
+					if( targetExists ){
+						achievement->targets.erase( targetId );
+						continue;
+					}else{
+						this->invalidWarning( targetNode["Count"], "Target count has to be > 0, skipping.\n" );
+						return 0;
+					}
+				}
+
 				target->count = count;
 				target->count = count;
 			}else{
 			}else{
 				if( !targetExists ){
 				if( !targetExists ){
-					target->count = 0;
+					target->count = 1;
 				}
 				}
 			}
 			}
 
 
-			if( this->nodeExists( targetNode, "MobID" ) ){
+			if( this->nodeExists( targetNode, "Mob" ) ){
 				if( achievement->group != AG_BATTLE && achievement->group != AG_TAMING ){
 				if( achievement->group != AG_BATTLE && achievement->group != AG_TAMING ){
-					this->invalidWarning( targets, "Node \"MobID\" is only supported for targets in group AG_BATTLE or AG_TAMING, skipping.\n" );
-					return 0;
+					this->invalidWarning( targets, "Target Mob is only supported for targets in group AG_BATTLE or AG_TAMING, skipping.\n" );
+					continue;
 				}
 				}
 
 
-				uint32 mob_id;
+				std::string mob_name;
 
 
-				// TODO: not camel case
-				if( !this->asUInt32( targetNode, "MobID", mob_id ) ){
+				if( !this->asString( targetNode, "Mob", mob_name ) ){
 					return 0;
 					return 0;
 				}
 				}
 
 
-				if( mob_db.find( mob_id ) == nullptr ){
-					this->invalidWarning( targetNode["MobID"], "Unknown monster ID %d, skipping.\n", mob_id );
+				std::shared_ptr<s_mob_db> mob = mobdb_search_aegisname( mob_name.c_str() );
+
+				if (mob == nullptr) {
+					this->invalidWarning(targetNode["Mob"], "Target Mob %s does not exist, skipping.\n", mob_name.c_str());
 					return 0;
 					return 0;
 				}
 				}
 
 
+				uint32 mob_id = mob->vd.class_;
+
 				if( !this->mobexists( mob_id ) ){
 				if( !this->mobexists( mob_id ) ){
 					this->achievement_mobs.push_back( mob_id );
 					this->achievement_mobs.push_back( mob_id );
 				}
 				}
@@ -195,12 +202,13 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 
 
 		achievement->condition = parse_script( condition.c_str(), this->getCurrentFile().c_str(), node["Condition"].Mark().line + 1, SCRIPT_IGNORE_EXTERNAL_BRACKETS );
 		achievement->condition = parse_script( condition.c_str(), this->getCurrentFile().c_str(), node["Condition"].Mark().line + 1, SCRIPT_IGNORE_EXTERNAL_BRACKETS );
 	}else{
 	}else{
-		achievement->condition = nullptr;
+		if (!exists)
+			achievement->condition = nullptr;
 	}
 	}
 
 
 	if( this->nodeExists( node, "Map" ) ){
 	if( this->nodeExists( node, "Map" ) ){
-		if( achievement->group != AG_CHAT ){
-			this->invalidWarning( node, "Node \"Map\" can only be used with the group AG_CHATTING, skipping.\n" );
+		if( achievement->group != AG_CHATTING ){
+			this->invalidWarning( node, "Map can only be used with the group AG_CHATTING, skipping.\n" );
 			return 0;
 			return 0;
 		}
 		}
 
 
@@ -213,7 +221,7 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 		achievement->mapindex = map_mapname2mapid( mapname.c_str() );
 		achievement->mapindex = map_mapname2mapid( mapname.c_str() );
 
 
 		if( achievement->mapindex == -1 ){
 		if( achievement->mapindex == -1 ){
-			this->invalidWarning( node["Map"], "Unknown map name '%s'.\n", mapname.c_str() );
+			this->invalidWarning( node["Map"], "Map %s does not exist, skipping.\n", mapname.c_str() );
 			return 0;
 			return 0;
 		}
 		}
 	}else{
 	}else{
@@ -222,43 +230,51 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 		}
 		}
 	}
 	}
 
 
-	if( this->nodeExists( node, "Dependent" ) ){
-		for( const YAML::Node& subNode : node["Dependent"] ){
-			uint32 dependent_achievement_id;
+	if( this->nodeExists( node, "Dependents" ) ){
+		const YAML::Node &dependentNode = node["Dependents"];
 
 
-			if( !this->asUInt32( subNode, "Id", dependent_achievement_id ) ){
+		for( const auto it : dependentNode ){
+			uint32 dependent_achievement_id = it.first.as<uint32>();
+			bool active;
+
+			if (!this->asBool(dependentNode, std::to_string(dependent_achievement_id), active))
 				return 0;
 				return 0;
-			}
 
 
-			// TODO: import logic for clearing => continue
-			// TODO: change to set to prevent multiple entries with the same id?
-			achievement->dependent_ids.push_back( dependent_achievement_id );
+			if (active) {
+				if (std::find(achievement->dependent_ids.begin(), achievement->dependent_ids.end(), dependent_achievement_id) != achievement->dependent_ids.end()) {
+					this->invalidWarning(dependentNode, "Dependent achievement %d is already part of the list, skipping.\n", dependent_achievement_id);
+					continue;
+				}
+
+				if (achievement->dependent_ids.size() >= MAX_ACHIEVEMENT_DEPENDENTS) {
+					this->invalidWarning(dependentNode, "Maximum amount (%d) of dependent achievements reached, skipping.\n", MAX_ACHIEVEMENT_DEPENDENTS);
+					break;
+				}
+
+				achievement->dependent_ids.push_back(dependent_achievement_id);
+			} else
+				util::vector_erase_if_exists(achievement->dependent_ids, dependent_achievement_id);
 		}
 		}
 	}
 	}
 
 
-	// TODO: not plural
-	if( this->nodeExists( node, "Reward" ) ){
-		const YAML::Node& rewardNode = node["Reward"];
+	if( this->nodeExists( node, "Rewards" ) ){
+		const YAML::Node& rewardNode = node["Rewards"];
 
 
-		// TODO: not camel case
-		if( this->nodeExists( rewardNode, "ItemID" ) ){
-			t_itemid itemId;
+		if( this->nodeExists( rewardNode, "Item" ) ){
+			std::string item_name;
 
 
-			if( !this->asUInt32( rewardNode, "ItemID", itemId ) ){
+			if( !this->asString( rewardNode, "Item", item_name ) ){
 				return 0;
 				return 0;
 			}
 			}
 
 
-			if( !itemdb_exists( itemId ) ){
-				this->invalidWarning( rewardNode["ItemID"], "Unknown item with ID %u.\n", itemId );
+			struct item_data *item = itemdb_search_aegisname(item_name.c_str());
+
+			if (item == nullptr) {
+				this->invalidWarning(rewardNode["Item"], "Reward Item %s does not exist, skipping.\n", item_name.c_str());
 				return 0;
 				return 0;
 			}
 			}
 
 
-			achievement->rewards.nameid = itemId;
-
-			if( achievement->rewards.amount == 0 ){
-				// Default the amount to 1
-				achievement->rewards.amount = 1;
-			}
+			achievement->rewards.nameid = item->nameid;
 		}
 		}
 
 
 		if( this->nodeExists( rewardNode, "Amount" ) ){
 		if( this->nodeExists( rewardNode, "Amount" ) ){
@@ -269,6 +285,9 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 			}
 			}
 
 
 			achievement->rewards.amount = amount;
 			achievement->rewards.amount = amount;
+		} else {
+			if (!exists)
+				achievement->rewards.amount = 1;
 		}
 		}
 
 
 		if( this->nodeExists( rewardNode, "Script" ) ){
 		if( this->nodeExists( rewardNode, "Script" ) ){
@@ -285,18 +304,26 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 
 
 			achievement->rewards.script = parse_script( script.c_str(), this->getCurrentFile().c_str(), achievement_id, SCRIPT_IGNORE_EXTERNAL_BRACKETS );
 			achievement->rewards.script = parse_script( script.c_str(), this->getCurrentFile().c_str(), achievement_id, SCRIPT_IGNORE_EXTERNAL_BRACKETS );
 		}else{
 		}else{
-			achievement->rewards.script = nullptr;
+			if (!exists)
+				achievement->rewards.script = nullptr;
 		}
 		}
 
 
-		// TODO: not camel case
-		if( this->nodeExists( rewardNode, "TitleID" ) ){
+		if( this->nodeExists( rewardNode, "TitleId" ) ){
 			uint32 title;
 			uint32 title;
 
 
-			if( !this->asUInt32( rewardNode, "TitleID", title ) ){
+			if( !this->asUInt32( rewardNode, "TitleId", title ) ){
+				return 0;
+			}
+
+			if (title < TITLE_BASE || title > TITLE_MAX) {
+				this->invalidWarning(rewardNode["TitleId"], "Reward Title ID %u does not exist (%hu~%hu), skipping.\n", title, TITLE_BASE, TITLE_MAX);
 				return 0;
 				return 0;
 			}
 			}
 
 
 			achievement->rewards.title_id = title;
 			achievement->rewards.title_id = title;
+		} else {
+			if (!exists)
+				achievement->rewards.title_id = 0;
 		}
 		}
 	}
 	}
 
 
@@ -308,6 +335,9 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 		}
 		}
 
 
 		achievement->score = score;
 		achievement->score = score;
+	} else {
+		if (!exists)
+			achievement->score = 0;
 	}
 	}
 
 
 	if( !exists ){
 	if( !exists ){
@@ -317,6 +347,25 @@ uint64 AchievementDatabase::parseBodyNode(const YAML::Node &node){
 	return 1;
 	return 1;
 }
 }
 
 
+void AchievementDatabase::loadingFinished(){
+	for (const auto &achit : achievement_db) {
+		const std::shared_ptr<s_achievement_db> ach = achit.second;
+
+		for (auto dep = ach->dependent_ids.begin(); dep != ach->dependent_ids.end(); dep++) {
+			if (!achievement_db.exists(*dep)) {
+				ShowWarning("achievement_read_db: An invalid Dependent ID %d was given for Achievement %d. Removing from list.\n", *dep, ach->achievement_id);
+				dep = ach->dependent_ids.erase(dep);
+
+				if (dep == ach->dependent_ids.end()) {
+					break;
+				}
+			}
+		}
+
+		ach->dependent_ids.shrink_to_fit();
+	}
+}
+
 AchievementDatabase achievement_db;
 AchievementDatabase achievement_db;
 
 
 /**
 /**
@@ -507,8 +556,8 @@ bool achievement_check_dependent(struct map_session_data *sd, int achievement_id
 
 
 	// Check if the achievement has a dependent
 	// Check if the achievement has a dependent
 	// If so, then do a check on all dependents to see if they're complete
 	// If so, then do a check on all dependents to see if they're complete
-	for (int i = 0; i < adb->dependent_ids.size(); i++) {
-		if (!achievement_done(sd, adb->dependent_ids[i]))
+	for (const auto &depit : adb->dependent_ids) {
+		if (!achievement_done(sd, depit))
 			return false; // One of the dependent is not complete!
 			return false; // One of the dependent is not complete!
 	}
 	}
 
 
@@ -850,6 +899,19 @@ bool achievement_check_condition( struct script_code* condition, struct map_sess
 	return value != 0;
 	return value != 0;
 }
 }
 
 
+/**
+ * Check to see if an achievement's target count is complete
+ * @param ad: Achievement data
+ * @param current_count: Current target data
+ * @return True if all target values meet the requirements or false otherwise
+ */
+static bool achievement_target_complete(std::shared_ptr<s_achievement_db> ad, std::array<int, MAX_ACHIEVEMENT_OBJECTIVES> current_count) {
+	return std::find_if(ad->targets.begin(), ad->targets.end(),
+		[current_count](const std::pair<uint16, std::shared_ptr<achievement_target>> &target) -> bool {
+		return current_count[target.first] < target.second->count;
+	}) == ad->targets.end();
+}
+
 /**
 /**
  * Update achievement objectives.
  * Update achievement objectives.
  * @param sd: Player to update
  * @param sd: Player to update
@@ -892,9 +954,9 @@ static bool achievement_update_objectives(struct map_session_data *sd, std::shar
 	switch (group) {
 	switch (group) {
 		case AG_ADD_FRIEND:
 		case AG_ADD_FRIEND:
 		case AG_BABY:
 		case AG_BABY:
-		case AG_CHAT_COUNT:
-		case AG_CHAT_CREATE:
-		case AG_CHAT_DYING:
+		case AG_CHATTING_COUNT:
+		case AG_CHATTING_CREATE:
+		case AG_CHATTING_DYING:
 		case AG_GET_ITEM:
 		case AG_GET_ITEM:
 		case AG_GET_ZENY:
 		case AG_GET_ZENY:
 		case AG_GOAL_LEVEL:
 		case AG_GOAL_LEVEL:
@@ -902,8 +964,8 @@ static bool achievement_update_objectives(struct map_session_data *sd, std::shar
 		case AG_JOB_CHANGE:
 		case AG_JOB_CHANGE:
 		case AG_MARRY:
 		case AG_MARRY:
 		case AG_PARTY:
 		case AG_PARTY:
-		case AG_REFINE_FAIL:
-		case AG_REFINE_SUCCESS:
+		case AG_ENCHANT_FAIL:
+		case AG_ENCHANT_SUCCESS:
 			if (!ad->condition)
 			if (!ad->condition)
 				return false;
 				return false;
 
 
@@ -914,15 +976,9 @@ static bool achievement_update_objectives(struct map_session_data *sd, std::shar
 			complete = true;
 			complete = true;
 			break;
 			break;
 		case AG_SPEND_ZENY:
 		case AG_SPEND_ZENY:
-		//case AG_CHAT: // No information on trigger events
 			if (ad->targets.empty() || !ad->condition)
 			if (ad->targets.empty() || !ad->condition)
 				return false;
 				return false;
 
 
-			//if (group == AG_CHAT) {
-			//	if (ad->mapindex > -1 && sd->bl.m != ad->mapindex)
-			//		return false;
-			//}
-
 			for (const auto &it : ad->targets) {
 			for (const auto &it : ad->targets) {
 				if (current_count[it.first] < it.second->count)
 				if (current_count[it.first] < it.second->count)
 					current_count[it.first] += update_count[it.first];
 					current_count[it.first] += update_count[it.first];
@@ -933,11 +989,7 @@ static bool achievement_update_objectives(struct map_session_data *sd, std::shar
 
 
 			changed = true;
 			changed = true;
 
 
-			if (std::find_if(ad->targets.begin(), ad->targets.end(),
-				[current_count](const std::pair<uint16, std::shared_ptr<achievement_target>> &target) -> bool {
-					return current_count[target.first] < target.second->count;
-				}
-			) == ad->targets.end())
+			if (achievement_target_complete(ad, current_count))
 				complete = true;
 				complete = true;
 			break;
 			break;
 		case AG_BATTLE:
 		case AG_BATTLE:
@@ -955,13 +1007,38 @@ static bool achievement_update_objectives(struct map_session_data *sd, std::shar
 			if (!changed)
 			if (!changed)
 				return false;
 				return false;
 
 
-			if (std::find_if(ad->targets.begin(), ad->targets.end(),
-				[current_count](const std::pair<uint16, std::shared_ptr<achievement_target>> &target) -> bool {
-					return current_count[target.first] < target.second->count;
+			if (achievement_target_complete(ad, current_count))
+				complete = true;
+			break;
+		case AG_GOAL_ACHIEVE:
+			if (!achievement_check_condition(ad->condition, sd)) // Parameters weren't met
+				return false;
+
+			changed = true;
+			complete = true;
+			break;
+		/*
+		case AG_CHATTING:
+			if (ad->targets.empty())
+				return false;
+
+			if (ad->mapindex > -1 && sd->bl.m != ad->mapindex)
+				return false;
+
+			for (const auto &it : ad->targets) {
+				if (current_count[it.first] < it.second->count) {
+					current_count[it.first]++;
+					changed = true;
 				}
 				}
-			) == ad->targets.end())
+			}
+
+			if (!changed)
+				return false;
+
+			if (achievement_target_complete(ad, current_count))
 				complete = true;
 				complete = true;
 			break;
 			break;
+		*/
 	}
 	}
 
 
 	if( isNew ){
 	if( isNew ){
@@ -1022,15 +1099,8 @@ void achievement_update_objective(struct map_session_data *sd, enum e_achievemen
 		}
 		}
 		va_end(ap);
 		va_end(ap);
 
 
-		switch(group) {
-			case AG_CHAT: //! TODO: Not sure how this works officially
-				// These have no objective use.
-				break;
-			default:
-				for (auto &ach : achievement_db)
-					achievement_update_objectives(sd, ach.second, group, count);
-				break;
-		}
+		for (auto &ach : achievement_db)
+			achievement_update_objectives(sd, ach.second, group, count);
 
 
 		// Remove variables that might have been set
 		// Remove variables that might have been set
 		for (int i = 0; i < arg_count; i++){
 		for (int i = 0; i < arg_count; i++){
@@ -1069,34 +1139,11 @@ int achievement_update_objective_sub(block_list *bl, va_list ap)
 	return 1;
 	return 1;
 }
 }
 
 
-/**
- * Loads achievements from the achievement db.
- */
-void achievement_read_db(void)
-{	
-	achievement_db.load();
-
-	for (auto &achit : achievement_db) {
-		const auto ach = achit.second;
-
-		for (int i = 0; i < ach->dependent_ids.size(); i++) {
-			if (!achievement_db.exists(ach->dependent_ids[i])) {
-				ShowWarning("achievement_read_db: An invalid Dependent ID %d was given for Achievement %d. Removing from list.\n", ach->dependent_ids[i], ach->achievement_id);
-				ach->dependent_ids.erase(ach->dependent_ids.begin() + i);
-			}
-		}
-	}
-
-	achievement_level_db.load();
-}
-
 /**
 /**
  * Reloads the achievement database
  * Reloads the achievement database
  */
  */
 void achievement_db_reload(void)
 void achievement_db_reload(void)
 {
 {
-	if (!battle_config.feature_achievement)
-		return;
 	do_final_achievement();
 	do_final_achievement();
 	do_init_achievement();
 	do_init_achievement();
 }
 }
@@ -1108,7 +1155,8 @@ void do_init_achievement(void)
 {
 {
 	if (!battle_config.feature_achievement)
 	if (!battle_config.feature_achievement)
 		return;
 		return;
-	achievement_read_db();
+	achievement_db.load();
+	achievement_level_db.load();
 }
 }
 
 
 /**
 /**
@@ -1129,7 +1177,7 @@ s_achievement_db::s_achievement_db()
 	, targets()
 	, targets()
 	, dependent_ids()
 	, dependent_ids()
 	, condition(nullptr)
 	, condition(nullptr)
-	, mapindex(0)
+	, mapindex(-1)
 	, rewards()
 	, rewards()
 	, score(0)
 	, score(0)
 	, has_dependent(0)
 	, has_dependent(0)

+ 15 - 11
src/map/achievement.hpp

@@ -24,23 +24,21 @@ enum e_achievement_group {
 	AG_ADVENTURE,
 	AG_ADVENTURE,
 	AG_BABY,
 	AG_BABY,
 	AG_BATTLE,
 	AG_BATTLE,
-	AG_CHAT,
-	AG_CHAT_COUNT,
-	AG_CHAT_CREATE,
-	AG_CHAT_DYING,
+	AG_CHATTING,
+	AG_CHATTING_COUNT,
+	AG_CHATTING_CREATE,
+	AG_CHATTING_DYING,
 	AG_EAT,
 	AG_EAT,
 	AG_GET_ITEM,
 	AG_GET_ITEM,
 	AG_GET_ZENY,
 	AG_GET_ZENY,
 	AG_GOAL_ACHIEVE,
 	AG_GOAL_ACHIEVE,
 	AG_GOAL_LEVEL,
 	AG_GOAL_LEVEL,
 	AG_GOAL_STATUS,
 	AG_GOAL_STATUS,
-	AG_HEAR,
 	AG_JOB_CHANGE,
 	AG_JOB_CHANGE,
 	AG_MARRY,
 	AG_MARRY,
 	AG_PARTY,
 	AG_PARTY,
-	AG_REFINE_FAIL,
-	AG_REFINE_SUCCESS,
-	AG_SEE,
+	AG_ENCHANT_FAIL,
+	AG_ENCHANT_SUCCESS,
 	AG_SPEND_ZENY,
 	AG_SPEND_ZENY,
 	AG_TAMING,
 	AG_TAMING,
 	AG_MAX
 	AG_MAX
@@ -65,6 +63,12 @@ enum e_achievement_info {
 	ACHIEVEINFO_MAX,
 	ACHIEVEINFO_MAX,
 };
 };
 
 
+enum e_title_table : uint16 {
+	TITLE_NONE = 0,
+	TITLE_BASE = 1000,
+	TITLE_MAX = 1046,
+};
+
 struct achievement_target {
 struct achievement_target {
 	int mob;
 	int mob;
 	int count;
 	int count;
@@ -95,17 +99,17 @@ struct s_achievement_db {
 
 
 class AchievementDatabase : public TypesafeYamlDatabase<uint32, s_achievement_db>{
 class AchievementDatabase : public TypesafeYamlDatabase<uint32, s_achievement_db>{
 private:
 private:
-	// Avoids checking achievements on every mob killed
-	std::vector<uint32> achievement_mobs;
+	std::vector<uint32> achievement_mobs; // Avoids checking achievements on every mob killed
 
 
 public:
 public:
-	AchievementDatabase() : TypesafeYamlDatabase( "ACHIEVEMENT_DB", 1 ){
+	AchievementDatabase() : TypesafeYamlDatabase( "ACHIEVEMENT_DB", 2 ){
 
 
 	}
 	}
 
 
 	void clear();
 	void clear();
 	const std::string getDefaultLocation();
 	const std::string getDefaultLocation();
 	uint64 parseBodyNode( const YAML::Node& node );
 	uint64 parseBodyNode( const YAML::Node& node );
+	void loadingFinished();
 
 
 	// Additional
 	// Additional
 	bool mobexists(uint32 mob_id);
 	bool mobexists(uint32 mob_id);

+ 1 - 1
src/map/atcommand.cpp

@@ -2353,7 +2353,7 @@ ACMD_FUNC(refine)
 			clif_additem(sd, i, 1, 0);
 			clif_additem(sd, i, 1, 0);
 			pc_equipitem(sd, i, current_position);
 			pc_equipitem(sd, i, current_position);
 			clif_misceffect(&sd->bl, 3);
 			clif_misceffect(&sd->bl, 3);
-			achievement_update_objective(sd, AG_REFINE_SUCCESS, 2, sd->inventory_data[i]->wlv, sd->inventory.u.items_inventory[i].refine);
+			achievement_update_objective(sd, AG_ENCHANT_SUCCESS, 2, sd->inventory_data[i]->wlv, sd->inventory.u.items_inventory[i].refine);
 			count++;
 			count++;
 		}
 		}
 	}
 	}

+ 3 - 3
src/map/chat.cpp

@@ -109,9 +109,9 @@ int chat_createpcchat(struct map_session_data* sd, const char* title, const char
 		clif_dispchat(cd,0);
 		clif_dispchat(cd,0);
 
 
 		if (status_isdead(&sd->bl))
 		if (status_isdead(&sd->bl))
-			achievement_update_objective(sd, AG_CHAT_DYING, 1, 1);
+			achievement_update_objective(sd, AG_CHATTING_DYING, 1, 1);
 		else
 		else
-			achievement_update_objective(sd, AG_CHAT_CREATE, 1, 1);
+			achievement_update_objective(sd, AG_CHATTING_CREATE, 1, 1);
 	} else
 	} else
 		clif_createchat(sd,1);
 		clif_createchat(sd,1);
 
 
@@ -173,7 +173,7 @@ int chat_joinchat(struct map_session_data* sd, int chatid, const char* pass)
 	clif_dispchat(cd, 0); //Reported number of changes to the people around
 	clif_dispchat(cd, 0); //Reported number of changes to the people around
 
 
 	if (cd->owner->type == BL_PC)
 	if (cd->owner->type == BL_PC)
-		achievement_update_objective(map_id2sd(cd->owner->id), AG_CHAT_COUNT, 1, cd->users);
+		achievement_update_objective(map_id2sd(cd->owner->id), AG_CHATTING_COUNT, 1, cd->users);
 
 
 	chat_triggerevent(cd); //Event
 	chat_triggerevent(cd); //Event
 
 

+ 2 - 0
src/map/clif.cpp

@@ -10337,6 +10337,8 @@ static bool clif_process_message(struct map_session_data* sd, bool whisperFormat
 	if (battle_config.hom_idle_no_share && sd->hd && battle_config.idletime_hom_option&IDLE_CHAT)
 	if (battle_config.hom_idle_no_share && sd->hd && battle_config.idletime_hom_option&IDLE_CHAT)
 		sd->idletime_hom = last_tick;
 		sd->idletime_hom = last_tick;
 
 
+	//achievement_update_objective(sd, AG_CHATTING, 1, 1); // !TODO: Confirm how this achievement is triggered
+
 	return true;
 	return true;
 }
 }
 
 

+ 3 - 3
src/map/script.cpp

@@ -9257,7 +9257,7 @@ BUILDIN_FUNC(successrefitem) {
 		clif_additem(sd,i,1,0);
 		clif_additem(sd,i,1,0);
 		pc_equipitem(sd,i,ep);
 		pc_equipitem(sd,i,ep);
 		clif_misceffect(&sd->bl,3);
 		clif_misceffect(&sd->bl,3);
-		achievement_update_objective(sd, AG_REFINE_SUCCESS, 2, sd->inventory_data[i]->wlv, sd->inventory.u.items_inventory[i].refine);
+		achievement_update_objective(sd, AG_ENCHANT_SUCCESS, 2, sd->inventory_data[i]->wlv, sd->inventory.u.items_inventory[i].refine);
 		if (sd->inventory.u.items_inventory[i].refine == battle_config.blacksmith_fame_refine_threshold &&
 		if (sd->inventory.u.items_inventory[i].refine == battle_config.blacksmith_fame_refine_threshold &&
 			sd->inventory.u.items_inventory[i].card[0] == CARD0_FORGE &&
 			sd->inventory.u.items_inventory[i].card[0] == CARD0_FORGE &&
 			sd->status.char_id == (int)MakeDWord(sd->inventory.u.items_inventory[i].card[2],sd->inventory.u.items_inventory[i].card[3]))
 			sd->status.char_id == (int)MakeDWord(sd->inventory.u.items_inventory[i].card[2],sd->inventory.u.items_inventory[i].card[3]))
@@ -9307,7 +9307,7 @@ BUILDIN_FUNC(failedrefitem) {
 		clif_refine(sd->fd,1,i,sd->inventory.u.items_inventory[i].refine); //notify client of failure
 		clif_refine(sd->fd,1,i,sd->inventory.u.items_inventory[i].refine); //notify client of failure
 		pc_delitem(sd,i,1,0,2,LOG_TYPE_SCRIPT);
 		pc_delitem(sd,i,1,0,2,LOG_TYPE_SCRIPT);
 		clif_misceffect(&sd->bl,2); 	// display failure effect
 		clif_misceffect(&sd->bl,2); 	// display failure effect
-		achievement_update_objective(sd, AG_REFINE_FAIL, 1, 1);
+		achievement_update_objective(sd, AG_ENCHANT_FAIL, 1, 1);
 		script_pushint(st, 1);
 		script_pushint(st, 1);
 		return SCRIPT_CMD_SUCCESS;
 		return SCRIPT_CMD_SUCCESS;
 	}
 	}
@@ -9356,7 +9356,7 @@ BUILDIN_FUNC(downrefitem) {
 		clif_additem(sd,i,1,0);
 		clif_additem(sd,i,1,0);
 		pc_equipitem(sd,i,ep);
 		pc_equipitem(sd,i,ep);
 		clif_misceffect(&sd->bl,2);
 		clif_misceffect(&sd->bl,2);
-		achievement_update_objective(sd, AG_REFINE_FAIL, 1, sd->inventory.u.items_inventory[i].refine);
+		achievement_update_objective(sd, AG_ENCHANT_FAIL, 1, sd->inventory.u.items_inventory[i].refine);
 		script_pushint(st, sd->inventory.u.items_inventory[i].refine);
 		script_pushint(st, sd->inventory.u.items_inventory[i].refine);
 		return SCRIPT_CMD_SUCCESS;
 		return SCRIPT_CMD_SUCCESS;
 	}
 	}

+ 21 - 23
src/map/script_constants.hpp

@@ -5211,29 +5211,27 @@
 	export_constant(USW_ALL);
 	export_constant(USW_ALL);
 
 
 	/* achievement groups */
 	/* achievement groups */
-	export_constant2("AG_ADD_FRIEND", AG_ADD_FRIEND);
-	export_constant2("AG_ADVENTURE", AG_ADVENTURE);
-	export_constant2("AG_BABY", AG_BABY);
-	export_constant2("AG_BATTLE", AG_BATTLE);
-	export_constant2("AG_CHATTING", AG_CHAT);
-	export_constant2("AG_CHATTING_COUNT", AG_CHAT_COUNT);
-	export_constant2("AG_CHATTING_CREATE", AG_CHAT_CREATE);
-	export_constant2("AG_CHATTING_DYING", AG_CHAT_DYING);
-	export_constant2("AG_EAT", AG_EAT);
-	export_constant2("AG_GET_ITEM", AG_GET_ITEM);
-	export_constant2("AG_GET_ZENY", AG_GET_ZENY);
-	export_constant2("AG_GOAL_ACHIEVE", AG_GOAL_ACHIEVE);
-	export_constant2("AG_GOAL_LEVEL", AG_GOAL_LEVEL);
-	export_constant2("AG_GOAL_STATUS", AG_GOAL_STATUS);
-	export_constant2("AG_HEAR", AG_HEAR);
-	export_constant2("AG_JOB_CHANGE", AG_JOB_CHANGE);
-	export_constant2("AG_MARRY", AG_MARRY);
-	export_constant2("AG_PARTY", AG_PARTY);
-	export_constant2("AG_ENCHANT_FAIL", AG_REFINE_FAIL);
-	export_constant2("AG_ENCHANT_SUCCESS", AG_REFINE_SUCCESS);
-	export_constant2("AG_SEE", AG_SEE);
-	export_constant2("AG_SPEND_ZENY", AG_SPEND_ZENY);
-	export_constant2("AG_TAMING", AG_TAMING);
+	export_constant(AG_ADD_FRIEND);
+	export_constant(AG_ADVENTURE);
+	export_constant(AG_BABY);
+	export_constant(AG_BATTLE);
+	export_constant(AG_CHATTING);
+	export_constant(AG_CHATTING_COUNT);
+	export_constant(AG_CHATTING_CREATE);
+	export_constant(AG_CHATTING_DYING);
+	export_constant(AG_EAT);
+	export_constant(AG_GET_ITEM);
+	export_constant(AG_GET_ZENY);
+	export_constant(AG_GOAL_ACHIEVE);
+	export_constant(AG_GOAL_LEVEL);
+	export_constant(AG_GOAL_STATUS);
+	export_constant(AG_JOB_CHANGE);
+	export_constant(AG_MARRY);
+	export_constant(AG_PARTY);
+	export_constant(AG_ENCHANT_FAIL);
+	export_constant(AG_ENCHANT_SUCCESS);
+	export_constant(AG_SPEND_ZENY);
+	export_constant(AG_TAMING);
 
 
 	/* achievement info */
 	/* achievement info */
 	export_constant(ACHIEVEINFO_COUNT1);
 	export_constant(ACHIEVEINFO_COUNT1);

+ 2 - 2
src/map/skill.cpp

@@ -17687,7 +17687,7 @@ void skill_weaponrefine(struct map_session_data *sd, int idx)
 				clif_upgrademessage(sd, 0, item->nameid);
 				clif_upgrademessage(sd, 0, item->nameid);
 				clif_inventorylist(sd);
 				clif_inventorylist(sd);
 				clif_refine(sd->fd,0,idx,item->refine);
 				clif_refine(sd->fd,0,idx,item->refine);
-				achievement_update_objective(sd, AG_REFINE_SUCCESS, 2, ditem->wlv, item->refine);
+				achievement_update_objective(sd, AG_ENCHANT_SUCCESS, 2, ditem->wlv, item->refine);
 				if (ep)
 				if (ep)
 					pc_equipitem(sd,idx,ep);
 					pc_equipitem(sd,idx,ep);
 				clif_misceffect(&sd->bl,3);
 				clif_misceffect(&sd->bl,3);
@@ -17713,7 +17713,7 @@ void skill_weaponrefine(struct map_session_data *sd, int idx)
 					pc_unequipitem(sd,idx,3);
 					pc_unequipitem(sd,idx,3);
 				clif_upgrademessage(sd, 1, item->nameid);
 				clif_upgrademessage(sd, 1, item->nameid);
 				clif_refine(sd->fd,1,idx,item->refine);
 				clif_refine(sd->fd,1,idx,item->refine);
-				achievement_update_objective(sd, AG_REFINE_FAIL, 1, 1);
+				achievement_update_objective(sd, AG_ENCHANT_FAIL, 1, 1);
 				pc_delitem(sd,idx,1,0,2, LOG_TYPE_OTHER);
 				pc_delitem(sd,idx,1,0,2, LOG_TYPE_OTHER);
 				clif_misceffect(&sd->bl,2);
 				clif_misceffect(&sd->bl,2);
 				clif_emotion(&sd->bl, ET_HUK);
 				clif_emotion(&sd->bl, ET_HUK);

+ 17 - 10
src/tool/Makefile.in

@@ -18,12 +18,14 @@ CSV2YAML_OBJ = obj_all/csv2yaml.o
 
 
 YAML2SQL_OBJ = obj_all/yaml2sql.o
 YAML2SQL_OBJ = obj_all/yaml2sql.o
 
 
+YAMLUPGRADE_OBJ = obj_all/yamlupgrade.o
+
 @SET_MAKE@
 @SET_MAKE@
 
 
 #####################################################################
 #####################################################################
-.PHONY : all mapcache csv2yaml yaml2sql clean help
+.PHONY : all mapcache csv2yaml yaml2sql yamlupgrade clean help
 
 
-all: mapcache csv2yaml yaml2sql
+all: mapcache csv2yaml yaml2sql yamlupgrade
 
 
 mapcache: obj_all $(MAPCACHE_OBJ) $(COMMON_DIR_OBJ)
 mapcache: obj_all $(MAPCACHE_OBJ) $(COMMON_DIR_OBJ)
 	@echo "	LD	$@"
 	@echo "	LD	$@"
@@ -37,18 +39,23 @@ yaml2sql: obj_all $(YAML2SQL_OBJ) $(COMMON_DIR_OBJ) $(YAML_CPP_AR)
 	@echo "	LD	$@"
 	@echo "	LD	$@"
 	@@CXX@ @LDFLAGS@ -o ../../yaml2sql@EXEEXT@ $(YAML2SQL_OBJ) $(COMMON_DIR_OBJ) $(YAML_CPP_AR) @LIBS@
 	@@CXX@ @LDFLAGS@ -o ../../yaml2sql@EXEEXT@ $(YAML2SQL_OBJ) $(COMMON_DIR_OBJ) $(YAML_CPP_AR) @LIBS@
 
 
+yamlupgrade: obj_all $(YAMLUPGRADE_OBJ) $(COMMON_DIR_OBJ) $(YAML_CPP_AR)
+	@echo "	LD	$@"
+	@@CXX@ @LDFLAGS@ -o ../../yamlupgrade@EXEEXT@ $(YAMLUPGRADE_OBJ) $(COMMON_DIR_OBJ) ../common/obj/database.o $(YAML_CPP_AR) @LIBS@
+
 clean:
 clean:
 	@echo "	CLEAN	tool"
 	@echo "	CLEAN	tool"
-	@rm -rf obj_all/*.o ../../mapcache@EXEEXT@ ../../csv2yaml@EXEEXT@ ../../yaml2sql@EXEEXT@
+	@rm -rf obj_all/*.o ../../mapcache@EXEEXT@ ../../csv2yaml@EXEEXT@ ../../yaml2sql@EXEEXT@ ../../yamlupgrade@EXEEXT@
 
 
 help:
 help:
-	@echo "possible targets are 'mapcache' 'csv2yaml' 'yaml2sql' 'all' 'clean' 'help'"
-	@echo "'mapcache'  - mapcache generator"
-	@echo "'csv2yaml'  - converts TXT databases to YAML"
-	@echo "'yaml2sql'  - converts YAML databases to SQL"
-	@echo "'all'       - builds all above targets"
-	@echo "'clean'     - cleans builds and objects"
-	@echo "'help'      - outputs this message"
+	@echo "possible targets are 'mapcache' 'csv2yaml' 'yaml2sql' 'yamlupgrade' 'all' 'clean' 'help'"
+	@echo "'mapcache'     - mapcache generator"
+	@echo "'csv2yaml'     - converts TXT databases to YAML"
+	@echo "'yaml2sql'     - converts YAML databases to SQL"
+	@echo "'yamlupgrade'  - upgrades YAML databases to latest version"
+	@echo "'all'          - builds all above targets"
+	@echo "'clean'        - cleans builds and objects"
+	@echo "'help'         - outputs this message"
 
 
 #####################################################################
 #####################################################################
 
 

+ 25 - 971
src/tool/csv2yaml.cpp

@@ -1,195 +1,9 @@
 // Copyright (c) rAthena Dev Teams - Licensed under GNU GPL
 // Copyright (c) rAthena Dev Teams - Licensed under GNU GPL
 // For more information, see LICENCE in the main folder
 // For more information, see LICENCE in the main folder
 
 
-#include <fstream>
-#include <functional>
-#include <iostream>
-#include <locale>
-#include <map>
-#include <unordered_map>
-#include <vector>
-
-#ifdef WIN32
-	#include <conio.h>
-#else
-	#include <termios.h>
-	#include <unistd.h>
-	#include <stdio.h>
-#endif
+#include "csv2yaml.hpp"
 
 
 #include <math.h>
 #include <math.h>
-#include <yaml-cpp/yaml.h>
-
-#include "../common/cbasetypes.hpp"
-#include "../common/core.hpp"
-#include "../common/malloc.hpp"
-#include "../common/mmo.hpp"
-#include "../common/nullpo.hpp"
-#include "../common/showmsg.hpp"
-#include "../common/strlib.hpp"
-#include "../common/utilities.hpp"
-#include "../common/utils.hpp"
-#ifdef WIN32
-#include "../common/winapi.hpp"
-#endif
-
-// Only for constants - do not use functions of it or linking will fail
-#include "../map/achievement.hpp"
-#include "../map/battle.hpp"
-#include "../map/battleground.hpp"
-#include "../map/channel.hpp"
-#include "../map/chat.hpp"
-#include "../map/date.hpp"
-#include "../map/instance.hpp"
-#include "../map/mercenary.hpp"
-#include "../map/mob.hpp"
-#include "../map/npc.hpp"
-#include "../map/pc.hpp"
-#include "../map/pet.hpp"
-#include "../map/quest.hpp"
-#include "../map/script.hpp"
-#include "../map/skill.hpp"
-#include "../map/storage.hpp"
-
-using namespace rathena;
-
-#define MAX_MAP_PER_INSTANCE 255
-
-#ifndef WIN32
-int getch( void ){
-    struct termios oldattr, newattr;
-    int ch;
-    tcgetattr( STDIN_FILENO, &oldattr );
-    newattr = oldattr;
-    newattr.c_lflag &= ~( ICANON | ECHO );
-    tcsetattr( STDIN_FILENO, TCSANOW, &newattr );
-    ch = getchar();
-    tcsetattr( STDIN_FILENO, TCSANOW, &oldattr );
-    return ch;
-}
-#endif
-
-// Required constant and structure definitions
-#define MAX_GUILD_SKILL_REQUIRE 5
-#define MAX_SKILL_ITEM_REQUIRE	10
-#define MAX_SKILL_STATUS_REQUIRE 3
-#define MAX_SKILL_EQUIP_REQUIRE 10
-#define MAX_QUEST_DROPS 3
-
-struct s_skill_unit_csv : s_skill_db {
-	std::string target_str;
-	int unit_flag_csv;
-};
-
-std::unordered_map<uint16, s_skill_require> skill_require;
-std::unordered_map<uint16, s_skill_db> skill_cast;
-std::unordered_map<uint16, s_skill_db> skill_castnodex;
-std::unordered_map<uint16, s_skill_unit_csv> skill_unit;
-std::unordered_map<uint16, s_skill_copyable> skill_copyable;
-std::unordered_map<uint16, s_skill_db> skill_nearnpc;
-
-static unsigned int level_penalty[3][CLASS_MAX][MAX_LEVEL * 2 + 1];
-
-struct s_item_flag_csv2yaml {
-	bool buyingstore, dead_branch, group, guid, broadcast, bindOnEquip, delay_consume;
-	e_item_drop_effect dropEffect;
-};
-
-struct s_item_delay_csv2yaml {
-	uint32 delay;
-	std::string sc;
-};
-
-struct s_item_stack_csv2yaml {
-	uint16 amount;
-	bool inventory, cart, storage, guild_storage;
-};
-
-struct s_item_nouse_csv2yaml {
-	uint16 override;
-	bool sitting;
-};
-
-struct s_item_trade_csv2yaml {
-	uint16 override;
-	bool drop, trade, trade_partner, sell, cart, storage, guild_storage, mail, auction;
-};
-
-std::unordered_map<t_itemid, t_itemid> item_avail;
-std::unordered_map<t_itemid, bool> item_buyingstore;
-std::unordered_map<t_itemid, s_item_flag_csv2yaml> item_flag;
-std::unordered_map<t_itemid, s_item_delay_csv2yaml> item_delay;
-std::unordered_map<t_itemid, s_item_stack_csv2yaml> item_stack;
-std::unordered_map<t_itemid, s_item_nouse_csv2yaml> item_nouse;
-std::unordered_map<t_itemid, s_item_trade_csv2yaml> item_trade;
-
-struct s_random_opt_group_csv : s_random_opt_group {
-	std::vector<uint16> rate;
-};
-
-std::unordered_map<uint16, std::string> rand_opt_db;
-std::unordered_map<uint16, s_random_opt_group_csv> rand_opt_group;
-
-static std::map<std::string, int> um_mapid2jobname {
-	{ "Novice", JOB_NOVICE }, // Novice and Super Novice share the same value
-	{ "SuperNovice", JOB_NOVICE },
-	{ "Swordman", JOB_SWORDMAN },
-	{ "Mage", JOB_MAGE },
-	{ "Archer", JOB_ARCHER },
-	{ "Acolyte", JOB_ACOLYTE },
-	{ "Merchant", JOB_MERCHANT },
-	{ "Thief", JOB_THIEF },
-	{ "Knight", JOB_KNIGHT },
-	{ "Priest", JOB_PRIEST },
-	{ "Wizard", JOB_WIZARD },
-	{ "Blacksmith", JOB_BLACKSMITH },
-	{ "Hunter", JOB_HUNTER },
-	{ "Assassin", JOB_ASSASSIN },
-	{ "Crusader", JOB_CRUSADER },
-	{ "Monk", JOB_MONK },
-	{ "Sage", JOB_SAGE },
-	{ "Rogue", JOB_ROGUE },
-	{ "Alchemist", JOB_ALCHEMIST },
-	{ "BardDancer", JOB_BARD }, // Bard and Dancer share the same value
-	{ "BardDancer", JOB_DANCER },
-	{ "Gunslinger", JOB_GUNSLINGER },
-	{ "Ninja", JOB_NINJA },
-	{ "Taekwon", 21 },
-	{ "StarGladiator", 22 },
-	{ "SoulLinker", 23 },
-//	{ "Gangsi", 26 },
-//	{ "DeathKnight", 27 },
-//	{ "DarkCollector", 28 },
-#ifdef RENEWAL
-	{ "KagerouOboro", 29 }, // Kagerou and Oboro share the same value
-	{ "Rebellion", 30 },
-	{ "Summoner", 31 },
-#endif
-};
-
-static std::unordered_map<std::string, equip_pos> um_equipnames {
-	{ "Head_Low", EQP_HEAD_LOW },
-	{ "Head_Mid", EQP_HEAD_MID },
-	{ "Head_Top", EQP_HEAD_TOP },
-	{ "Right_Hand", EQP_HAND_R },
-	{ "Left_Hand", EQP_HAND_L },
-	{ "Armor", EQP_ARMOR },
-	{ "Shoes", EQP_SHOES },
-	{ "Garment", EQP_GARMENT },
-	{ "Right_Accessory", EQP_ACC_R },
-	{ "Left_Accessory", EQP_ACC_L },
-	{ "Costume_Head_Top", EQP_COSTUME_HEAD_TOP },
-	{ "Costume_Head_Mid", EQP_COSTUME_HEAD_MID },
-	{ "Costume_Head_Low", EQP_COSTUME_HEAD_LOW },
-	{ "Costume_Garment", EQP_COSTUME_GARMENT },
-	{ "Ammo", EQP_AMMO },
-	{ "Shadow_Armor", EQP_SHADOW_ARMOR },
-	{ "Shadow_Weapon", EQP_SHADOW_WEAPON },
-	{ "Shadow_Shield", EQP_SHADOW_SHIELD },
-	{ "Shadow_Shoes", EQP_SHADOW_SHOES },
-	{ "Shadow_Right_Accessory", EQP_SHADOW_ACC_R },
-	{ "Shadow_Left_Accessory", EQP_SHADOW_ACC_L },
-};
 
 
 struct s_mob_drop_csv : s_mob_drop {
 struct s_mob_drop_csv : s_mob_drop {
 	std::string group_string;
 	std::string group_string;
@@ -199,54 +13,9 @@ struct s_mob_drop_csv : s_mob_drop {
 std::unordered_map<uint16, std::vector<uint32>> mob_race2;
 std::unordered_map<uint16, std::vector<uint32>> mob_race2;
 std::map<uint32, std::vector<s_mob_drop_csv>> mob_drop;
 std::map<uint32, std::vector<s_mob_drop_csv>> mob_drop;
 
 
-// Forward declaration of conversion functions
-static bool guild_read_guildskill_tree_db( char* split[], int columns, int current );
-static bool pet_read_db( const char* file );
-static bool skill_parse_row_magicmushroomdb(char *split[], int column, int current);
-static bool skill_parse_row_abradb(char* split[], int columns, int current);
-static bool skill_parse_row_spellbookdb(char* split[], int columns, int current);
-static bool mob_readdb_mobavail(char *str[], int columns, int current);
-static bool skill_parse_row_requiredb(char* split[], int columns, int current);
-static bool skill_parse_row_castdb(char* split[], int columns, int current);
-static bool skill_parse_row_castnodexdb(char* split[], int columns, int current);
-static bool skill_parse_row_unitdb(char* split[], int columns, int current);
-static bool skill_parse_row_copyabledb(char* split[], int columns, int current);
-static bool skill_parse_row_nonearnpcrangedb(char* split[], int columns, int current);
-static bool skill_parse_row_skilldb(char* split[], int columns, int current);
-static bool quest_read_db(char *split[], int columns, int current);
-static bool instance_readdb_sub(char* str[], int columns, int current);
-static bool itemdb_read_itemavail(char *str[], int columns, int current);
-static bool itemdb_read_buyingstore(char* fields[], int columns, int current);
-static bool itemdb_read_flag(char* fields[], int columns, int current);
-static bool itemdb_read_itemdelay(char* str[], int columns, int current);
-static bool itemdb_read_stack(char* fields[], int columns, int current);
-static bool itemdb_read_nouse(char* fields[], int columns, int current);
-static bool itemdb_read_itemtrade(char* fields[], int columns, int current);
-static bool itemdb_read_db(const char *file);
-static bool itemdb_read_randomopt(const char* file);
-static bool itemdb_read_randomopt_group(char *str[], int columns, int current);
-static bool itemdb_randomopt_group_yaml(void);
-static bool pc_readdb_levelpenalty(char* fields[], int columns, int current);
-static bool pc_levelpenalty_yaml();
-static bool mob_readdb_race2(char *fields[], int columns, int current);
-static bool mob_readdb_drop(char *str[], int columns, int current);
-static bool mob_readdb_sub(char *fields[], int columns, int current);
-
-// Constants for conversion
-std::unordered_map<t_itemid, std::string> aegis_itemnames;
-std::unordered_map<t_itemid, t_itemid> aegis_itemviewid;
-std::unordered_map<uint16, std::string> aegis_mobnames;
-std::unordered_map<uint16, std::string> aegis_skillnames;
-std::unordered_map<const char*, int64> constants;
-
-// Forward declaration of constant loading functions
-static bool parse_item_constants_txt( const char* path );
-static bool parse_mob_constants_txt( char* split[], int columns, int current );
-static bool parse_skill_constants_txt( char* split[], int columns, int current );
-static void init_random_option_constants();
-
-bool fileExists( const std::string& path );
-bool askConfirmation( const char* fmt, ... );
+static bool mob_readdb_race2(char* fields[], int columns, int current);
+static bool mob_readdb_drop(char* str[], int columns, int current);
+static bool mob_readdb_sub(char* fields[], int columns, int current);
 
 
 // Skill database data to memory
 // Skill database data to memory
 static void skill_txt_data(const std::string& modePath, const std::string& fixedPath) {
 static void skill_txt_data(const std::string& modePath, const std::string& fixedPath) {
@@ -308,88 +77,6 @@ static void mob_txt_data(const std::string &modePath, const std::string &fixedPa
 		sv_readdb(modePath.c_str(), "mob_drop.txt", ',', 3, 5, -1, mob_readdb_drop, false);
 		sv_readdb(modePath.c_str(), "mob_drop.txt", ',', 3, 5, -1, mob_readdb_drop, false);
 }
 }
 
 
-YAML::Emitter body;
-
-// Implement the function instead of including the original version by linking
-void script_set_constant_( const char* name, int64 value, const char* constant_name, bool isparameter, bool deprecated ){
-	constants[name] = value;
-}
-
-const char* constant_lookup( int32 value, const char* prefix ){
-	if (prefix == nullptr)
-		return nullptr;
-
-	for( auto const& pair : constants ){
-		// Same prefix group and same value
-		if( strncasecmp( pair.first, prefix, strlen( prefix ) ) == 0 && pair.second == value ){
-			return pair.first;
-		}
-	}
-
-	return nullptr;
-}
-
-int64 constant_lookup_int(const char* constant) {
-	if (constant == nullptr)
-		return -100;
-
-	for (auto const &pair : constants) {
-		if (strlen(pair.first) == strlen(constant) && strncasecmp(pair.first, constant, strlen(constant)) == 0) {
-			return pair.second;
-		}
-	}
-
-	return -100;
-}
-
-void copyFileIfExists( std::ofstream& file,const std::string& name, bool newLine ){
-	std::string path = "doc/yaml/db/" + name + ".yml";
-
-	if( fileExists( path ) ){
-		std::ifstream source( path, std::ios::binary );
-
-		std::istreambuf_iterator<char> begin_source( source );
-		std::istreambuf_iterator<char> end_source;
-		std::ostreambuf_iterator<char> begin_dest( file );
-		copy( begin_source, end_source, begin_dest );
-
-		source.close();
-
-		if( newLine ){
-			file << "\n";
-		}
-	}
-}
-
-void prepareHeader(std::ofstream &file, const std::string& type, uint32 version, const std::string& name) {
-	copyFileIfExists( file, "license", false );
-	copyFileIfExists( file, name, true );
-
-	YAML::Emitter header(file);
-
-	header << YAML::BeginMap;
-	header << YAML::Key << "Header";
-	header << YAML::BeginMap;
-	header << YAML::Key << "Type" << YAML::Value << type;
-	header << YAML::Key << "Version" << YAML::Value << version;
-	header << YAML::EndMap;
-	header << YAML::EndMap;
-
-	file << "\n";
-	file << "\n";
-}
-
-void prepareBody(void) {
-	body << YAML::BeginMap;
-	body << YAML::Key << "Body";
-	body << YAML::BeginSeq;
-}
-
-void finalizeBody(void) {
-	body << YAML::EndSeq;
-	body << YAML::EndMap;
-}
-
 template<typename Func>
 template<typename Func>
 bool process( const std::string& type, uint32 version, const std::vector<std::string>& paths, const std::string& name, Func lambda, const std::string& rename = "" ){
 bool process( const std::string& type, uint32 version, const std::vector<std::string>& paths, const std::string& name, Func lambda, const std::string& rename = "" ){
 	for( const std::string& path : paths ){
 	for( const std::string& path : paths ){
@@ -408,6 +95,8 @@ bool process( const std::string& type, uint32 version, const std::vector<std::st
 				}
 				}
 			}
 			}
 
 
+			ShowNotice("Conversion process has begun.\n");
+
 			std::ofstream out;
 			std::ofstream out;
 
 
 			body.~Emitter();
 			body.~Emitter();
@@ -526,7 +215,7 @@ int do_init( int argc, char** argv ){
 		return 0;
 		return 0;
 	}
 	}
 
 
-	if (!process("QUEST_DB", 2, root_paths, "quest_db", [](const std::string &path, const std::string &name_ext) -> bool {
+	if (!process("QUEST_DB", 1, root_paths, "quest_db", [](const std::string &path, const std::string &name_ext) -> bool {
 		return sv_readdb(path.c_str(), name_ext.c_str(), ',', 3 + MAX_QUEST_OBJECTIVES * 2 + MAX_QUEST_DROPS * 3, 100, -1, &quest_read_db, false);
 		return sv_readdb(path.c_str(), name_ext.c_str(), ',', 3 + MAX_QUEST_OBJECTIVES * 2 + MAX_QUEST_DROPS * 3, 100, -1, &quest_read_db, false);
 	})) {
 	})) {
 		return 0;
 		return 0;
@@ -588,7 +277,7 @@ int do_init( int argc, char** argv ){
 	})) {
 	})) {
 		return 0;
 		return 0;
 	}
 	}
-	
+
 	mob_txt_data(path_db_import, path_db_import);
 	mob_txt_data(path_db_import, path_db_import);
 	if (!process("MOB_DB", 1, { path_db_import }, "mob_db", [](const std::string &path, const std::string &name_ext) -> bool {
 	if (!process("MOB_DB", 1, { path_db_import }, "mob_db", [](const std::string &path, const std::string &name_ext) -> bool {
 		return sv_readdb(path.c_str(), name_ext.c_str(), ',', 31 + 2 * MAX_MVP_DROP + 2 * MAX_MOB_DROP, 31 + 2 * MAX_MVP_DROP + 2 * MAX_MOB_DROP, -1, &mob_readdb_sub, false);
 		return sv_readdb(path.c_str(), name_ext.c_str(), ',', 31 + 2 * MAX_MVP_DROP + 2 * MAX_MOB_DROP, 31 + 2 * MAX_MVP_DROP + 2 * MAX_MOB_DROP, -1, &mob_readdb_sub, false);
@@ -604,397 +293,6 @@ int do_init( int argc, char** argv ){
 void do_final(void){
 void do_final(void){
 }
 }
 
 
-bool fileExists( const std::string& path ){
-	std::ifstream in;
-
-	in.open( path );
-
-	if( in.is_open() ){
-		in.close();
-
-		return true;
-	}else{
-		return false;
-	}
-}
-
-bool askConfirmation( const char* fmt, ... ){
-	va_list ap;
-
-	va_start( ap, fmt );
-
-	_vShowMessage( MSG_NONE, fmt, ap );
-
-	va_end( ap );
-
-	char c = getch();
-
-	if( c == 'Y' || c == 'y' ){
-		return true;
-	}else{
-		return false;
-	}
-}
-
-// Constant loading functions
-static bool parse_item_constants_txt( const char* path ){
-	uint32 lines = 0, count = 0;
-	char line[1024];
-
-	FILE* fp;
-
-	fp = fopen(path, "r");
-	if (fp == NULL) {
-		ShowWarning("parse_item_constants_txt: File not found \"%s\", skipping.\n", path);
-		return false;
-	}
-
-	// process rows one by one
-	while (fgets(line, sizeof(line), fp))
-	{
-		char *str[32], *p;
-		int i;
-		lines++;
-		if (line[0] == '/' && line[1] == '/')
-			continue;
-		memset(str, 0, sizeof(str));
-
-		p = strstr(line, "//");
-
-		if (p != nullptr) {
-			*p = '\0';
-		}
-
-		p = line;
-		while (ISSPACE(*p))
-			++p;
-		if (*p == '\0')
-			continue;// empty line
-		for (i = 0; i < 19; ++i)
-		{
-			str[i] = p;
-			p = strchr(p, ',');
-			if (p == NULL)
-				break;// comma not found
-			*p = '\0';
-			++p;
-		}
-
-		if (p == NULL)
-		{
-			ShowError("parse_item_constants_txt: Insufficient columns in line %d of \"%s\" (item with id %d), skipping.\n", lines, path, atoi(str[0]));
-			continue;
-		}
-
-		// Script
-		if (*p != '{')
-		{
-			ShowError("parse_item_constants_txt: Invalid format (Script column) in line %d of \"%s\" (item with id %d), skipping.\n", lines, path, atoi(str[0]));
-			continue;
-		}
-		str[19] = p + 1;
-		p = strstr(p + 1, "},");
-		if (p == NULL)
-		{
-			ShowError("parse_item_constants_txt: Invalid format (Script column) in line %d of \"%s\" (item with id %d), skipping.\n", lines, path, atoi(str[0]));
-			continue;
-		}
-		*p = '\0';
-		p += 2;
-
-		// OnEquip_Script
-		if (*p != '{')
-		{
-			ShowError("parse_item_constants_txt: Invalid format (OnEquip_Script column) in line %d of \"%s\" (item with id %d), skipping.\n", lines, path, atoi(str[0]));
-			continue;
-		}
-		str[20] = p + 1;
-		p = strstr(p + 1, "},");
-		if (p == NULL)
-		{
-			ShowError("parse_item_constants_txt: Invalid format (OnEquip_Script column) in line %d of \"%s\" (item with id %d), skipping.\n", lines, path, atoi(str[0]));
-			continue;
-		}
-		*p = '\0';
-		p += 2;
-
-		// OnUnequip_Script (last column)
-		if (*p != '{')
-		{
-			ShowError("parse_item_constants_txt: Invalid format (OnUnequip_Script column) in line %d of \"%s\" (item with id %d), skipping.\n", lines, path, atoi(str[0]));
-			continue;
-		}
-		str[21] = p;
-		p = &str[21][strlen(str[21]) - 2];
-
-		if (*p != '}') {
-			/* lets count to ensure it's not something silly e.g. a extra space at line ending */
-			int lcurly = 0, rcurly = 0;
-
-			for (size_t v = 0; v < strlen(str[21]); v++) {
-				if (str[21][v] == '{')
-					lcurly++;
-				else if (str[21][v] == '}') {
-					rcurly++;
-					p = &str[21][v];
-				}
-			}
-
-			if (lcurly != rcurly) {
-				ShowError("parse_item_constants_txt: Mismatching curly braces in line %d of \"%s\" (item with id %d), skipping.\n", lines, path, atoi(str[0]));
-				continue;
-			}
-		}
-		str[21] = str[21] + 1;  //skip the first left curly
-		*p = '\0';              //null the last right curly
-
-		uint16 item_id = atoi( str[0] );
-		char* name = trim( str[1] );
-
-		aegis_itemnames[item_id] = std::string(name);
-
-		if (atoi(str[14]) & (EQP_HELM | EQP_COSTUME_HELM) && util::umap_find(aegis_itemviewid, (t_itemid)atoi(str[18])) == nullptr)
-			aegis_itemviewid[atoi(str[18])] = item_id;
-
-		count++;
-	}
-
-	fclose(fp);
-
-	ShowStatus("Done reading '" CL_WHITE "%u" CL_RESET "' entries in '" CL_WHITE "%s" CL_RESET "'.\n", count, path);
-
-	return true;
-}
-
-const std::string ItemDatabase::getDefaultLocation(){
-	return std::string( db_path ) + "/item_db.yml";
-}
-
-uint64 ItemDatabase::parseBodyNode(const YAML::Node& node) {
-	t_itemid nameid;
-
-	if (!this->asUInt32(node, "Id", nameid))
-		return 0;
-
-	if (this->nodeExists(node, "AegisName")) {
-		std::string name;
-
-		if (!this->asString(node, "AegisName", name))
-			return 0;
-
-		aegis_itemnames[nameid] = name;
-	}
-
-	if (this->nodeExists(node, "View")) {
-		uint32 look;
-
-		if (!this->asUInt32(node, "View", look))
-			return 0;
-
-		if( look > 0 ){
-			if (this->nodeExists(node, "Locations")) {
-				const YAML::Node& locationNode = node["Locations"];
-
-				static std::vector<std::string> locations = {
-					"Head_Low",
-					"Head_Mid",
-					"Head_Top",
-					"Costume_Head_Low",
-					"Costume_Head_Mid",
-					"Costume_Head_Top"
-				};
-
-				for( std::string& location : locations ){
-					if (this->nodeExists(locationNode, location)) {
-						bool active;
-
-						if (!this->asBool(locationNode, location, active))
-							return 0;
-
-						aegis_itemviewid[look] = nameid;
-						break;
-					}
-				}
-			}
-		}
-	}
-
-	return 1;
-}
-
-void ItemDatabase::loadingFinished(){
-}
-
-ItemDatabase item_db;
-
-static bool parse_mob_constants_txt( char* split[], int columns, int current ){
-	uint16 mob_id = atoi( split[0] );
-	char* name = trim( split[1] );
-
-	aegis_mobnames[mob_id] = std::string( name );
-
-	return true;
-}
-
-const std::string MobDatabase::getDefaultLocation(){
-	return std::string( db_path ) + "/mob_db.yml";
-}
-
-uint64 MobDatabase::parseBodyNode(const YAML::Node& node) {
-	uint16 mob_id;
-
-	if (!this->asUInt16(node, "Id", mob_id))
-		return 0;
-
-	if (this->nodeExists(node, "AegisName")) {
-		std::string name;
-
-		if (!this->asString(node, "AegisName", name))
-			return 0;
-
-		aegis_mobnames[mob_id] = name;
-	}
-
-	return 1;
-}
-
-void MobDatabase::loadingFinished() {};
-
-MobDatabase mob_db;
-
-static bool parse_skill_constants_txt( char* split[], int columns, int current ){
-	uint16 skill_id = atoi( split[0] );
-	char* name = trim( split[16] );
-
-	aegis_skillnames[skill_id] = std::string( name );
-
-	return true;
-}
-
-const std::string SkillDatabase::getDefaultLocation() {
-	return std::string(db_path) + "/skill_db.yml";
-}
-
-uint64 SkillDatabase::parseBodyNode(const YAML::Node &node) {
-	t_itemid nameid;
-
-	if (!this->asUInt32(node, "Id", nameid))
-		return 0;
-
-	if (this->nodeExists(node, "Name")) {
-		std::string name;
-
-		if (!this->asString(node, "Name", name))
-			return 0;
-
-		aegis_skillnames[nameid] = name;
-	}
-
-	return 1;
-}
-
-void SkillDatabase::clear() {
-	TypesafeCachedYamlDatabase::clear();
-}
-
-SkillDatabase skill_db;
-
-/**
- * Split the string with ':' as separator and put each value for a skilllv
- * @param str: String to split
- * @param val: Array of MAX_SKILL_LEVEL to put value into
- * @return 0:error, x:number of value assign (should be MAX_SKILL_LEVEL)
- */
-int skill_split_atoi(char *str, int *val) {
-	int i;
-
-	for (i = 0; i < MAX_SKILL_LEVEL; i++) {
-		if (!str)
-			break;
-		val[i] = atoi(str);
-		str = strchr(str, ':');
-		if (str)
-			*str++ = 0;
-	}
-
-	if (i == 0) // No data found.
-		return 0;
-
-	if (i == 1) // Single value, have the whole range have the same value.
-		return 1;
-
-	return i;
-}
-
-/**
- * Split string to int by constant value (const.txt) or atoi()
- * @param *str: String input
- * @param *val: Temporary storage
- * @param *delim: Delimiter (for multiple value support)
- * @param min_value: Minimum value. If the splitted value is less or equal than this, will be skipped
- * @param max: Maximum number that can be allocated
- * @return count: Number of success
- */
-uint8 skill_split_atoi2(char *str, int64 *val, const char *delim, int min_value, uint16 max) {
-	uint8 i = 0;
-	char *p = strtok(str, delim);
-
-	while (p != NULL) {
-		int64 n = min_value;
-
-		trim(p);
-
-		if (ISDIGIT(p[0])) // If using numeric
-			n = atoi(p);
-		else {
-			n = constant_lookup_int(p);
-			p = strtok(NULL, delim);
-		}
-
-		if (n > min_value) {
-			val[i] = n;
-			i++;
-			if (i >= max)
-				break;
-		}
-		p = strtok(NULL, delim);
-	}
-	return i;
-}
-
-/**
- * Split string to int
- * @param str: String input
- * @param val1: Temporary storage to first value
- * @param val2: Temporary storage to second value
- */
-static void itemdb_re_split_atoi(char* str, int* val1, int* val2) {
-	int i, val[2];
-
-	for (i = 0; i < 2; i++) {
-		if (!str)
-			break;
-		val[i] = atoi(str);
-		str = strchr(str, ':');
-		if (str)
-			*str++ = 0;
-	}
-	if (i == 0) {
-		*val1 = *val2 = 0;
-		return; // no data found
-	}
-	if (i == 1) { // Single Value
-		*val1 = val[0];
-		*val2 = 0;
-		return;
-	}
-
-	// We assume we have 2 values.
-	*val1 = val[0];
-	*val2 = val[1];
-	return;
-}
-
 // Implementation of the conversion functions
 // Implementation of the conversion functions
 
 
 // Copied and adjusted from guild.cpp
 // Copied and adjusted from guild.cpp
@@ -1354,7 +652,7 @@ static bool mob_readdb_mobavail(char* str[], int columns, int current) {
 		if (atoi(str[11]) != 0)
 		if (atoi(str[11]) != 0)
 			body << YAML::Key << "ClothColor" << YAML::Value << atoi(str[11]);
 			body << YAML::Key << "ClothColor" << YAML::Value << atoi(str[11]);
 
 
-		if (atoi(str[5]) != 0) {
+		if (strtoul(str[5], nullptr, 10) != 0) {
 			t_itemid weapon_item_id = strtoul( str[5], nullptr, 10 );
 			t_itemid weapon_item_id = strtoul( str[5], nullptr, 10 );
 			std::string *weapon_item_name = util::umap_find(aegis_itemnames, weapon_item_id);
 			std::string *weapon_item_name = util::umap_find(aegis_itemnames, weapon_item_id);
 
 
@@ -1366,7 +664,7 @@ static bool mob_readdb_mobavail(char* str[], int columns, int current) {
 			body << YAML::Key << "Weapon" << YAML::Value << *weapon_item_name;
 			body << YAML::Key << "Weapon" << YAML::Value << *weapon_item_name;
 		}
 		}
 
 
-		if (atoi(str[6]) != 0) {
+		if (strtoul(str[6], nullptr, 10) != 0) {
 			t_itemid shield_item_id = strtoul( str[6], nullptr, 10 );
 			t_itemid shield_item_id = strtoul( str[6], nullptr, 10 );
 			std::string *shield_item_name = util::umap_find(aegis_itemnames, shield_item_id);
 			std::string *shield_item_name = util::umap_find(aegis_itemnames, shield_item_id);
 
 
@@ -1378,54 +676,54 @@ static bool mob_readdb_mobavail(char* str[], int columns, int current) {
 			body << YAML::Key << "Shield" << YAML::Value << *shield_item_name;
 			body << YAML::Key << "Shield" << YAML::Value << *shield_item_name;
 		}
 		}
 
 
-		if (atoi(str[7]) != 0) {
-			t_itemid *headtop_item_id = util::umap_find(aegis_itemviewid, (t_itemid)atoi(str[7]));
+		if (strtoul(str[7], nullptr, 10) != 0) {
+			t_itemid *headtop_item_id = util::umap_find(aegis_itemviewid, (uint32)strtoul(str[7], nullptr, 10));
 
 
 			if (headtop_item_id == nullptr) {
 			if (headtop_item_id == nullptr) {
-				ShowError("Item ID for view ID %hu (head top) is not known.\n", atoi(str[7]));
+				ShowError("Item ID for view ID %u (head top) is not known.\n", strtoul(str[7], nullptr, 10));
 				return false;
 				return false;
 			}
 			}
 
 
-			std::string *headtop_item_name = util::umap_find(aegis_itemnames, (t_itemid)*headtop_item_id);
+			std::string *headtop_item_name = util::umap_find(aegis_itemnames, *headtop_item_id);
 
 
 			if (headtop_item_name == nullptr) {
 			if (headtop_item_name == nullptr) {
-				ShowError("Item name for item ID %hu (head top) is not known.\n", *headtop_item_id);
+				ShowError("Item name for item ID %u (head top) is not known.\n", *headtop_item_id);
 				return false;
 				return false;
 			}
 			}
 
 
 			body << YAML::Key << "HeadTop" << YAML::Value << *headtop_item_name;
 			body << YAML::Key << "HeadTop" << YAML::Value << *headtop_item_name;
 		}
 		}
 
 
-		if (atoi(str[8]) != 0) {
-			t_itemid *headmid_item_id = util::umap_find(aegis_itemviewid, (t_itemid)atoi(str[8]));
+		if (strtoul(str[8], nullptr, 10) != 0) {
+			t_itemid *headmid_item_id = util::umap_find(aegis_itemviewid, (uint32)strtoul(str[8], nullptr, 10));
 
 
 			if (headmid_item_id == nullptr) {
 			if (headmid_item_id == nullptr) {
-				ShowError("Item ID for view ID %hu (head mid) is not known.\n", atoi(str[8]));
+				ShowError("Item ID for view ID %u (head mid) is not known.\n", strtoul(str[8], nullptr, 10));
 				return false;
 				return false;
 			}
 			}
 
 
-			std::string *headmid_item_name = util::umap_find(aegis_itemnames, (t_itemid)*headmid_item_id);
+			std::string *headmid_item_name = util::umap_find(aegis_itemnames, *headmid_item_id);
 
 
 			if (headmid_item_name == nullptr) {
 			if (headmid_item_name == nullptr) {
-				ShowError("Item name for item ID %hu (head mid) is not known.\n", *headmid_item_id);
+				ShowError("Item name for item ID %u (head mid) is not known.\n", *headmid_item_id);
 				return false;
 				return false;
 			}
 			}
 
 
 			body << YAML::Key << "HeadMid" << YAML::Value << *headmid_item_name;
 			body << YAML::Key << "HeadMid" << YAML::Value << *headmid_item_name;
 		}
 		}
 
 
-		if (atoi(str[9]) != 0) {
-			t_itemid *headlow_item_id = util::umap_find(aegis_itemviewid, (t_itemid)atoi(str[9]));
+		if (strtoul(str[9], nullptr, 10) != 0) {
+			t_itemid *headlow_item_id = util::umap_find(aegis_itemviewid, (uint32)strtoul(str[9], nullptr, 10));
 
 
 			if (headlow_item_id == nullptr) {
 			if (headlow_item_id == nullptr) {
-				ShowError("Item ID for view ID %hu (head low) is not known.\n", atoi(str[9]));
+				ShowError("Item ID for view ID %u (head low) is not known.\n", strtoul(str[9], nullptr, 10));
 				return false;
 				return false;
 			}
 			}
 
 
-			std::string *headlow_item_name = util::umap_find(aegis_itemnames, (t_itemid)*headlow_item_id);
+			std::string *headlow_item_name = util::umap_find(aegis_itemnames, *headlow_item_id);
 
 
 			if (headlow_item_name == nullptr) {
 			if (headlow_item_name == nullptr) {
-				ShowError("Item name for item ID %hu (head low) is not known.\n", *headlow_item_id);
+				ShowError("Item name for item ID %u (head low) is not known.\n", *headlow_item_id);
 				return false;
 				return false;
 			}
 			}
 
 
@@ -1771,29 +1069,6 @@ static bool skill_parse_row_nonearnpcrangedb(char* split[], int column, int curr
 	return true;
 	return true;
 }
 }
 
 
-static bool isMultiLevel(int arr[]) {
-	int count = 0;
-
-	for (int i = 0; i < MAX_SKILL_LEVEL; i++) {
-		if (arr[i] != 0)
-			count++;
-	}
-
-	return (count == 0 || count == 1 ? false : true);
-}
-
-std::string name2Upper(std::string name) {
-	std::transform(name.begin(), name.end(), name.begin(), ::tolower);
-	name[0] = toupper(name[0]);
-
-	for (size_t i = 0; i < name.size(); i++) {
-		if (name[i - 1] == '_' || (name[i - 2] == '1' && name[i - 1] == 'h') || (name[i - 2] == '2' && name[i - 1] == 'h'))
-			name[i] = toupper(name[i]);
-	}
-
-	return name;
-}
-
 // Copied and adjusted from skill.cpp
 // Copied and adjusted from skill.cpp
 static bool skill_parse_row_skilldb(char* split[], int columns, int current) {
 static bool skill_parse_row_skilldb(char* split[], int columns, int current) {
 	int arr[MAX_SKILL_LEVEL], arr_size, skill_id = atoi(split[0]);
 	int arr[MAX_SKILL_LEVEL], arr_size, skill_id = atoi(split[0]);
@@ -3689,227 +2964,6 @@ bool pc_levelpenalty_yaml(){
 	return true;
 	return true;
 }
 }
 
 
-// Initialize Random Option constants
-void init_random_option_constants() {
-	#define export_constant2(a, b) script_set_constant_(a, b, a, false, false)
-
-	export_constant2("RDMOPT_VAR_MAXHPAMOUNT", 1);
-	export_constant2("RDMOPT_VAR_MAXSPAMOUNT", 2);
-	export_constant2("RDMOPT_VAR_STRAMOUNT", 3);
-	export_constant2("RDMOPT_VAR_AGIAMOUNT", 4);
-	export_constant2("RDMOPT_VAR_VITAMOUNT", 5);
-	export_constant2("RDMOPT_VAR_INTAMOUNT", 6);
-	export_constant2("RDMOPT_VAR_DEXAMOUNT", 7);
-	export_constant2("RDMOPT_VAR_LUKAMOUNT", 8);
-	export_constant2("RDMOPT_VAR_MAXHPPERCENT", 9);
-	export_constant2("RDMOPT_VAR_MAXSPPERCENT", 10);
-	export_constant2("RDMOPT_VAR_HPACCELERATION", 11);
-	export_constant2("RDMOPT_VAR_SPACCELERATION", 12);
-	export_constant2("RDMOPT_VAR_ATKPERCENT", 13);
-	export_constant2("RDMOPT_VAR_MAGICATKPERCENT", 14);
-	export_constant2("RDMOPT_VAR_PLUSASPD", 15);
-	export_constant2("RDMOPT_VAR_PLUSASPDPERCENT", 16);
-	export_constant2("RDMOPT_VAR_ATTPOWER", 17);
-	export_constant2("RDMOPT_VAR_HITSUCCESSVALUE", 18);
-	export_constant2("RDMOPT_VAR_ATTMPOWER", 19);
-	export_constant2("RDMOPT_VAR_ITEMDEFPOWER", 20);
-	export_constant2("RDMOPT_VAR_MDEFPOWER", 21);
-	export_constant2("RDMOPT_VAR_AVOIDSUCCESSVALUE", 22);
-	export_constant2("RDMOPT_VAR_PLUSAVOIDSUCCESSVALUE", 23);
-	export_constant2("RDMOPT_VAR_CRITICALSUCCESSVALUE", 24);
-	export_constant2("RDMOPT_ATTR_TOLERACE_NOTHING", 25);
-	export_constant2("RDMOPT_ATTR_TOLERACE_WATER", 26);
-	export_constant2("RDMOPT_ATTR_TOLERACE_GROUND", 27);
-	export_constant2("RDMOPT_ATTR_TOLERACE_FIRE", 28);
-	export_constant2("RDMOPT_ATTR_TOLERACE_WIND", 29);
-	export_constant2("RDMOPT_ATTR_TOLERACE_POISON", 30);
-	export_constant2("RDMOPT_ATTR_TOLERACE_SAINT", 31);
-	export_constant2("RDMOPT_ATTR_TOLERACE_DARKNESS", 32);
-	export_constant2("RDMOPT_ATTR_TOLERACE_TELEKINESIS", 33);
-	export_constant2("RDMOPT_ATTR_TOLERACE_UNDEAD", 34);
-	export_constant2("RDMOPT_ATTR_TOLERACE_ALLBUTNOTHING", 35);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_NOTHING_USER", 36);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_NOTHING_TARGET", 37);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_WATER_USER", 38);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_WATER_TARGET", 39);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_GROUND_USER", 40);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_GROUND_TARGET", 41);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_FIRE_USER", 42);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_FIRE_TARGET", 43);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_WIND_USER", 44);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_WIND_TARGET", 45);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_POISON_USER", 46);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_POISON_TARGET", 47);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_SAINT_USER", 48);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_SAINT_TARGET", 49);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_DARKNESS_USER", 50);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_DARKNESS_TARGET", 51);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_TELEKINESIS_USER", 52);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_TELEKINESIS_TARGET", 53);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_UNDEAD_USER", 54);
-	export_constant2("RDMOPT_DAMAGE_PROPERTY_UNDEAD_TARGET", 55);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_NOTHING_USER", 56);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_NOTHING_TARGET", 57);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_WATER_USER", 58);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_WATER_TARGET", 59);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_GROUND_USER", 60);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_GROUND_TARGET", 61);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_FIRE_USER", 62);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_FIRE_TARGET", 63);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_WIND_USER", 64);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_WIND_TARGET", 65);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_POISON_USER", 66);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_POISON_TARGET", 67);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_SAINT_USER", 68);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_SAINT_TARGET", 69);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_DARKNESS_USER", 70);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_DARKNESS_TARGET", 71);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_TELEKINESIS_USER", 72);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_TELEKINESIS_TARGET", 73);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_UNDEAD_USER", 74);
-	export_constant2("RDMOPT_MDAMAGE_PROPERTY_UNDEAD_TARGET", 75);
-	export_constant2("RDMOPT_BODY_ATTR_NOTHING", 76);
-	export_constant2("RDMOPT_BODY_ATTR_WATER", 77);
-	export_constant2("RDMOPT_BODY_ATTR_GROUND", 78);
-	export_constant2("RDMOPT_BODY_ATTR_FIRE", 79);
-	export_constant2("RDMOPT_BODY_ATTR_WIND", 80);
-	export_constant2("RDMOPT_BODY_ATTR_POISON", 81);
-	export_constant2("RDMOPT_BODY_ATTR_SAINT", 82);
-	export_constant2("RDMOPT_BODY_ATTR_DARKNESS", 83);
-	export_constant2("RDMOPT_BODY_ATTR_TELEKINESIS", 84);
-	export_constant2("RDMOPT_BODY_ATTR_UNDEAD", 85);
-	export_constant2("RDMOPT_RACE_TOLERACE_NOTHING", 87);
-	export_constant2("RDMOPT_RACE_TOLERACE_UNDEAD", 88);
-	export_constant2("RDMOPT_RACE_TOLERACE_ANIMAL", 89);
-	export_constant2("RDMOPT_RACE_TOLERACE_PLANT", 90);
-	export_constant2("RDMOPT_RACE_TOLERACE_INSECT", 91);
-	export_constant2("RDMOPT_RACE_TOLERACE_FISHS", 92);
-	export_constant2("RDMOPT_RACE_TOLERACE_DEVIL", 93);
-	export_constant2("RDMOPT_RACE_TOLERACE_HUMAN", 94);
-	export_constant2("RDMOPT_RACE_TOLERACE_ANGEL", 95);
-	export_constant2("RDMOPT_RACE_TOLERACE_DRAGON", 96);
-	export_constant2("RDMOPT_RACE_DAMAGE_NOTHING", 97);
-	export_constant2("RDMOPT_RACE_DAMAGE_UNDEAD", 98);
-	export_constant2("RDMOPT_RACE_DAMAGE_ANIMAL", 99);
-	export_constant2("RDMOPT_RACE_DAMAGE_PLANT", 100);
-	export_constant2("RDMOPT_RACE_DAMAGE_INSECT", 101);
-	export_constant2("RDMOPT_RACE_DAMAGE_FISHS", 102);
-	export_constant2("RDMOPT_RACE_DAMAGE_DEVIL", 103);
-	export_constant2("RDMOPT_RACE_DAMAGE_HUMAN", 104);
-	export_constant2("RDMOPT_RACE_DAMAGE_ANGEL", 105);
-	export_constant2("RDMOPT_RACE_DAMAGE_DRAGON", 106);
-	export_constant2("RDMOPT_RACE_MDAMAGE_NOTHING", 107);
-	export_constant2("RDMOPT_RACE_MDAMAGE_UNDEAD", 108);
-	export_constant2("RDMOPT_RACE_MDAMAGE_ANIMAL", 109);
-	export_constant2("RDMOPT_RACE_MDAMAGE_PLANT", 110);
-	export_constant2("RDMOPT_RACE_MDAMAGE_INSECT", 111);
-	export_constant2("RDMOPT_RACE_MDAMAGE_FISHS", 112);
-	export_constant2("RDMOPT_RACE_MDAMAGE_DEVIL", 113);
-	export_constant2("RDMOPT_RACE_MDAMAGE_HUMAN", 114);
-	export_constant2("RDMOPT_RACE_MDAMAGE_ANGEL", 115);
-	export_constant2("RDMOPT_RACE_MDAMAGE_DRAGON", 116);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_NOTHING", 117);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_UNDEAD", 118);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_ANIMAL", 119);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_PLANT", 120);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_INSECT", 121);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_FISHS", 122);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_DEVIL", 123);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_HUMAN", 124);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_ANGEL", 125);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_DRAGON", 126);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_NOTHING", 127);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_UNDEAD", 128);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_ANIMAL", 129);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_PLANT", 130);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_INSECT", 131);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_FISHS", 132);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_DEVIL", 133);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_HUMAN", 134);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_ANGEL", 135);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_DRAGON", 136);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_NOTHING", 137);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_UNDEAD", 138);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_ANIMAL", 139);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_PLANT", 140);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_INSECT", 141);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_FISHS", 142);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_DEVIL", 143);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_HUMAN", 144);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_ANGEL", 145);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_DRAGON", 146);
-	export_constant2("RDMOPT_CLASS_DAMAGE_NORMAL_TARGET", 147);
-	export_constant2("RDMOPT_CLASS_DAMAGE_BOSS_TARGET", 148);
-	export_constant2("RDMOPT_CLASS_DAMAGE_NORMAL_USER", 149);
-	export_constant2("RDMOPT_CLASS_DAMAGE_BOSS_USER", 150);
-	export_constant2("RDMOPT_CLASS_MDAMAGE_NORMAL", 151);
-	export_constant2("RDMOPT_CLASS_MDAMAGE_BOSS", 152);
-	export_constant2("RDMOPT_CLASS_IGNORE_DEF_PERCENT_NORMAL", 153);
-	export_constant2("RDMOPT_CLASS_IGNORE_DEF_PERCENT_BOSS", 154);
-	export_constant2("RDMOPT_CLASS_IGNORE_MDEF_PERCENT_NORMAL", 155);
-	export_constant2("RDMOPT_CLASS_IGNORE_MDEF_PERCENT_BOSS", 156);
-	export_constant2("RDMOPT_DAMAGE_SIZE_SMALL_TARGET", 157);
-	export_constant2("RDMOPT_DAMAGE_SIZE_MIDIUM_TARGET", 158);
-	export_constant2("RDMOPT_DAMAGE_SIZE_LARGE_TARGET", 159);
-	export_constant2("RDMOPT_DAMAGE_SIZE_SMALL_USER", 160);
-	export_constant2("RDMOPT_DAMAGE_SIZE_MIDIUM_USER", 161);
-	export_constant2("RDMOPT_DAMAGE_SIZE_LARGE_USER", 162);
-	export_constant2("RDMOPT_DAMAGE_SIZE_PERFECT", 163);
-	export_constant2("RDMOPT_DAMAGE_CRI_TARGET", 164);
-	export_constant2("RDMOPT_DAMAGE_CRI_USER", 165);
-	export_constant2("RDMOPT_RANGE_ATTACK_DAMAGE_TARGET", 166);
-	export_constant2("RDMOPT_RANGE_ATTACK_DAMAGE_USER", 167);
-	export_constant2("RDMOPT_HEAL_VALUE", 168);
-	export_constant2("RDMOPT_HEAL_MODIFY_PERCENT", 169);
-	export_constant2("RDMOPT_DEC_SPELL_CAST_TIME", 170);
-	export_constant2("RDMOPT_DEC_SPELL_DELAY_TIME", 171);
-	export_constant2("RDMOPT_DEC_SP_CONSUMPTION", 172);
-	export_constant2("RDMOPT_WEAPON_ATTR_NOTHING", 175);
-	export_constant2("RDMOPT_WEAPON_ATTR_WATER", 176);
-	export_constant2("RDMOPT_WEAPON_ATTR_GROUND", 177);
-	export_constant2("RDMOPT_WEAPON_ATTR_FIRE", 178);
-	export_constant2("RDMOPT_WEAPON_ATTR_WIND", 179);
-	export_constant2("RDMOPT_WEAPON_ATTR_POISON", 180);
-	export_constant2("RDMOPT_WEAPON_ATTR_SAINT", 181);
-	export_constant2("RDMOPT_WEAPON_ATTR_DARKNESS", 182);
-	export_constant2("RDMOPT_WEAPON_ATTR_TELEKINESIS", 183);
-	export_constant2("RDMOPT_WEAPON_ATTR_UNDEAD", 184);
-	export_constant2("RDMOPT_WEAPON_INDESTRUCTIBLE", 185);
-	export_constant2("RDMOPT_BODY_INDESTRUCTIBLE", 186);
-	export_constant2("RDMOPT_MDAMAGE_SIZE_SMALL_TARGET", 187);
-	export_constant2("RDMOPT_MDAMAGE_SIZE_MIDIUM_TARGET", 188);
-	export_constant2("RDMOPT_MDAMAGE_SIZE_LARGE_TARGET", 189);
-	export_constant2("RDMOPT_MDAMAGE_SIZE_SMALL_USER", 190);
-	export_constant2("RDMOPT_MDAMAGE_SIZE_MIDIUM_USER", 191);
-	export_constant2("RDMOPT_MDAMAGE_SIZE_LARGE_USER", 192);
-	export_constant2("RDMOPT_ATTR_TOLERACE_ALL", 193);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_NOTHING", 194);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_UNDEAD", 195);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_ANIMAL", 196);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_PLANT", 197);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_INSECT", 198);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_FISHS", 199);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_DEVIL", 200);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_HUMAN", 201);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_ANGEL", 202);
-	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_DRAGON", 203);
-	export_constant2("RDMOPT_RACE_TOLERACE_PLAYER_HUMAN", 206);
-	export_constant2("RDMOPT_RACE_TOLERACE_PLAYER_DORAM", 207);
-	export_constant2("RDMOPT_RACE_DAMAGE_PLAYER_HUMAN", 208);
-	export_constant2("RDMOPT_RACE_DAMAGE_PLAYER_DORAM", 209);
-	export_constant2("RDMOPT_RACE_MDAMAGE_PLAYER_HUMAN", 210);
-	export_constant2("RDMOPT_RACE_MDAMAGE_PLAYER_DORAM", 211);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_PLAYER_HUMAN", 212);
-	export_constant2("RDMOPT_RACE_CRI_PERCENT_PLAYER_DORAM", 213);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_PLAYER_HUMAN", 214);
-	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_PLAYER_DORAM", 215);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_PLAYER_HUMAN", 216);
-	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_PLAYER_DORAM", 217);
-	export_constant2("RDMOPT_MELEE_ATTACK_DAMAGE_TARGET", 219);
-	export_constant2("RDMOPT_MELEE_ATTACK_DAMAGE_USER", 220);
-
-	#undef export_constant2
-}
 
 
 // mob_db.yml function
 // mob_db.yml function
 //--------------------
 //--------------------

+ 384 - 0
src/tool/csv2yaml.hpp

@@ -0,0 +1,384 @@
+// Copyright (c) rAthena Dev Teams - Licensed under GNU GPL
+// For more information, see LICENCE in the main folder
+
+#ifndef CSV2YAML_HPP
+#define CSV2YAML_HPP
+
+#include "yaml.hpp"
+
+// Required constant and structure definitions
+#define MAX_GUILD_SKILL_REQUIRE 5
+#define MAX_SKILL_ITEM_REQUIRE	10
+#define MAX_SKILL_STATUS_REQUIRE 3
+#define MAX_SKILL_EQUIP_REQUIRE 10
+#define MAX_QUEST_DROPS 3
+#define MAX_MAP_PER_INSTANCE 255
+
+// Database to memory maps
+struct s_skill_unit_csv : s_skill_db {
+	std::string target_str;
+	int unit_flag_csv;
+};
+
+std::unordered_map<uint16, s_skill_require> skill_require;
+std::unordered_map<uint16, s_skill_db> skill_cast;
+std::unordered_map<uint16, s_skill_db> skill_castnodex;
+std::unordered_map<uint16, s_skill_unit_csv> skill_unit;
+std::unordered_map<uint16, s_skill_copyable> skill_copyable;
+std::unordered_map<uint16, s_skill_db> skill_nearnpc;
+
+static unsigned int level_penalty[3][CLASS_MAX][MAX_LEVEL * 2 + 1];
+
+struct s_item_flag_csv2yaml {
+	bool buyingstore, dead_branch, group, guid, broadcast, bindOnEquip, delay_consume;
+	e_item_drop_effect dropEffect;
+};
+
+struct s_item_delay_csv2yaml {
+	uint32 delay;
+	std::string sc;
+};
+
+struct s_item_stack_csv2yaml {
+	uint16 amount;
+	bool inventory, cart, storage, guild_storage;
+};
+
+struct s_item_nouse_csv2yaml {
+	uint16 override;
+	bool sitting;
+};
+
+struct s_item_trade_csv2yaml {
+	uint16 override;
+	bool drop, trade, trade_partner, sell, cart, storage, guild_storage, mail, auction;
+};
+
+std::unordered_map<t_itemid, t_itemid> item_avail;
+std::unordered_map<t_itemid, bool> item_buyingstore;
+std::unordered_map<t_itemid, s_item_flag_csv2yaml> item_flag;
+std::unordered_map<t_itemid, s_item_delay_csv2yaml> item_delay;
+std::unordered_map<t_itemid, s_item_stack_csv2yaml> item_stack;
+std::unordered_map<t_itemid, s_item_nouse_csv2yaml> item_nouse;
+std::unordered_map<t_itemid, s_item_trade_csv2yaml> item_trade;
+
+struct s_random_opt_group_csv : s_random_opt_group {
+	std::vector<uint16> rate;
+};
+
+std::unordered_map<uint16, std::string> rand_opt_db;
+std::unordered_map<uint16, s_random_opt_group_csv> rand_opt_group;
+
+static std::map<std::string, int> um_mapid2jobname {
+	{ "Novice", JOB_NOVICE }, // Novice and Super Novice share the same value
+	{ "SuperNovice", JOB_NOVICE },
+	{ "Swordman", JOB_SWORDMAN },
+	{ "Mage", JOB_MAGE },
+	{ "Archer", JOB_ARCHER },
+	{ "Acolyte", JOB_ACOLYTE },
+	{ "Merchant", JOB_MERCHANT },
+	{ "Thief", JOB_THIEF },
+	{ "Knight", JOB_KNIGHT },
+	{ "Priest", JOB_PRIEST },
+	{ "Wizard", JOB_WIZARD },
+	{ "Blacksmith", JOB_BLACKSMITH },
+	{ "Hunter", JOB_HUNTER },
+	{ "Assassin", JOB_ASSASSIN },
+	{ "Crusader", JOB_CRUSADER },
+	{ "Monk", JOB_MONK },
+	{ "Sage", JOB_SAGE },
+	{ "Rogue", JOB_ROGUE },
+	{ "Alchemist", JOB_ALCHEMIST },
+	{ "BardDancer", JOB_BARD }, // Bard and Dancer share the same value
+	{ "BardDancer", JOB_DANCER },
+	{ "Gunslinger", JOB_GUNSLINGER },
+	{ "Ninja", JOB_NINJA },
+	{ "Taekwon", 21 },
+	{ "StarGladiator", 22 },
+	{ "SoulLinker", 23 },
+//	{ "Gangsi", 26 },
+//	{ "DeathKnight", 27 },
+//	{ "DarkCollector", 28 },
+#ifdef RENEWAL
+	{ "KagerouOboro", 29 }, // Kagerou and Oboro share the same value
+	{ "Rebellion", 30 },
+	{ "Summoner", 31 },
+#endif
+};
+
+static std::unordered_map<std::string, equip_pos> um_equipnames {
+	{ "Head_Low", EQP_HEAD_LOW },
+	{ "Head_Mid", EQP_HEAD_MID },
+	{ "Head_Top", EQP_HEAD_TOP },
+	{ "Right_Hand", EQP_HAND_R },
+	{ "Left_Hand", EQP_HAND_L },
+	{ "Armor", EQP_ARMOR },
+	{ "Shoes", EQP_SHOES },
+	{ "Garment", EQP_GARMENT },
+	{ "Right_Accessory", EQP_ACC_R },
+	{ "Left_Accessory", EQP_ACC_L },
+	{ "Costume_Head_Top", EQP_COSTUME_HEAD_TOP },
+	{ "Costume_Head_Mid", EQP_COSTUME_HEAD_MID },
+	{ "Costume_Head_Low", EQP_COSTUME_HEAD_LOW },
+	{ "Costume_Garment", EQP_COSTUME_GARMENT },
+	{ "Ammo", EQP_AMMO },
+	{ "Shadow_Armor", EQP_SHADOW_ARMOR },
+	{ "Shadow_Weapon", EQP_SHADOW_WEAPON },
+	{ "Shadow_Shield", EQP_SHADOW_SHIELD },
+	{ "Shadow_Shoes", EQP_SHADOW_SHOES },
+	{ "Shadow_Right_Accessory", EQP_SHADOW_ACC_R },
+	{ "Shadow_Left_Accessory", EQP_SHADOW_ACC_L },
+};
+
+// Initialize Random Option constants
+void init_random_option_constants() {
+	#define export_constant2(a, b) script_set_constant_(a, b, a, false, false)
+
+	export_constant2("RDMOPT_VAR_MAXHPAMOUNT", 1);
+	export_constant2("RDMOPT_VAR_MAXSPAMOUNT", 2);
+	export_constant2("RDMOPT_VAR_STRAMOUNT", 3);
+	export_constant2("RDMOPT_VAR_AGIAMOUNT", 4);
+	export_constant2("RDMOPT_VAR_VITAMOUNT", 5);
+	export_constant2("RDMOPT_VAR_INTAMOUNT", 6);
+	export_constant2("RDMOPT_VAR_DEXAMOUNT", 7);
+	export_constant2("RDMOPT_VAR_LUKAMOUNT", 8);
+	export_constant2("RDMOPT_VAR_MAXHPPERCENT", 9);
+	export_constant2("RDMOPT_VAR_MAXSPPERCENT", 10);
+	export_constant2("RDMOPT_VAR_HPACCELERATION", 11);
+	export_constant2("RDMOPT_VAR_SPACCELERATION", 12);
+	export_constant2("RDMOPT_VAR_ATKPERCENT", 13);
+	export_constant2("RDMOPT_VAR_MAGICATKPERCENT", 14);
+	export_constant2("RDMOPT_VAR_PLUSASPD", 15);
+	export_constant2("RDMOPT_VAR_PLUSASPDPERCENT", 16);
+	export_constant2("RDMOPT_VAR_ATTPOWER", 17);
+	export_constant2("RDMOPT_VAR_HITSUCCESSVALUE", 18);
+	export_constant2("RDMOPT_VAR_ATTMPOWER", 19);
+	export_constant2("RDMOPT_VAR_ITEMDEFPOWER", 20);
+	export_constant2("RDMOPT_VAR_MDEFPOWER", 21);
+	export_constant2("RDMOPT_VAR_AVOIDSUCCESSVALUE", 22);
+	export_constant2("RDMOPT_VAR_PLUSAVOIDSUCCESSVALUE", 23);
+	export_constant2("RDMOPT_VAR_CRITICALSUCCESSVALUE", 24);
+	export_constant2("RDMOPT_ATTR_TOLERACE_NOTHING", 25);
+	export_constant2("RDMOPT_ATTR_TOLERACE_WATER", 26);
+	export_constant2("RDMOPT_ATTR_TOLERACE_GROUND", 27);
+	export_constant2("RDMOPT_ATTR_TOLERACE_FIRE", 28);
+	export_constant2("RDMOPT_ATTR_TOLERACE_WIND", 29);
+	export_constant2("RDMOPT_ATTR_TOLERACE_POISON", 30);
+	export_constant2("RDMOPT_ATTR_TOLERACE_SAINT", 31);
+	export_constant2("RDMOPT_ATTR_TOLERACE_DARKNESS", 32);
+	export_constant2("RDMOPT_ATTR_TOLERACE_TELEKINESIS", 33);
+	export_constant2("RDMOPT_ATTR_TOLERACE_UNDEAD", 34);
+	export_constant2("RDMOPT_ATTR_TOLERACE_ALLBUTNOTHING", 35);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_NOTHING_USER", 36);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_NOTHING_TARGET", 37);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_WATER_USER", 38);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_WATER_TARGET", 39);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_GROUND_USER", 40);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_GROUND_TARGET", 41);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_FIRE_USER", 42);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_FIRE_TARGET", 43);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_WIND_USER", 44);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_WIND_TARGET", 45);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_POISON_USER", 46);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_POISON_TARGET", 47);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_SAINT_USER", 48);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_SAINT_TARGET", 49);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_DARKNESS_USER", 50);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_DARKNESS_TARGET", 51);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_TELEKINESIS_USER", 52);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_TELEKINESIS_TARGET", 53);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_UNDEAD_USER", 54);
+	export_constant2("RDMOPT_DAMAGE_PROPERTY_UNDEAD_TARGET", 55);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_NOTHING_USER", 56);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_NOTHING_TARGET", 57);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_WATER_USER", 58);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_WATER_TARGET", 59);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_GROUND_USER", 60);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_GROUND_TARGET", 61);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_FIRE_USER", 62);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_FIRE_TARGET", 63);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_WIND_USER", 64);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_WIND_TARGET", 65);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_POISON_USER", 66);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_POISON_TARGET", 67);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_SAINT_USER", 68);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_SAINT_TARGET", 69);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_DARKNESS_USER", 70);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_DARKNESS_TARGET", 71);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_TELEKINESIS_USER", 72);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_TELEKINESIS_TARGET", 73);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_UNDEAD_USER", 74);
+	export_constant2("RDMOPT_MDAMAGE_PROPERTY_UNDEAD_TARGET", 75);
+	export_constant2("RDMOPT_BODY_ATTR_NOTHING", 76);
+	export_constant2("RDMOPT_BODY_ATTR_WATER", 77);
+	export_constant2("RDMOPT_BODY_ATTR_GROUND", 78);
+	export_constant2("RDMOPT_BODY_ATTR_FIRE", 79);
+	export_constant2("RDMOPT_BODY_ATTR_WIND", 80);
+	export_constant2("RDMOPT_BODY_ATTR_POISON", 81);
+	export_constant2("RDMOPT_BODY_ATTR_SAINT", 82);
+	export_constant2("RDMOPT_BODY_ATTR_DARKNESS", 83);
+	export_constant2("RDMOPT_BODY_ATTR_TELEKINESIS", 84);
+	export_constant2("RDMOPT_BODY_ATTR_UNDEAD", 85);
+	export_constant2("RDMOPT_RACE_TOLERACE_NOTHING", 87);
+	export_constant2("RDMOPT_RACE_TOLERACE_UNDEAD", 88);
+	export_constant2("RDMOPT_RACE_TOLERACE_ANIMAL", 89);
+	export_constant2("RDMOPT_RACE_TOLERACE_PLANT", 90);
+	export_constant2("RDMOPT_RACE_TOLERACE_INSECT", 91);
+	export_constant2("RDMOPT_RACE_TOLERACE_FISHS", 92);
+	export_constant2("RDMOPT_RACE_TOLERACE_DEVIL", 93);
+	export_constant2("RDMOPT_RACE_TOLERACE_HUMAN", 94);
+	export_constant2("RDMOPT_RACE_TOLERACE_ANGEL", 95);
+	export_constant2("RDMOPT_RACE_TOLERACE_DRAGON", 96);
+	export_constant2("RDMOPT_RACE_DAMAGE_NOTHING", 97);
+	export_constant2("RDMOPT_RACE_DAMAGE_UNDEAD", 98);
+	export_constant2("RDMOPT_RACE_DAMAGE_ANIMAL", 99);
+	export_constant2("RDMOPT_RACE_DAMAGE_PLANT", 100);
+	export_constant2("RDMOPT_RACE_DAMAGE_INSECT", 101);
+	export_constant2("RDMOPT_RACE_DAMAGE_FISHS", 102);
+	export_constant2("RDMOPT_RACE_DAMAGE_DEVIL", 103);
+	export_constant2("RDMOPT_RACE_DAMAGE_HUMAN", 104);
+	export_constant2("RDMOPT_RACE_DAMAGE_ANGEL", 105);
+	export_constant2("RDMOPT_RACE_DAMAGE_DRAGON", 106);
+	export_constant2("RDMOPT_RACE_MDAMAGE_NOTHING", 107);
+	export_constant2("RDMOPT_RACE_MDAMAGE_UNDEAD", 108);
+	export_constant2("RDMOPT_RACE_MDAMAGE_ANIMAL", 109);
+	export_constant2("RDMOPT_RACE_MDAMAGE_PLANT", 110);
+	export_constant2("RDMOPT_RACE_MDAMAGE_INSECT", 111);
+	export_constant2("RDMOPT_RACE_MDAMAGE_FISHS", 112);
+	export_constant2("RDMOPT_RACE_MDAMAGE_DEVIL", 113);
+	export_constant2("RDMOPT_RACE_MDAMAGE_HUMAN", 114);
+	export_constant2("RDMOPT_RACE_MDAMAGE_ANGEL", 115);
+	export_constant2("RDMOPT_RACE_MDAMAGE_DRAGON", 116);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_NOTHING", 117);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_UNDEAD", 118);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_ANIMAL", 119);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_PLANT", 120);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_INSECT", 121);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_FISHS", 122);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_DEVIL", 123);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_HUMAN", 124);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_ANGEL", 125);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_DRAGON", 126);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_NOTHING", 127);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_UNDEAD", 128);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_ANIMAL", 129);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_PLANT", 130);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_INSECT", 131);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_FISHS", 132);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_DEVIL", 133);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_HUMAN", 134);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_ANGEL", 135);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_DRAGON", 136);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_NOTHING", 137);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_UNDEAD", 138);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_ANIMAL", 139);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_PLANT", 140);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_INSECT", 141);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_FISHS", 142);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_DEVIL", 143);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_HUMAN", 144);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_ANGEL", 145);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_DRAGON", 146);
+	export_constant2("RDMOPT_CLASS_DAMAGE_NORMAL_TARGET", 147);
+	export_constant2("RDMOPT_CLASS_DAMAGE_BOSS_TARGET", 148);
+	export_constant2("RDMOPT_CLASS_DAMAGE_NORMAL_USER", 149);
+	export_constant2("RDMOPT_CLASS_DAMAGE_BOSS_USER", 150);
+	export_constant2("RDMOPT_CLASS_MDAMAGE_NORMAL", 151);
+	export_constant2("RDMOPT_CLASS_MDAMAGE_BOSS", 152);
+	export_constant2("RDMOPT_CLASS_IGNORE_DEF_PERCENT_NORMAL", 153);
+	export_constant2("RDMOPT_CLASS_IGNORE_DEF_PERCENT_BOSS", 154);
+	export_constant2("RDMOPT_CLASS_IGNORE_MDEF_PERCENT_NORMAL", 155);
+	export_constant2("RDMOPT_CLASS_IGNORE_MDEF_PERCENT_BOSS", 156);
+	export_constant2("RDMOPT_DAMAGE_SIZE_SMALL_TARGET", 157);
+	export_constant2("RDMOPT_DAMAGE_SIZE_MIDIUM_TARGET", 158);
+	export_constant2("RDMOPT_DAMAGE_SIZE_LARGE_TARGET", 159);
+	export_constant2("RDMOPT_DAMAGE_SIZE_SMALL_USER", 160);
+	export_constant2("RDMOPT_DAMAGE_SIZE_MIDIUM_USER", 161);
+	export_constant2("RDMOPT_DAMAGE_SIZE_LARGE_USER", 162);
+	export_constant2("RDMOPT_DAMAGE_SIZE_PERFECT", 163);
+	export_constant2("RDMOPT_DAMAGE_CRI_TARGET", 164);
+	export_constant2("RDMOPT_DAMAGE_CRI_USER", 165);
+	export_constant2("RDMOPT_RANGE_ATTACK_DAMAGE_TARGET", 166);
+	export_constant2("RDMOPT_RANGE_ATTACK_DAMAGE_USER", 167);
+	export_constant2("RDMOPT_HEAL_VALUE", 168);
+	export_constant2("RDMOPT_HEAL_MODIFY_PERCENT", 169);
+	export_constant2("RDMOPT_DEC_SPELL_CAST_TIME", 170);
+	export_constant2("RDMOPT_DEC_SPELL_DELAY_TIME", 171);
+	export_constant2("RDMOPT_DEC_SP_CONSUMPTION", 172);
+	export_constant2("RDMOPT_WEAPON_ATTR_NOTHING", 175);
+	export_constant2("RDMOPT_WEAPON_ATTR_WATER", 176);
+	export_constant2("RDMOPT_WEAPON_ATTR_GROUND", 177);
+	export_constant2("RDMOPT_WEAPON_ATTR_FIRE", 178);
+	export_constant2("RDMOPT_WEAPON_ATTR_WIND", 179);
+	export_constant2("RDMOPT_WEAPON_ATTR_POISON", 180);
+	export_constant2("RDMOPT_WEAPON_ATTR_SAINT", 181);
+	export_constant2("RDMOPT_WEAPON_ATTR_DARKNESS", 182);
+	export_constant2("RDMOPT_WEAPON_ATTR_TELEKINESIS", 183);
+	export_constant2("RDMOPT_WEAPON_ATTR_UNDEAD", 184);
+	export_constant2("RDMOPT_WEAPON_INDESTRUCTIBLE", 185);
+	export_constant2("RDMOPT_BODY_INDESTRUCTIBLE", 186);
+	export_constant2("RDMOPT_MDAMAGE_SIZE_SMALL_TARGET", 187);
+	export_constant2("RDMOPT_MDAMAGE_SIZE_MIDIUM_TARGET", 188);
+	export_constant2("RDMOPT_MDAMAGE_SIZE_LARGE_TARGET", 189);
+	export_constant2("RDMOPT_MDAMAGE_SIZE_SMALL_USER", 190);
+	export_constant2("RDMOPT_MDAMAGE_SIZE_MIDIUM_USER", 191);
+	export_constant2("RDMOPT_MDAMAGE_SIZE_LARGE_USER", 192);
+	export_constant2("RDMOPT_ATTR_TOLERACE_ALL", 193);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_NOTHING", 194);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_UNDEAD", 195);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_ANIMAL", 196);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_PLANT", 197);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_INSECT", 198);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_FISHS", 199);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_DEVIL", 200);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_HUMAN", 201);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_ANGEL", 202);
+	export_constant2("RDMOPT_RACE_WEAPON_TOLERACE_DRAGON", 203);
+	export_constant2("RDMOPT_RACE_TOLERACE_PLAYER_HUMAN", 206);
+	export_constant2("RDMOPT_RACE_TOLERACE_PLAYER_DORAM", 207);
+	export_constant2("RDMOPT_RACE_DAMAGE_PLAYER_HUMAN", 208);
+	export_constant2("RDMOPT_RACE_DAMAGE_PLAYER_DORAM", 209);
+	export_constant2("RDMOPT_RACE_MDAMAGE_PLAYER_HUMAN", 210);
+	export_constant2("RDMOPT_RACE_MDAMAGE_PLAYER_DORAM", 211);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_PLAYER_HUMAN", 212);
+	export_constant2("RDMOPT_RACE_CRI_PERCENT_PLAYER_DORAM", 213);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_PLAYER_HUMAN", 214);
+	export_constant2("RDMOPT_RACE_IGNORE_DEF_PERCENT_PLAYER_DORAM", 215);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_PLAYER_HUMAN", 216);
+	export_constant2("RDMOPT_RACE_IGNORE_MDEF_PERCENT_PLAYER_DORAM", 217);
+	export_constant2("RDMOPT_MELEE_ATTACK_DAMAGE_TARGET", 219);
+	export_constant2("RDMOPT_MELEE_ATTACK_DAMAGE_USER", 220);
+
+	#undef export_constant2
+}
+
+static bool guild_read_guildskill_tree_db( char* split[], int columns, int current );
+static bool pet_read_db( const char* file );
+static bool skill_parse_row_magicmushroomdb(char *split[], int column, int current);
+static bool skill_parse_row_abradb(char* split[], int columns, int current);
+static bool skill_parse_row_spellbookdb(char* split[], int columns, int current);
+static bool mob_readdb_mobavail(char *str[], int columns, int current);
+static bool skill_parse_row_requiredb(char* split[], int columns, int current);
+static bool skill_parse_row_castdb(char* split[], int columns, int current);
+static bool skill_parse_row_castnodexdb(char* split[], int columns, int current);
+static bool skill_parse_row_unitdb(char* split[], int columns, int current);
+static bool skill_parse_row_copyabledb(char* split[], int columns, int current);
+static bool skill_parse_row_nonearnpcrangedb(char* split[], int columns, int current);
+static bool skill_parse_row_skilldb(char* split[], int columns, int current);
+static bool quest_read_db(char *split[], int columns, int current);
+static bool instance_readdb_sub(char* str[], int columns, int current);
+static bool itemdb_read_itemavail(char *str[], int columns, int current);
+static bool itemdb_read_buyingstore(char* fields[], int columns, int current);
+static bool itemdb_read_flag(char* fields[], int columns, int current);
+static bool itemdb_read_itemdelay(char* str[], int columns, int current);
+static bool itemdb_read_stack(char* fields[], int columns, int current);
+static bool itemdb_read_nouse(char* fields[], int columns, int current);
+static bool itemdb_read_itemtrade(char* fields[], int columns, int current);
+static bool itemdb_read_db(const char *file);
+static bool itemdb_read_randomopt(const char* file);
+static bool itemdb_read_randomopt_group(char *str[], int columns, int current);
+static bool itemdb_randomopt_group_yaml(void);
+static bool pc_readdb_levelpenalty(char* fields[], int columns, int current);
+static bool pc_levelpenalty_yaml();
+
+#endif /* CSV2YAML_HPP */

+ 4 - 0
src/tool/csv2yaml.vcxproj

@@ -158,6 +158,10 @@
       <AdditionalDependencies>ws2_32.lib;$(SolutionDir).vs\build\common-minicore.lib;$(SolutionDir)3rdparty\zlib\lib\$(Platform)\zlib.lib;$(SolutionDir).vs\build\yaml-cpp.lib;%(AdditionalDependencies)</AdditionalDependencies>
       <AdditionalDependencies>ws2_32.lib;$(SolutionDir).vs\build\common-minicore.lib;$(SolutionDir)3rdparty\zlib\lib\$(Platform)\zlib.lib;$(SolutionDir).vs\build\yaml-cpp.lib;%(AdditionalDependencies)</AdditionalDependencies>
     </Link>
     </Link>
   </ItemDefinitionGroup>
   </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClInclude Include="csv2yaml.hpp" />
+    <ClInclude Include="yaml.hpp" />
+  </ItemGroup>
   <ItemGroup>
   <ItemGroup>
     <ClCompile Include="..\common\database.cpp" />
     <ClCompile Include="..\common\database.cpp" />
     <ClCompile Include="csv2yaml.cpp" />
     <ClCompile Include="csv2yaml.cpp" />

+ 8 - 0
src/tool/csv2yaml.vcxproj.filters

@@ -10,6 +10,14 @@
       <Extensions>h;hh;hpp;hxx;hm;inl;inc;xsd</Extensions>
       <Extensions>h;hh;hpp;hxx;hm;inl;inc;xsd</Extensions>
     </Filter>
     </Filter>
   </ItemGroup>
   </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="csv2yaml.hpp">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="yaml.hpp">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
   <ItemGroup>
   <ItemGroup>
     <ClCompile Include="csv2yaml.cpp">
     <ClCompile Include="csv2yaml.cpp">
       <Filter>Source Files</Filter>
       <Filter>Source Files</Filter>

+ 657 - 0
src/tool/yaml.hpp

@@ -0,0 +1,657 @@
+// Copyright (c) rAthena Dev Teams - Licensed under GNU GPL
+// For more information, see LICENCE in the main folder
+
+#ifndef YAML_HPP
+#define YAML_HPP
+
+#include <fstream>
+#include <functional>
+#include <iostream>
+#include <locale>
+#include <map>
+#include <unordered_map>
+#include <vector>
+
+#ifdef WIN32
+	#include <conio.h>
+#else
+	#include <termios.h>
+	#include <unistd.h>
+	#include <stdio.h>
+#endif
+
+#include <yaml-cpp/yaml.h>
+
+#include "../common/cbasetypes.hpp"
+#include "../common/core.hpp"
+#include "../common/malloc.hpp"
+#include "../common/mmo.hpp"
+#include "../common/nullpo.hpp"
+#include "../common/showmsg.hpp"
+#include "../common/strlib.hpp"
+#include "../common/utilities.hpp"
+#include "../common/utils.hpp"
+#ifdef WIN32
+#include "../common/winapi.hpp"
+#endif
+
+// Only for constants - do not use functions of it or linking will fail
+#include "../map/achievement.hpp"
+#include "../map/battle.hpp"
+#include "../map/battleground.hpp"
+#include "../map/channel.hpp"
+#include "../map/chat.hpp"
+#include "../map/date.hpp"
+#include "../map/instance.hpp"
+#include "../map/mercenary.hpp"
+#include "../map/mob.hpp"
+#include "../map/npc.hpp"
+#include "../map/pc.hpp"
+#include "../map/pet.hpp"
+#include "../map/quest.hpp"
+#include "../map/script.hpp"
+#include "../map/skill.hpp"
+#include "../map/storage.hpp"
+
+using namespace rathena;
+
+#ifndef WIN32
+int getch(void) {
+	struct termios oldattr, newattr;
+	int ch;
+	tcgetattr(STDIN_FILENO, &oldattr);
+	newattr = oldattr;
+	newattr.c_lflag &= ~(ICANON | ECHO);
+	tcsetattr(STDIN_FILENO, TCSANOW, &newattr);
+	ch = getchar();
+	tcsetattr(STDIN_FILENO, TCSANOW, &oldattr);
+	return ch;
+}
+#endif
+
+YAML::Node inNode;
+YAML::Emitter body;
+
+// Constants for conversion
+std::unordered_map<t_itemid, std::string> aegis_itemnames;
+std::unordered_map<uint32, t_itemid> aegis_itemviewid;
+std::unordered_map<uint16, std::string> aegis_mobnames;
+std::unordered_map<uint16, std::string> aegis_skillnames;
+std::unordered_map<const char *, int64> constants;
+
+// Implement the function instead of including the original version by linking
+void script_set_constant_(const char *name, int64 value, const char *constant_name, bool isparameter, bool deprecated) {
+	constants[name] = value;
+}
+
+const char *constant_lookup(int32 value, const char *prefix) {
+	nullpo_retr(nullptr, prefix);
+
+	for (auto const &pair : constants) {
+		// Same prefix group and same value
+		if (strncasecmp(pair.first, prefix, strlen(prefix)) == 0 && pair.second == value) {
+			return pair.first;
+		}
+	}
+
+	return nullptr;
+}
+
+int64 constant_lookup_int(const char *constant) {
+	nullpo_retr(-100, constant);
+
+	for (auto const &pair : constants) {
+		if (strlen(pair.first) == strlen(constant) && strncasecmp(pair.first, constant, strlen(constant)) == 0) {
+			return pair.second;
+		}
+	}
+
+	return -100;
+}
+
+/**
+ * Determines if a file exists.
+ * @param path: File to check for
+ * @return True if file exists or false otherwise
+ */
+bool fileExists(const std::string &path) {
+	std::ifstream in;
+
+	in.open(path);
+
+	if (in.is_open()) {
+		in.close();
+
+		return true;
+	} else {
+		return false;
+	}
+}
+
+/**
+ * Prompt for confirmation.
+ * @param fmt: Message to print
+ * @param va_arg: Any arguments needed for message
+ * @return True on yes or false otherwise
+ */
+bool askConfirmation(const char *fmt, ...) {
+	va_list ap;
+
+	va_start(ap, fmt);
+
+	_vShowMessage(MSG_NONE, fmt, ap);
+
+	va_end(ap);
+
+	char c = getch();
+
+	if (c == 'Y' || c == 'y') {
+		return true;
+	} else {
+		return false;
+	}
+}
+
+/**
+ * Returns a YAML header version
+ * @param node: YAML node
+ * @return Version number
+ */
+uint32 getHeaderVersion(YAML::Node &node) {
+	return node["Header"]["Version"].as<uint32>();
+}
+
+/**
+ * Copy a file if it exists.
+ * @param file: File stream
+ * @param name: File name
+ * @param newLine: Append new line at end of copy
+ */
+void copyFileIfExists(std::ofstream &file, const std::string &name, bool newLine) {
+	std::string path = "doc/yaml/db/" + name + ".yml";
+
+	if (fileExists(path)) {
+		std::ifstream source(path, std::ios::binary);
+
+		std::istreambuf_iterator<char> begin_source(source);
+		std::istreambuf_iterator<char> end_source;
+		std::ostreambuf_iterator<char> begin_dest(file);
+		copy(begin_source, end_source, begin_dest);
+
+		source.close();
+
+		if (newLine) {
+			file << "\n";
+		}
+	}
+}
+
+/**
+ * Prepares header for output.
+ * @param file: File stream
+ * @param type: Database type
+ * @param version: Database version
+ * @param name: File name
+ */
+void prepareHeader(std::ofstream &file, const std::string &type, uint32 version, const std::string &name) {
+	copyFileIfExists(file, "license", false);
+	copyFileIfExists(file, name, true);
+
+	YAML::Emitter header(file);
+
+	header << YAML::BeginMap;
+	header << YAML::Key << "Header";
+	header << YAML::BeginMap;
+	header << YAML::Key << "Type" << YAML::Value << type;
+	header << YAML::Key << "Version" << YAML::Value << version;
+	header << YAML::EndMap;
+	header << YAML::EndMap;
+
+	file << "\n";
+	file << "\n";
+}
+
+/**
+ * Prepares footer for output.
+ * @param file: File stream
+ */
+void prepareFooter(std::ostream &file) {
+	if (!inNode["Footer"].IsDefined())
+		return;
+
+	if (inNode["Body"].IsDefined()) {
+		file << "\n";
+		file << "\n";
+	}
+
+	YAML::Emitter footer(file);
+
+	footer << YAML::BeginMap;
+	footer << YAML::Key << "Footer";
+	footer << YAML::BeginMap;
+	footer << YAML::Key << "Imports";
+	footer << YAML::BeginSeq;
+	for (const YAML::Node &import : inNode["Footer"]["Imports"]) {
+		footer << YAML::BeginMap;
+		footer << YAML::Key << "Path" << YAML::Value << import["Path"];
+		if (import["Mode"].IsDefined())
+			footer << YAML::Key << "Mode" << YAML::Value << import["Mode"];
+		footer << YAML::EndMap;
+	}
+	footer << YAML::EndSeq;
+	footer << YAML::EndMap;
+	footer << YAML::EndMap;
+}
+
+/**
+ * Prepares body for output.
+ */
+void prepareBody(void) {
+	body << YAML::BeginMap;
+	body << YAML::Key << "Body";
+	body << YAML::BeginSeq;
+}
+
+/**
+ * Finalizes body's output.
+ */
+void finalizeBody(void) {
+	body << YAML::EndSeq;
+	body << YAML::EndMap;
+}
+
+/**
+ * Split the string with ':' as separator and put each value for a skilllv
+ * @param str: String to split
+ * @param val: Array of MAX_SKILL_LEVEL to put value into
+ * @return 0:error, x:number of value assign (should be MAX_SKILL_LEVEL)
+ */
+int skill_split_atoi(char *str, int *val) {
+	int i;
+
+	for (i = 0; i < MAX_SKILL_LEVEL; i++) {
+		if (!str)
+			break;
+		val[i] = atoi(str);
+		str = strchr(str, ':');
+		if (str)
+			*str++ = 0;
+	}
+
+	if (i == 0) // No data found.
+		return 0;
+
+	if (i == 1) // Single value, have the whole range have the same value.
+		return 1;
+
+	return i;
+}
+
+/**
+ * Split string to int by constant value (const.txt) or atoi()
+ * @param *str: String input
+ * @param *val: Temporary storage
+ * @param *delim: Delimiter (for multiple value support)
+ * @param min_value: Minimum value. If the splitted value is less or equal than this, will be skipped
+ * @param max: Maximum number that can be allocated
+ * @return count: Number of success
+ */
+uint8 skill_split_atoi2(char *str, int64 *val, const char *delim, int min_value, uint16 max) {
+	uint8 i = 0;
+	char *p = strtok(str, delim);
+
+	while (p != NULL) {
+		int64 n = min_value;
+
+		trim(p);
+
+		if (ISDIGIT(p[0])) // If using numeric
+			n = atoi(p);
+		else {
+			n = constant_lookup_int(p);
+			p = strtok(NULL, delim);
+		}
+
+		if (n > min_value) {
+			val[i] = n;
+			i++;
+			if (i >= max)
+				break;
+		}
+		p = strtok(NULL, delim);
+	}
+	return i;
+}
+
+/**
+ * Split string to int
+ * @param str: String input
+ * @param val1: Temporary storage to first value
+ * @param val2: Temporary storage to second value
+ */
+static void itemdb_re_split_atoi(char* str, int* val1, int* val2) {
+	int i, val[2];
+
+	for (i = 0; i < 2; i++) {
+		if (!str)
+			break;
+		val[i] = atoi(str);
+		str = strchr(str, ':');
+		if (str)
+			*str++ = 0;
+	}
+	if (i == 0) {
+		*val1 = *val2 = 0;
+		return; // no data found
+	}
+	if (i == 1) { // Single Value
+		*val1 = val[0];
+		*val2 = 0;
+		return;
+	}
+
+	// We assume we have 2 values.
+	*val1 = val[0];
+	*val2 = val[1];
+	return;
+}
+
+/**
+ * Determine if array contains level specific data
+ * @param arr: Array to check
+ * @return True if level specific or false for same for all levels
+ */
+static bool isMultiLevel(int arr[]) {
+	uint8 count = 0;
+
+	for (uint8 i = 0; i < MAX_SKILL_LEVEL; i++) {
+		if (arr[i] != 0)
+			count++;
+	}
+
+	return (count < 2 ? false : true);
+}
+
+/**
+ * Converts a string to upper case characters based on specific cases.
+ * @param name: String to convert
+ * @return Converted string
+ */
+std::string name2Upper(std::string name) {
+	std::transform(name.begin(), name.end(), name.begin(), ::tolower);
+	name[0] = toupper(name[0]);
+
+	for (size_t i = 0; i < name.size(); i++) {
+		if (name[i - 1] == '_' || (name[i - 2] == '1' && name[i - 1] == 'h') || (name[i - 2] == '2' && name[i - 1] == 'h'))
+			name[i] = toupper(name[i]);
+	}
+
+	return name;
+}
+
+// Constant loading functions
+static bool parse_item_constants_txt(const char *path) {
+	uint32 lines = 0, count = 0;
+	char line[1024];
+
+	FILE *fp;
+
+	fp = fopen(path, "r");
+	if (fp == NULL) {
+		ShowWarning("itemdb_readdb: File not found \"%s\", skipping.\n", path);
+		return false;
+	}
+
+	// process rows one by one
+	while (fgets(line, sizeof(line), fp))
+	{
+		char *str[32], *p;
+		int i;
+		lines++;
+		if (line[0] == '/' && line[1] == '/')
+			continue;
+		memset(str, 0, sizeof(str));
+
+		p = strstr(line, "//");
+
+		if (p != nullptr) {
+			*p = '\0';
+		}
+
+		p = line;
+		while (ISSPACE(*p))
+			++p;
+		if (*p == '\0')
+			continue;// empty line
+		for (i = 0; i < 19; ++i)
+		{
+			str[i] = p;
+			p = strchr(p, ',');
+			if (p == NULL)
+				break;// comma not found
+			*p = '\0';
+			++p;
+		}
+
+		t_itemid item_id = strtoul(str[0], nullptr, 10);
+
+		if (p == NULL)
+		{
+			ShowError("itemdb_readdb: Insufficient columns in line %d of \"%s\" (item with id %u), skipping.\n", lines, path, item_id);
+			continue;
+		}
+
+		// Script
+		if (*p != '{')
+		{
+			ShowError("itemdb_readdb: Invalid format (Script column) in line %d of \"%s\" (item with id %u), skipping.\n", lines, path, item_id);
+			continue;
+		}
+		str[19] = p + 1;
+		p = strstr(p + 1, "},");
+		if (p == NULL)
+		{
+			ShowError("itemdb_readdb: Invalid format (Script column) in line %d of \"%s\" (item with id %u), skipping.\n", lines, path, item_id);
+			continue;
+		}
+		*p = '\0';
+		p += 2;
+
+		// OnEquip_Script
+		if (*p != '{')
+		{
+			ShowError("itemdb_readdb: Invalid format (OnEquip_Script column) in line %d of \"%s\" (item with id %u), skipping.\n", lines, path, item_id);
+			continue;
+		}
+		str[20] = p + 1;
+		p = strstr(p + 1, "},");
+		if (p == NULL)
+		{
+			ShowError("itemdb_readdb: Invalid format (OnEquip_Script column) in line %d of \"%s\" (item with id %u), skipping.\n", lines, path, item_id);
+			continue;
+		}
+		*p = '\0';
+		p += 2;
+
+		// OnUnequip_Script (last column)
+		if (*p != '{')
+		{
+			ShowError("itemdb_readdb: Invalid format (OnUnequip_Script column) in line %d of \"%s\" (item with id %u), skipping.\n", lines, path, item_id);
+			continue;
+		}
+		str[21] = p;
+		p = &str[21][strlen(str[21]) - 2];
+
+		if (*p != '}') {
+			/* lets count to ensure it's not something silly e.g. a extra space at line ending */
+			int lcurly = 0, rcurly = 0;
+
+			for (size_t v = 0; v < strlen(str[21]); v++) {
+				if (str[21][v] == '{')
+					lcurly++;
+				else if (str[21][v] == '}') {
+					rcurly++;
+					p = &str[21][v];
+				}
+			}
+
+			if (lcurly != rcurly) {
+				ShowError("itemdb_readdb: Mismatching curly braces in line %d of \"%s\" (item with id %u), skipping.\n", lines, path, item_id);
+				continue;
+			}
+		}
+		str[21] = str[21] + 1;  //skip the first left curly
+		*p = '\0';              //null the last right curly
+
+		uint32 view_id = strtoul(str[18], nullptr, 10);
+		char *name = trim(str[1]);
+
+		aegis_itemnames[item_id] = std::string(name);
+
+		if (atoi(str[14]) & (EQP_HELM | EQP_COSTUME_HELM) && util::umap_find(aegis_itemviewid, view_id) == nullptr)
+			aegis_itemviewid[view_id] = item_id;
+
+		count++;
+	}
+
+	fclose(fp);
+
+	ShowStatus("Done reading '" CL_WHITE "%u" CL_RESET "' entries in '" CL_WHITE "%s" CL_RESET "'.\n", count, path);
+
+	return true;
+}
+
+const std::string ItemDatabase::getDefaultLocation() {
+	return std::string(db_path) + "/item_db.yml";
+}
+
+uint64 ItemDatabase::parseBodyNode(const YAML::Node& node) {
+	t_itemid nameid;
+
+	if (!this->asUInt32(node, "Id", nameid))
+		return 0;
+
+	if (this->nodeExists(node, "AegisName")) {
+		std::string name;
+
+		if (!this->asString(node, "AegisName", name))
+			return 0;
+
+		aegis_itemnames[nameid] = name;
+	}
+
+	if (this->nodeExists(node, "View")) {
+		uint32 look;
+
+		if (!this->asUInt32(node, "View", look))
+			return 0;
+
+		if (look > 0) {
+			if (this->nodeExists(node, "Locations")) {
+				const YAML::Node& locationNode = node["Locations"];
+
+				static std::vector<std::string> locations = {
+					"Head_Low",
+					"Head_Mid",
+					"Head_Top",
+					"Costume_Head_Low",
+					"Costume_Head_Mid",
+					"Costume_Head_Top"
+				};
+
+				for (std::string& location : locations) {
+					if (this->nodeExists(locationNode, location)) {
+						bool active;
+
+						if (!this->asBool(locationNode, location, active))
+							return 0;
+
+						aegis_itemviewid[look] = nameid;
+						break;
+					}
+				}
+			}
+		}
+	}
+
+	return 1;
+}
+
+void ItemDatabase::loadingFinished() {
+}
+
+ItemDatabase item_db;
+
+static bool parse_mob_constants_txt(char *split[], int columns, int current) {
+	uint16 mob_id = atoi(split[0]);
+	char *name = trim(split[1]);
+
+	aegis_mobnames[mob_id] = std::string(name);
+
+	return true;
+}
+
+static bool parse_skill_constants_txt(char *split[], int columns, int current) {
+	uint16 skill_id = atoi(split[0]);
+	char *name = trim(split[16]);
+
+	aegis_skillnames[skill_id] = std::string(name);
+
+	return true;
+}
+
+const std::string SkillDatabase::getDefaultLocation() {
+	return std::string(db_path) + "/skill_db.yml";
+}
+
+uint64 SkillDatabase::parseBodyNode(const YAML::Node &node) {
+	t_itemid nameid;
+
+	if (!this->asUInt32(node, "Id", nameid))
+		return 0;
+
+	if (this->nodeExists(node, "Name")) {
+		std::string name;
+
+		if (!this->asString(node, "Name", name))
+			return 0;
+
+		aegis_skillnames[nameid] = name;
+	}
+
+	return 1;
+}
+
+void SkillDatabase::clear() {
+	TypesafeCachedYamlDatabase::clear();
+}
+
+SkillDatabase skill_db;
+
+const std::string MobDatabase::getDefaultLocation(){
+	return std::string( db_path ) + "/mob_db.yml";
+}
+
+uint64 MobDatabase::parseBodyNode(const YAML::Node& node) {
+	uint16 mob_id;
+
+	if (!this->asUInt16(node, "Id", mob_id))
+		return 0;
+
+	if (this->nodeExists(node, "AegisName")) {
+		std::string name;
+
+		if (!this->asString(node, "AegisName", name))
+			return 0;
+
+		aegis_mobnames[mob_id] = name;
+	}
+
+	return 1;
+}
+
+void MobDatabase::loadingFinished() {};
+
+MobDatabase mob_db;
+
+#endif /* YAML_HPP */

+ 221 - 0
src/tool/yamlupgrade.cpp

@@ -0,0 +1,221 @@
+// Copyright (c) rAthena Dev Teams - Licensed under GNU GPL
+// For more information, see LICENCE in the main folder
+
+#include "yamlupgrade.hpp"
+
+static bool upgrade_achievement_db(std::string file, const uint32 source_version);
+
+template<typename Func>
+bool process(const std::string &type, uint32 version, const std::vector<std::string> &paths, const std::string &name, Func lambda) {
+	for (const std::string &path : paths) {
+		const std::string name_ext = name + ".yml";
+		const std::string from = path + "/" + name_ext;
+		const std::string to = path + "/" + name + "-upgrade.yml";
+
+		inNode.reset();
+
+		if (fileExists(from)) {
+			inNode = YAML::LoadFile(from);
+			uint32 source_version = getHeaderVersion(inNode);
+
+			if (source_version >= version) {
+				continue;
+			}
+
+			if (!askConfirmation("Found the file \"%s\", which requires an upgrade.\nDo you want to convert it now? (Y/N)\n", from.c_str())) {
+				continue;
+			}
+
+			if (fileExists(to)) {
+				if (!askConfirmation("The file \"%s\" already exists.\nDo you want to replace it? (Y/N)\n", to.c_str())) {
+					continue;
+				}
+			}
+
+			ShowNotice("Upgrade process has begun.\n");
+
+			std::ofstream out;
+
+			body.~Emitter();
+			new (&body) YAML::Emitter();
+			out.open(to);
+
+			if (!out.is_open()) {
+				ShowError("Can not open file \"%s\" for writing.\n", to.c_str());
+				return false;
+			}
+
+			prepareHeader(out, type, version, name);
+			if (inNode["Body"].IsDefined()) {
+				prepareBody();
+
+				if (!lambda(path, name_ext, source_version)) {
+					out.close();
+					return false;
+				}
+
+				finalizeBody();
+				out << body.c_str();
+			}
+			prepareFooter(out);
+			// Make sure there is an empty line at the end of the file for git
+			out << "\n";
+			out.close();
+		}
+	}
+
+	return true;
+}
+
+int do_init(int argc, char** argv) {
+	const std::string path_db = std::string(db_path);
+	const std::string path_db_mode = path_db + "/" + DBPATH;
+	const std::string path_db_import = path_db + "/" + DBIMPORT;
+
+	// Loads required conversion constants
+	if (fileExists(item_db.getDefaultLocation())) {
+		item_db.load();
+	} else {
+		parse_item_constants_txt((path_db_mode + "item_db.txt").c_str());
+		parse_item_constants_txt((path_db_import + "item_db.txt").c_str());
+	}
+	if (fileExists(mob_db.getDefaultLocation())) {
+		mob_db.load();
+	} else {
+		sv_readdb(path_db_mode.c_str(), "mob_db.txt", ',', 31 + 2 * MAX_MVP_DROP + 2 * MAX_MOB_DROP, 31 + 2 * MAX_MVP_DROP + 2 * MAX_MOB_DROP, -1, &parse_mob_constants_txt, false);
+		sv_readdb(path_db_import.c_str(), "mob_db.txt", ',', 31 + 2 * MAX_MVP_DROP + 2 * MAX_MOB_DROP, 31 + 2 * MAX_MVP_DROP + 2 * MAX_MOB_DROP, -1, &parse_mob_constants_txt, false);
+	}
+	if (fileExists(skill_db.getDefaultLocation())) {
+		skill_db.load();
+	} else {
+		sv_readdb(path_db_mode.c_str(), "skill_db.txt", ',', 18, 18, -1, parse_skill_constants_txt, false);
+		sv_readdb(path_db_import.c_str(), "skill_db.txt", ',', 18, 18, -1, parse_skill_constants_txt, false);
+	}
+
+	// Load constants
+	#define export_constant_npc(a) export_constant(a)
+	#include "../map/script_constants.hpp"
+
+	std::vector<std::string> root_paths = {
+		path_db,
+		path_db_mode,
+		path_db_import
+	};
+
+	if (!process("ACHIEVEMENT_DB", 2, root_paths, "achievement_db", [](const std::string &path, const std::string &name_ext, uint32 source_version) -> bool {
+		return upgrade_achievement_db(path + name_ext, source_version);
+	})) {
+		return 0;
+	}
+
+	return 0;
+}
+
+void do_final(void) {
+}
+
+// Implementation of the upgrade functions
+static bool upgrade_achievement_db(std::string file, const uint32 source_version) {
+	size_t entries = 0;
+
+	for (const auto &input : inNode["Body"]) {
+		body << YAML::BeginMap;
+		body << YAML::Key << "Id" << YAML::Value << input["ID"];
+
+		std::string constant = input["Group"].as<std::string>();
+
+		constant.erase(0, 3); // Remove "AG_"
+		if (constant.compare("Chat") == 0) // Chat -> Chatting
+			constant.insert(4, "ting");
+		else if (constant.compare("Hear") == 0 || constant.compare("See") == 0)
+			constant = "Chatting"; // Aegis treats these as general "Talk to NPC" achievements.
+		else if (constant.compare("Refine") == 0) { // Refine -> Enchant
+			constant.erase(0, 6);
+			constant = "Enchant" + constant;
+		}
+		body << YAML::Key << "Group" << YAML::Value << name2Upper(constant);
+		body << YAML::Key << "Name" << YAML::Value << input["Name"];
+
+		if (input["Target"].IsDefined()) {
+			body << YAML::Key << "Targets";
+			body << YAML::BeginSeq;
+
+			for (const auto &it : input["Target"]) {
+				body << YAML::BeginMap;
+				body << YAML::Key << "Id" << YAML::Value << it["Id"];
+				if (it["MobID"].IsDefined()) {
+					uint16 mob_id = it["MobID"].as<uint16>();
+					std::string *mob_name = util::umap_find(aegis_mobnames, mob_id);
+
+					if (mob_name == nullptr) {
+						ShowWarning("mob_avail reading: Invalid mob-class %hu, Mob not read.\n", mob_id);
+						return false;
+					}
+
+					body << YAML::Key << "Mob" << YAML::Value << *mob_name;
+				}
+				if (it["Count"].IsDefined() && it["Count"].as<int32>() > 1)
+					body << YAML::Key << "Count" << YAML::Value << it["Count"];
+				body << YAML::EndMap;
+			}
+
+			body << YAML::EndSeq;
+		}
+
+		if (input["Condition"].IsDefined())
+			body << YAML::Key << "Condition" << YAML::Value << input["Condition"];
+
+		if (input["Map"].IsDefined())
+			body << YAML::Key << "Map" << YAML::Value << input["Map"];
+
+		if (input["Dependent"].IsDefined()) {
+			body << YAML::Key << "Dependents";
+			body << YAML::BeginMap;
+
+			for (const auto &it : input["Dependent"]) {
+				body << YAML::Key << it["Id"] << YAML::Value << true;
+			}
+
+			body << YAML::EndMap;
+		}
+
+		/**
+		 * Example usage for adding label at specific version.
+		if (source_version < ?) {
+			body << YAML::Key << "CustomLabel" << YAML::Value << "Unique";
+		}
+		*/
+
+		if (input["Reward"].IsDefined()) {
+			body << YAML::Key << "Rewards";
+			body << YAML::BeginMap;
+			if (input["Reward"]["ItemID"].IsDefined()) {
+				t_itemid item_id = input["Reward"]["ItemID"].as<t_itemid>();
+				std::string *item_name = util::umap_find(aegis_itemnames, item_id);
+
+				if (item_name == nullptr) {
+					ShowError("Reward item name for item ID %u is not known.\n", item_id);
+					return false;
+				}
+
+				body << YAML::Key << "Item" << YAML::Value << *item_name;
+			}
+			if (input["Reward"]["Amount"].IsDefined() && input["Reward"]["Amount"].as<uint16>() > 1)
+				body << YAML::Key << "Amount" << YAML::Value << input["Reward"]["Amount"];
+			if (input["Reward"]["Script"].IsDefined())
+				body << YAML::Key << "Script" << YAML::Value << input["Reward"]["Script"];
+			if (input["Reward"]["TitleID"].IsDefined())
+				body << YAML::Key << "TitleId" << YAML::Value << input["Reward"]["TitleID"];
+			body << YAML::EndMap;
+		}
+
+		body << YAML::Key << "Score" << YAML::Value << input["Score"];
+
+		body << YAML::EndMap;
+		entries++;
+	}
+
+	ShowStatus("Done converting/upgrading '" CL_WHITE "%d" CL_RESET "' achievements in '" CL_WHITE "%s" CL_RESET "'.\n", entries, file.c_str());
+
+	return true;
+}

+ 9 - 0
src/tool/yamlupgrade.hpp

@@ -0,0 +1,9 @@
+// Copyright (c) rAthena Dev Teams - Licensed under GNU GPL
+// For more information, see LICENCE in the main folder
+
+#ifndef YAMLUPGRADE_HPP
+#define YAMLUPGRADE_HPP
+
+#include "yaml.hpp"
+
+#endif /* YAMLUPGRADE_HPP */

+ 185 - 0
src/tool/yamlupgrade.vcxproj

@@ -0,0 +1,185 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="12.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{9115C6D1-520A-4540-B4FE-95F3C923FE2C}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>yamlupgrade</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>
+    <CharacterSet>MultiByte</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>
+    <CharacterSet>MultiByte</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>MultiByte</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>MultiByte</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <OutDir>$(SolutionDir)</OutDir>
+    <IntDir>$(SolutionDir).vs\build\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <OutDir>$(SolutionDir)</OutDir>
+    <IntDir>$(SolutionDir).vs\build\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+    <OutDir>$(SolutionDir)</OutDir>
+    <IntDir>$(SolutionDir).vs\build\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+    <OutDir>$(SolutionDir)</OutDir>
+    <IntDir>$(SolutionDir).vs\build\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>$(DefineConstants);WIN32;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;_WINSOCK_DEPRECATED_NO_WARNINGS;LIBCONFIG_STATIC;YY_USE_CONST;MINICORE;_DEBUG;_CONSOLE;_LIB;_ITERATOR_DEBUG_LEVEL=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>$(SolutionDir)3rdparty\yaml-cpp\include\</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <AdditionalDependencies>ws2_32.lib;$(SolutionDir).vs\build\common-minicore.lib;$(SolutionDir)3rdparty\zlib\lib\$(Platform)\zlib.lib;$(SolutionDir).vs\build\yaml-cpp.lib;%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>$(DefineConstants);WIN32;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;_WINSOCK_DEPRECATED_NO_WARNINGS;LIBCONFIG_STATIC;YY_USE_CONST;MINICORE;_DEBUG;_CONSOLE;_LIB;_ITERATOR_DEBUG_LEVEL=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>$(SolutionDir)3rdparty\yaml-cpp\include\</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <AdditionalDependencies>ws2_32.lib;$(SolutionDir).vs\build\common-minicore.lib;$(SolutionDir)3rdparty\zlib\lib\$(Platform)\zlib.lib;$(SolutionDir).vs\build\yaml-cpp.lib;%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>$(DefineConstants);WIN32;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;_WINSOCK_DEPRECATED_NO_WARNINGS;LIBCONFIG_STATIC;YY_USE_CONST;MINICORE;NDEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>$(SolutionDir)3rdparty\yaml-cpp\include\</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+      <AdditionalDependencies>ws2_32.lib;$(SolutionDir).vs\build\common-minicore.lib;$(SolutionDir)3rdparty\zlib\lib\$(Platform)\zlib.lib;$(SolutionDir).vs\build\yaml-cpp.lib;%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>$(DefineConstants);WIN32;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;_WINSOCK_DEPRECATED_NO_WARNINGS;LIBCONFIG_STATIC;YY_USE_CONST;MINICORE;NDEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>$(SolutionDir)3rdparty\yaml-cpp\include\</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+      <AdditionalDependencies>ws2_32.lib;$(SolutionDir).vs\build\common-minicore.lib;$(SolutionDir)3rdparty\zlib\lib\$(Platform)\zlib.lib;$(SolutionDir).vs\build\yaml-cpp.lib;%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClInclude Include="yaml.hpp" />
+    <ClInclude Include="yamlupgrade.hpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="..\common\database.cpp" />
+    <ClCompile Include="yamlupgrade.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\common\database.hpp" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+  <Target Name="AfterClean">
+    <Delete Files="$(SolutionDir)zlib.dll" ContinueOnError="true" />
+    <Delete Files="$(SolutionDir)serv.bat" ContinueOnError="true" />
+    <Delete Files="$(SolutionDir)yamlupgrade.bat" ContinueOnError="true" />
+  </Target>
+  <Target Name="AfterBuild">
+    <Copy SourceFiles="$(SolutionDir)3rdparty\zlib\lib\$(Platform)\zlib.dll" DestinationFolder="$(SolutionDir)" ContinueOnError="true" Condition="!Exists('$(SolutionDir)zlib.dll')" />
+    <Copy SourceFiles="$(SolutionDir)tools\serv.bat" DestinationFolder="$(SolutionDir)" ContinueOnError="true" Condition="!Exists('$(SolutionDir)serv.bat')" />
+    <Copy SourceFiles="$(SolutionDir)tools\yamlupgrade.bat" DestinationFolder="$(SolutionDir)" ContinueOnError="true" Condition="!Exists('$(SolutionDir)yamlupgrade.bat')" />
+  </Target>
+</Project>

+ 34 - 0
src/tool/yamlupgrade.vcxproj.filters

@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{de48fb82-cea1-4318-bd96-9aab02b5b59d}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{82d5c708-a60f-4ae1-8b0d-0aafaa8da273}</UniqueIdentifier>
+      <Extensions>h;hh;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="yaml.hpp">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="yamlupgrade.hpp">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="yamlupgrade.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="..\common\database.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\common\database.hpp">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>

+ 2 - 0
tools/yamlupgrade.bat

@@ -0,0 +1,2 @@
+@ECHO OFF
+CALL serv.bat yamlupgrade.exe YAML UPGRADE