add random name generators for goblin and under markets

This commit is contained in:
FaceDeer 2023-01-08 23:06:18 -07:00
parent c7730147b4
commit 5250151f92
8 changed files with 258 additions and 3 deletions

133
autotranslate.py Normal file
View File

@ -0,0 +1,133 @@
# A quick-and-dirty script to run untranslated text through Google Translate's API.
# The result will likely include comical errors a native speaker will laugh at you for
# or that will puzzle them, and some manual correction of escaped codes such as @1 and @= may be
# required, but hopefully it will serve as a start to something useful
# Copyright (C) 2020 FaceDeer
# LGPLv2.1+
# See https://github.com/minetest-tools/update_translations for
# potential future updates to this script.
from googletrans import Translator, LANGUAGES
import os, re, shutil
pattern_tr_filename = re.compile(r'\.tr$')
pattern_tr_id = re.compile(r'\.([^.]*)\.tr$')
pattern_line_to_translate = re.compile(r'^([^#].*[^@])=$') #finds lines that don't have a translation
translator = Translator()
def translate(tr_filename):
lang_id = pattern_tr_id.search(tr_filename)
if not lang_id:
print("Could not find language ID in tr filename " + tr_filename)
return
lang_id = lang_id.group(1)
if not lang_id in LANGUAGES:
print("language ID " + lang_id + " is not supported by Google Translate's API")
return
lines_to_translate = [] # this list of strings will ultimately be sent to Google for translation
with open(tr_filename, "r", encoding="utf-8") as tr_file_handle:
for line in tr_file_handle:
# Look for lines that end in "=", ie, that don't have a valid translation added to them
line_lacking_translation = pattern_line_to_translate.search(line)
if line_lacking_translation:
#break the line up at @n markers, this is not ideal for Google
#as it may remove some context but it's necessary to allow the
#@n markers to be preserved in the output later
lines_to_translate = lines_to_translate + line_lacking_translation.group(1).split("@n")
# Remove duplicates, and the empty string (a common artefact of splitting)
line_set = set(lines_to_translate)
line_set.discard("")
lines_to_translate = list(line_set)
# Only do more work if there are lines in need of translation
if lines_to_translate:
print("Calling Google API for " + tr_filename)
output = translator.translate(lines_to_translate, src="en", dest=lang_id)
#convert the output translations into a dictionary for easy substitution later
translation_dictionary = dict()
for out_line in output:
#Google's API sometimes seems to fail to translate a line for no apparent reason
#Don't put them in the dictionary, we can leave those untranslated and maybe try again
if out_line.origin != out_line.text:
translation_dictionary[out_line.origin] = out_line.text
translation_dictionary["@n"] = "@n" #These are to be left unchanged
tr_file_handle.seek(0)
with open(tr_filename + ".temp", "w", encoding="utf-8") as tr_file_new:
for line in tr_file_handle:
line_lacking_translation = pattern_line_to_translate.search(line)
if line_lacking_translation:
line = line.rstrip('\n') #remove trailing newline so we can add the translated string to the same line
line_split = re.split("(@n)", line[:-1]) #slice to leave off the "=" that's the last character of the line
translated_line = ""
#After splitting the line up on @n again, as was done before, we should have
#line segments that match the strings that were sent to Google.
for line_piece in line_split:
if line_piece in translation_dictionary:
translated_line = translated_line + translation_dictionary[line_piece]
else:
print("Google returned string unchanged in file " + tr_filename + ":")
print(line_piece)
translated_line = None
break
if translated_line:
tr_file_new.write("#WARNING: AUTOTRANSLATED BY GOOGLE TRANSLATE\n")
tr_file_new.write(line)
tr_file_new.write(translated_line)
tr_file_new.write("\n")
else:
tr_file_new.write(line)
tr_file_new.write("\n")
else:
tr_file_new.write(line)
shutil.move(tr_filename + ".temp", tr_filename) # Overwrite the original file with the new one
pattern_domain = re.compile(r'^# textdomain: (.+)$')
def create_tr_files_from_template(folder, lang_id):
if not lang_id in LANGUAGES:
print("language ID " + lang_id + " is not supported by Google Translate's API")
return
for root, dirs, files in os.walk(folder):
if root == "." or os.path.split(root)[1] == "locale":
for name in files:
if name == "template.txt":
template_filename = os.path.join(root,name)
with open(template_filename, "r", encoding="utf-8") as template_file:
first_line = template_file.readline()
domain = pattern_domain.search(first_line)
if domain:
translation_filename = domain.group(1) + "." + lang_id + ".tr"
translation_filename = os.path.join(root,translation_filename)
if not os.path.isfile(translation_filename):
print("Copying template.txt to " + translation_filename)
shutil.copy(template_filename, translation_filename)
else:
print(translation_filename + " already exists")
#If there are already .tr files in /locale, returns a list of their names
def get_existing_tr_files(folder):
out = []
for root, dirs, files in os.walk(folder):
for name in files:
if pattern_tr_filename.search(name):
out.append(os.path.join(root,name))
return out
#create_tr_files_from_template(".", "de")
#create_tr_files_from_template(".", "it")
tr_files = get_existing_tr_files(".")
for tr_file in tr_files:
translate(tr_file)

12
goblin_markets.cfg Normal file
View File

@ -0,0 +1,12 @@
name "goblin_markets" {
customGroupA = "Ach Adz Ak Ark Az Balg Bilg Blid Blig Blok Blot Bolg Boor Bot Bug Burk Chu Dokh Drik Driz Drub Duf Flug Gaw Gad Gag Gah Gak Gar Gat Gaz Ghag Ghak Ghor Git Glag Glak Glat Glig Gliz Glok Gnat Gog Grak Grat Guk Hig Irk Kak Kav Khad Krig Lag Lak Lig Likk Loz Luk Lun Mak Maz Miz Mog Mub Mur Nad Nag Naz Nig Nikk Nogg Nok Nukk Nur Pog Rag Rak Rat Rok Ronk Rot Shrig Shuk Skrag Skug Slai Slig Slog Sna Snag Snark Snat Snig Snik Snit Sog Spik Stogg Tog Unk Urf Vark Vog Yad Yagg Yak Yark Yarp Yig Yip Zat Zib Zit Ziz Zob Zord"
customGroupB = "ach adz ak ark awg az balg bilg blid blig blok blot bolg bot bug burk bus dokh drik driz duf ffy flug g ga gad gag gah gak gar gat gaz ghag ghak git glag glak glat glig gliz glok gnat gog grak grat gub guk hig irk kak khad krig lag lak lig likk loz luk mak maz miz mub murch nad nag naz nig nikk nogg nok nukk og plus rag rak rat rkus rok shrig shuk skrag skug slai slig slog sna snag snark snat snig snik snit sog spik stogg thus tog un urf us vark yad yagg yak yark yarp yig yip zat zib zit ziz"
customGroupC = "Exchange Shop Post Dump Stash Emporium Outlet Stall Stand Lot Stockpile Stock Lode Cache Pile Wares Hoard Heap"
syllablesPost = "ah, ay, e, ee, gah, ghy, y, ya"
rules = "%50$A$90B$10B's_$C, %35$A$p's_$C, %15$A$B$p's_$C"
}

View File

@ -42,6 +42,13 @@ Gold coins can be deposited and withdrawn from markets that accept them as curre
Right-click on this to open the market interface.=Кликните правой кнопкой мыши на это, чтобы открыть рыночный интерфейс.
### mapgen_dungeon_markets.lua ###
#WARNING: AUTOTRANSLATED BY GOOGLE TRANSLATE
A Goblin Exchange=Обмен гоблинов
#WARNING: AUTOTRANSLATED BY GOOGLE TRANSLATE
An Undermarket=Подрынок
### village_markets.lua ###
At this time of day the King's Market is closed.=В это время дня Королевский рынок закрыт.

View File

@ -41,6 +41,11 @@ Gold coins can be deposited and withdrawn from markets that accept them as curre
Right-click on this to open the market interface.=
### mapgen_dungeon_markets.lua ###
A Goblin Exchange=
An Undermarket=
### village_markets.lua ###
At this time of day the King's Market is closed.=

View File

@ -1,5 +1,8 @@
local goblin_enabled = minetest.settings:get_bool("commoditymarket_enable_goblin_market")
local under_enabled = minetest.settings:get_bool("commoditymarket_enable_under_market")
local S = commoditymarket_fantasy.S
local modpath = minetest.get_modpath(minetest.get_current_modname())
local goblin_enabled = minetest.settings:get_bool("commoditymarket_enable_goblin_market", true)
local under_enabled = minetest.settings:get_bool("commoditymarket_enable_under_market", true)
local goblin_prob = tonumber(minetest.settings:get("commoditymarket_goblin_market_dungeon_prob")) or 0.25
local under_prob = tonumber(minetest.settings:get("commoditymarket_under_market_dungeon_prob")) or 0.1
@ -25,7 +28,61 @@ if not (gen_goblin or gen_under) then
return
end
-------------------------------------------------------------
-- Names and waypoints
local named_waypoints_modpath = minetest.get_modpath("named_waypoints")
local name_generator_modpath = minetest.get_modpath("name_generator")
local goblin_named = minetest.settings:get_bool("commoditymarket_name_goblin_markets", true) and named_waypoints_modpath
local under_named = minetest.settings:get_bool("commoditymarket_name_under_markets", true) and named_waypoints_modpath
local item_required = nil
if minetest.settings:get_bool("commoditymarket_hud_requires_item", true) then
item_required = minetest.settings:get("commoditymarket_hud_item_required")
if item_required == nil or item_required == "" then
item_required = "map:mapping_kit"
end
end
if goblin_named then
local goblin_waypoint_def = {
default_name = S("A Goblin Exchange"),
default_color = 0x00A86B, -- jade green
discovery_volume_radius = 5,
visibility_requires_item = item_required,
}
if minetest.settings:get_bool("commoditymarket_show_goblin_markets_in_hud", true) then
goblin_waypoint_def.visibility_volume_radius = tonumber(minetest.settings:get("commoditymarket_hud_visibility_range")) or 250
goblin_waypoint_def.on_discovery = named_waypoints.default_discovery_popup
end
named_waypoints.register_named_waypoints("goblin_markets", goblin_waypoint_def)
if name_generator_modpath then
name_generator.parse_lines(io.lines(modpath.."/goblin_markets.cfg"))
end
end
if under_named then
local under_waypoint_def = {
default_name = S("An Undermarket"),
default_color = 0xB33000, -- darkened orangered
discovery_volume_radius = 5,
visibility_requires_item = item_required,
}
if minetest.settings:get_bool("commoditymarket_show_under_markets_in_hud", true) then
under_waypoint_def.visibility_volume_radius = tonumber(minetest.settings:get("commoditymarket_hud_visibility_range")) or 250
under_waypoint_def.on_discovery = named_waypoints.default_discovery_popup
end
named_waypoints.register_named_waypoints("under_markets", under_waypoint_def)
if name_generator_modpath then
name_generator.parse_lines(io.lines(modpath.."/under_markets.cfg"))
end
end
-------------------------------------------------------
-- The following is shamelessly copied from dungeon_loot and tweaked for placing markets instead of chests
--Licensed under the MIT License (MIT) Copyright (C) 2017 sfan5
@ -125,6 +182,14 @@ minetest.register_on_generated(function(minp, maxp, blockseed)
if minetest.get_node(under_loc).name == "air"
and is_wall(vector.subtract(under_loc, {x=0, y=1, z=0})) then
minetest.add_node(under_loc, {name="commoditymarket:under_market"})
local name = nil
if under_named then
if name_generator_modpath then
name = name_generator.generate("under_markets")
end
named_waypoints.add_waypoint("under_markets", under_loc, {name=name})
end
end
end
@ -148,6 +213,14 @@ minetest.register_on_generated(function(minp, maxp, blockseed)
-- make it face inwards to the room
local facedir = minetest.dir_to_facedir(vector.multiply(wall.facing, -1))
minetest.add_node(marketpos, {name = "commoditymarket:goblin_market", param2 = facedir})
local name = nil
if goblin_named then
if name_generator_modpath then
name = name_generator.generate("goblin_markets")
end
named_waypoints.add_waypoint("goblin_markets", marketpos, {name=name})
end
end
end
end)

View File

@ -1,4 +1,4 @@
name = commoditymarket_fantasy
description = Adds a number of fantasy-themed marketplaces
depends = commoditymarket
optional_depends = doc, lorebooks, default, mcl_core, mcl_sounds, mcl_chests, mesecons_wires
optional_depends = doc, lorebooks, default, mcl_core, mcl_sounds, mcl_chests, mesecons_wires, named_waypoints, name_generator

View File

@ -22,3 +22,15 @@ commoditymarket_goblin_market_dungeon_min (Lower y limit of goblin markets) int
commoditymarket_under_market_dungeon_prob (Undermarket probability per dungeon mapblock) float 0.1 0 1
commoditymarket_under_market_dungeon_max (Upper y limit of undermarkets) int -500
commoditymarket_under_market_dungeon_min (Lower y limit of undermarkets) int -31000
[Dungeon market HUD markers]
commoditymarket_name_goblin_markets (Give names to goblin markets) bool true
commoditymarket_name_under_markets (Give names to undermarkets) bool true
commoditymarket_show_goblin_markets_in_hud (Show Goblin markets in HUD) bool true
commoditymarket_show_under_markets_in_hud (Show Undermarkets in HUD) bool true
commoditymarket_hud_requires_item (Require an item to view waypoints) bool true
#Players can still discover the locations of markets without this, but waypoints
#will only be visible in their hud if they have this item in their inventory. You can also
#specify "group:groupname" here. Leave it blank to default to map:mapping_kit.
commoditymarket_hud_item_required (Specify the item or group required) string map:mapping_kit
commoditymarket_hud_visibility_range (Dungeon market HUD visibility range) int 250

13
under_markets.cfg Normal file
View File

@ -0,0 +1,13 @@
name "under_markets" {
customGroupA = "Ach Akk Ash Azt Bahor Bar Bas Brax Charn Dak Hrax Lach Lazt Mat Nam Nazt Ralk Rhast Sark Slarv Tash Thak Thalur Thalk Vach Vap Dek Ech Fesh Gek Hrek Lech Met Ner Ter Blik Gith Igm Inax Irsch Kir Lis Lisk Lith Nilv Nirr Tlizit Bor Chon Goch Gor Goth Hoth Khor Kos Loch Lok Loth Moch Moth Noc Och Oth Rolk Roth Sot Soth Vrok Dun Gur Hun Luth Muth Nur Rutt Sut Sutt Szut Tur Urt Utuk Uzt Krych Nyth Slyth Gaan Xaas Boak Ruaak Yalm Haerx Iex Draum Gaur Glaur Rauk Saur Duum Nuur Ruun"
customGroupB = "ach akk ash azt bahor bar bas brax charn dak hrax lach lazt mat nam nazt ralk rhast sark slarv tash thak thalur thalk vach vap dek ech fesh gek hrek lech met ner ter blik gith igm inax irsch kir lis lisk lith nilv nirr tlizit bor chon goch gor goth hoth khor kos loch lok loth moch moth noc och oth rolk roth sot soth vrok dun gur hun luth muth nur rutt sut sutt szut tur urt utuk uzt krych nyth slyth gaan xaas boak ruaak yalm haerx iex draum gaur glaur rauk saur duum nuur ruun"
customGroupC = "Ruin Exchange Well Arch Altar Crucible Temple House Shrine Font Prison Cell Compact Station Bond Pact Contract Mise"
phonemesVocals = "u u u o o i i a a e"
phonemesConsonants = "z y v r l j"
rules = "The_$C_of_$A$v$c$B, The_$C_of_$A$c$v$B, The_$C_of_$A-$v$c$B, The_$C_of_$A-$c$v$B, $A$v$c$B's_$C, $A$c$v$B's_$C, $A-$v$c$B's_$C, $A-$c$v$B's_$C"
}