H3c : guide des moddeurs (mods d'assets), outils NewMod/EditMod, version de reference a la publication

- Docs/Modding/FullGuides/Creating_Asset_Mods.md (anglais), explanation.lphair,
  explanation.lpmod (MODULE_DEFAULT_ENABLED).
- Tools/NewMod.ps1 (squelette ModSources/<Nom>), Tools/EditMod.ps1 (editeur avec le mod monte).
- Procedure de publication : version de reference Releases/<version> creee au build de
  distribution et livree avec les sources ; Mods/ vide au build (CHG-105).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
edujiro5972 2026-10-03 09:11:34 +02:00
parent a680f0bf19
commit 45bdb6dfb2
10 changed files with 318 additions and 2 deletions

View file

@ -142,3 +142,19 @@ git config user.name; git config user.email # edujiro5972 / 336072401+edujir
git push origin main <tag>
Get-FileHash <archive.7z> -Algorithm SHA256 # empreinte à publier dans le README
```
Liste de contrôle d'une publication (depuis H3c, `16_H3_Mods_Paquets.md` §7) :
```powershell
# 1. Version : Config\DefaultGame.ini, ProjectVersion=<annee>.<mois>.<compteur de publication> (ex. 2026.10.5)
# 2. Aucun mod monté dans le projet (il serait cuit avec le jeu)
. .\Tools\ModSource.ps1; Get-StrayMods (Get-Location) # doit être vide
# 3. Build de distribution ET version de référence, dans un dossier neuf (via cmd /c : la version serait coupée)
cmd /c '"<UE>\Build\BatchFiles\RunUAT.bat" BuildCookRun -project="<projet>\LifePlay.uproject" -platform=Win64 -clientconfig=Shipping -build -cook -iterate -stage -pak -iostore -compressed -createreleaseversion=<version> -archive -archivedirectory=D:\Game\LifePlay_Build_5.5_Shipping_V<x.y> -nodebuginfo -unattended -utf8output -nop4'
# 4. Contrôle : Releases\<version>\Windows\AssetRegistry.bin présent ; paquets identiques à ceux du build
Get-FileHash Releases\<version>\Windows\LifePlay-Windows.utoc, <build>\Windows\LifePlay\Content\Paks\LifePlay-Windows.utoc
# 5. Releases\ ne garde que la version publiée (les précédentes vers LifePlay_Backup_5.5\Releases) : l'archive des
# sources la contient (≈ 1,3 Go) ; exclure aussi les produits de cuisson des mods : -x!ModSources\*\Saved
# 6. Mod d'essai recuit contre la nouvelle version (contrôle de la chaîne) : .\Tools\BuildMod.ps1 -Name LPHairSample
# 7. README : section de la version avec le lien vers Docs/Modding/FullGuides/Creating_Asset_Mods.md
```

View file

@ -124,3 +124,7 @@ qui décide, pas autour de lui.
lourd ou binaire (`.gitignore` d'origine).
- Une version publiée est figée : tag (`v1.0`, `v1.1`), branche (`ue5.5-v1.1`), archive 7z dont
l'empreinte SHA-256 est publiée.
- Depuis H3 (mods d'assets) : le build de distribution produit la **version de référence** de la version publiée
(`Releases/<ProjectVersion>`), livrée dans l'archive des sources ; sans elle, aucun mod d'assets ne peut être cuit
pour cette version. `Mods/` doit être vide pendant le build (sources des mods dans `ModSources/`). Liste de
contrôle : `09_Commandes_Utiles.md` §7.

View file

@ -150,3 +150,19 @@ Corrections du lot :
(`FPackageName::DoesPackageExist`, avertissement).
- `BuildMod.ps1` : `cmd /c` avec guillemets imbriqués échoue depuis PowerShell (« syntaxe du nom de fichier
incorrecte ») ; d'où le fichier `.cmd`.
## 7. Documentation et publication (H3c, 2026-10-03)
- Guide des moddeurs (anglais, avec les guides d'origine de Vinfamy) :
`Docs/Modding/FullGuides/Creating_Asset_Mods.md` (fonctionnement, prérequis, création, coiffures, éditeur, cuisson et
essai, diffusion, dépannage) ; `Docs/Modding/ShortGuides/explanation.lphair` (format `.lphair`) ;
`explanation.lpmod` complété (`MODULE_DEFAULT_ENABLED`).
- Outils des moddeurs : `Tools/NewMod.ps1` (squelette `ModSources/<Nom>` : `.uplugin`, `Module/<Nom>.lpmod`,
`CREDITS.txt`, et avec `-Hairs` `Tools/mods/<Nom>.json`), `Tools/EditMod.ps1` (éditeur ouvert avec le mod monté,
remis en place à la fermeture). Essai de `NewMod.ps1` sur un mod jetable `H3cTest` (déplacé vers
`LifePlay_Backup_5.5\H3c`) : fichiers conformes, nom déjà pris refusé.
- Publication : la version de référence fait partie de chaque publication (`10_Protocole_Operations.md` §6, liste de
contrôle `09_Commandes_Utiles.md` §7). L'archive des sources V1.4 publiée ne la contient pas : les mods d'assets
sont donc possibles pour les moddeurs à partir de la publication suivante (la V1.4 reste jouable avec des mods cuits
ici contre `Releases/2026.10.4`).
- Ne pas faire de build complet destiné à la publication sans recréer la version de référence correspondante.

View file

@ -949,3 +949,4 @@ Validation L7c/L7d (2026-10-02, parc, même cadrage) : la nuit reste claire (sol
| CHG-102 | 2026-10-03 | H3a | `Source/LifePlay/LPHairstyleSubsystem.h/.cpp` ; `Content/Modules/lp_Revival/lp_Revival.lpmod` (`MODULE_DEFAULT_ENABLED: true`) | retour utilisateur : coiffure du mod présente alors que le mod est décoché. Le sous-système (H1) tenait pour actif un module absent de `GI.ModEnableds`, alors que le jeu le tient pour inactif (défaut présent en V1.4 : `lp_Revival` affiché décoché mais actif). Même règle que le jeu ; un module à clé `MODULE_DEFAULT_ENABLED: true` absent de la liste y est ajouté coché (au démarrage et après `LoadSettings`). Validé en jeu le 2026-10-03 | `git revert` du commit, recompiler |
| CHG-103 | 2026-10-03 | UI15 | `Content/UI/MainMenu.uasset`, `Content/UI/ModManager.uasset` (snapshot `LifePlay_Backup_5.5\UI15`) ; nouveaux `Source/LifePlayEditorTools/LPTitleModManagerCommandlet.h/.cpp`, `Source/LifePlay/LPModSettingsLibrary.h/.cpp`, `Docs/Migration/17_Mods_Ecran_Titre.md` ; build `LifePlay_Build_5.5_UI15b` | demande utilisateur : gestionnaire de mods dès l'écran titre, puis choix entre nouvelle partie et partie sauvegardée. Entrée dédiée sur l'écran titre (copie de « Load »), fermeture vers le menu titre avec relecture des données et enregistrement du choix (`SaveModSelection`, sans toucher à la dernière sauvegarde) ; entrée d'origine inchangée en partie. Première version (entrée d'origine rendue visible) remplacée après retour (alignement). **Validé en jeu le 2026-10-03** | `.\Tools\Restore.ps1 -Lot UI15` ; `git revert` du commit |
| CHG-104 | 2026-10-03 | H3b | nouveaux `Tools/BuildMod.ps1`, `Tools/ModSource.ps1` ; `Tools/HairPipeline.ps1` (mode `mod` : montage temporaire, `.lphair` et crédits dans `ModSources/<Nom>/Module`, `-Rebuild` déplace aussi les textures) ; `Tools/HairMaterials.py` (analyse synchrone du dossier, réutilisation des textures) ; `Tools/mods/LPHairSample.json` (`mod`) ; `Source/LifePlay/LPHairstyleSubsystem.cpp` (repli `DoesPackageExist`) ; Pocolov 05 reconstruite (précédente dans `LifePlay_Backup_5.5\H3a\Pocolov05\precedente_*`) ; build `LifePlay_Build_5.5_H3b` ; archive `D:\Game\LifePlay_Publication\Mods\LPHairSample-for-LifePlay-2026.10.4.zip` (334 473 octets, SHA-256 `8F6A45ED…CBC8`) | lot H3b : un mod d'assets en une commande ; plantage de `HairMaterials.py` dans un plugin expliqué (registre de la commandlet sans les assets du plugin) et corrigé ; build de base sans rien du mod par construction. **Validé en jeu le 2026-10-03** (16_H3_Mods_Paquets.md §6) | `git revert` du commit, recompiler |
| CHG-105 | 2026-10-03 | H3c | nouveaux `Docs/Modding/FullGuides/Creating_Asset_Mods.md`, `Docs/Modding/ShortGuides/explanation.lphair`, `Tools/NewMod.ps1`, `Tools/EditMod.ps1` ; `Docs/Modding/ShortGuides/explanation.lpmod` (`MODULE_DEFAULT_ENABLED`) ; `Docs/Migration/10_Protocole_Operations.md` §6, `09_Commandes_Utiles.md` §7 (liste de contrôle de publication), `16_H3_Mods_Paquets.md` §7 | lot H3c : guide des moddeurs en anglais, outils de création et d'édition d'un mod, version de référence intégrée à la procédure de publication (livrée dans l'archive des sources ; `Mods/` vide au build) | `git revert` du commit |

View file

@ -26,7 +26,7 @@ La migration a été reprise le 2026-09-29, après l'échec d'un premier portage
| [13_Protocole_Coiffure.md](13_Protocole_Coiffure.md) | protocole | ajouter une coiffure (FBX statique, Fab) : import, ajustement sur la tête de Bridget, matériaux, fichier `.lphair`, contrôles |
| [14_Interface_V1.4.md](14_Interface_V1.4.md) | lot | menu principal : version année.mois.publication, crédits (Vinfamy, auteur original), liens Donate et Discord, bouton Commission masqué |
| [15_Modules_Optionnels.md](15_Modules_Optionnels.md) | lot | build Shipping réduite aux modules essentiels, modules optionnels dans une archive séparée (`Tools/SplitModules.ps1`) |
| [16_H3_Mods_Paquets.md](16_H3_Mods_Paquets.md) | étude, prototype | H3 : assets apportés par les mods (plugins `Mods/`, cuisson DLC contre la version publiée) ; constats, architecture, risques, lots H3a à H3c ; §5 résultats du prototype H3a, §6 outillage H3b (`ModSources/`, `Tools/BuildMod.ps1`), validés |
| [16_H3_Mods_Paquets.md](16_H3_Mods_Paquets.md) | étude, prototype | H3 : assets apportés par les mods (plugins `Mods/`, cuisson DLC contre la version publiée) ; constats, architecture, risques, lots H3a à H3c ; §5 résultats du prototype H3a, §6 outillage H3b (`ModSources/`, `Tools/BuildMod.ps1`), validés ; §7 guide des moddeurs (`Docs/Modding/FullGuides/Creating_Asset_Mods.md`) et publication |
| [17_Mods_Ecran_Titre.md](17_Mods_Ecran_Titre.md) | lot | UI15 : gestionnaire de mods depuis l'écran titre (entrée dédiée, retour au menu titre, choix enregistré) |
| [Journal_Modifications.md](Journal_Modifications.md) | traçabilité | `CHG-001` à `CHG-057`, chacune avec son retour arrière |
| [Registre_Erreurs.md](Registre_Erreurs.md) | traçabilité | `ERR-001` à `ERR-037`, statut et lot |

View file

@ -0,0 +1,158 @@
# Creating asset mods (hairstyles, and more)
*LifePlay Revival addition (UE 5.5). Available from the first release published with its reference version (`Releases/<version>` in the full source archive), that is the release after LifePlay 2026.10.4 (V1.4).*
Text mods (scenes, actions, stats, presets...) work as before: a folder in `LifePlay/Content/Modules`, see
[Getting_Started.txt](Getting_Started.txt). This guide is about mods that bring **new 3D assets** (meshes, textures,
materials) without rebuilding the game. The first supported use is **hairstyles**.
## 1. How it works
An asset mod has two parts, installed side by side in the game folder:
```
LifePlay/Mods/<Name>/<Name>.uplugin plugin descriptor
LifePlay/Mods/<Name>/Content/Paks/Windows/<Name>LifePlay-Windows.pak/.utoc/.ucas cooked assets
LifePlay/Content/Modules/<Name>/<Name>.lpmod LifePlay module (text, as usual)
LifePlay/Content/Modules/<Name>/Hairstyles/*.lphair hairstyle declarations
LifePlay/Content/Modules/<Name>/CREDITS.txt credits and licenses
```
- The engine mounts every plugin found in `LifePlay/Mods/` at startup. Its assets live under `/<Name>/...`.
- The text module makes the mod visible in the **Mod Manager** (title screen, or Ctrl-M in game). The hairstyles are
available only while the module is enabled.
- Cooked assets are tied to a game version: a mod is built against the **reference version** of a release
(`Releases/<version>`, shipped with the full source archive) and is made for that version. Another game version
may require rebuilding the mod.
## 2. Requirements
- Windows, Unreal Engine **5.5** (Epic Games Launcher), Visual Studio 2022 is not needed for asset mods.
- The **LifePlay Revival full source archive** of the game version you target, including `Releases/<version>/`
(for example `Releases/2026.10.4/` for LifePlay 2026.10.4). Open `LifePlay.uproject` once to let the editor build
its caches.
- 7-Zip (`C:\Program Files\7-Zip\7z.exe`) to package the mod.
- Assets you are **allowed to redistribute**: CC0 or CC BY (credit the author). Store licenses such as the Fab
"Standard License" forbid redistributing the source files and are not suitable.
The scripts below are in `Tools/` and are run from a PowerShell window in the project folder. The engine path
(`D:\Game\Launcher\Engine\UE_5.5`) is set at the top of each script: adjust it if your engine is elsewhere.
## 3. Create the mod
```powershell
.\Tools\NewMod.ps1 -Name MyHairPack -Title "My Hair Pack" -Author "Me" -Hairs
```
This creates the mod sources in `ModSources/MyHairPack/`:
```
ModSources/MyHairPack/MyHairPack.uplugin content plugin
ModSources/MyHairPack/Content/ your assets (filled by the editor or the hair pipeline)
ModSources/MyHairPack/Module/MyHairPack.lpmod
ModSources/MyHairPack/Module/CREDITS.txt
Tools/mods/MyHairPack.json hair pipeline configuration (with -Hairs)
```
Mod sources stay in `ModSources/`. The tools move a mod into the project's `Mods/` folder only while they work on it
(import, cook) and move it back afterwards: a plugin left in `Mods/` would be cooked into the base game.
The name is the plugin name, the asset root (`/MyHairPack/`) and the module ID: letters, digits and underscores,
starting with a letter, unique.
## 4. Add hairstyles
Hairstyles must be skinned to the Genesis 8 skeleton used by the game characters and use the game's hair material.
The hair pipeline does this for static hairstyles distributed as FBX (for example the free Pocolov hairs on Fab):
it fits the hair to the default head, transfers skin weights from the body (head, neck, chest) so long hair follows
the character without cutting through the skin, and creates `DazHair` material instances.
1. Download the hairstyle archives (zip/rar/7z with an FBX and its textures).
2. Add one entry per hairstyle in `Tools/mods/MyHairPack.json` (see `Tools/mods/LPHairSample.json` for a complete
example):
```json
{
"name": "MyHair01",
"archive": "D:/Downloads/my-hair-01.zip",
"title": "My Hair 01",
"url": "https://source/of/the/asset",
"author": "Original author",
"license": "CC BY 4.0",
"sex": "F",
"mesh": "auto", "head": "auto", "cap_slots": "auto", "diffuse": "auto", "strands_opacity": "auto",
"cap_opacity": "white",
"thicken": 1
}
```
3. Inspect, read the report, fix the JSON if a guess is wrong, then apply:
```powershell
.\Tools\HairPipeline.ps1 -Config Tools\mods\MyHairPack.json -Step Inspect
.\Tools\HairPipeline.ps1 -Config Tools\mods\MyHairPack.json -Step Apply
```
`Apply` writes the assets to `ModSources/MyHairPack/Content/Hairs/`, one `.lphair` per hairstyle in
`Module/Hairstyles/` and one line per hairstyle in `Module/CREDITS.txt`. To redo a hairstyle: `-Step Inspect` then
`-Step Apply -Rebuild -Only MyHair01` (the previous version is moved to the backup folder, never deleted).
Fitting options per hairstyle (`margin`, `scale`, `offset_z`, `offset_y`, `skin`, `gap`) and the detailed protocol
are described (in French) in `Docs/Migration/13_Protocole_Coiffure.md`.
A `.lphair` file can also be written by hand for a hairstyle made another way (see
[explanation.lphair](../ShortGuides/explanation.lphair)):
```
HAIRSTYLE: /MyHairPack/Hairs/MyHair01.MyHair01
SEX: F
DAZ: true
```
## 5. Edit the mod in the editor
```powershell
.\Tools\EditMod.ps1 -Name MyHairPack
```
Opens the editor with the mod mounted: its assets appear in the Content Browser under **MyHairPack Content**
(`/MyHairPack/`). Close the editor to move the mod back to `ModSources/`. Keep every asset of the mod inside
`/MyHairPack/`; referencing game assets (skeletons, the `DazHair` material...) is fine, modifying them is not
(changes to game assets are not shipped by the mod).
## 6. Build and test
```powershell
.\Tools\BuildMod.ps1 -Name MyHairPack -Install <test game folder>\Windows
```
`BuildMod.ps1`:
1. checks the plugin, the module and the reference version (`Releases/<version>`, version read from
`Config/DefaultGame.ini`, or `-Version`);
2. cooks only the mod against the reference version (log in `Saved/Logs/portage/mods/`);
3. checks that the cooked container holds nothing outside `Mods/MyHairPack/` (no game asset is shipped);
4. builds `MyHairPack-for-LifePlay-<version>.zip` (with an install README) in `D:\Game\LifePlay_Publication\Mods`
(`-Out` to change it);
5. with `-Install`, copies the mod into a test game (the folder that contains `LifePlay.exe`).
Then start the game, open **Mod Manager** on the title screen, enable the mod, close the manager and start or load a
game: the new hairstyles are at the end of the hairstyle list (for the sex declared in `SEX`).
## 7. Distribute
Share the zip. Players extract it into the game folder (the one that contains `LifePlay.exe`), merging the `LifePlay`
folder, then enable the mod in the Mod Manager. To uninstall, they delete `LifePlay/Mods/<Name>` and
`LifePlay/Content/Modules/<Name>`. Always say which LifePlay version the mod was built for, and keep the credits of
every asset in `CREDITS.txt`.
## 8. Troubleshooting
| Symptom | Cause, fix |
|---|---|
| The mod is not listed in the Mod Manager | `LifePlay/Content/Modules/<Name>/<Name>.lpmod` missing, or `MODULE_UNIQUEID` different from the folder name |
| The mod is listed but the hairstyle does not appear | module not enabled; `HAIRSTYLE` path wrong (`/<Name>/Hairs/<Asset>.<Asset>`); `LifePlay/Mods/<Name>/Content/Paks/Windows` missing; wrong `SEX` |
| `Mods\<Name> existe deja` when running a tool | a previous run was interrupted: move `Mods/<Name>` back to `ModSources/<Name>` by hand |
| `Version de reference absente` | the source archive lacks `Releases/<version>`: use the source archive of the targeted game version |
| `Autres plugins dans Mods\` | another mod is still mounted: move it back to `ModSources/` |
| The hairstyle cuts through the shoulders or floats | adjust `gap`, `margin`, `offset_z`, `offset_y` and rebuild the hairstyle |

View file

@ -0,0 +1,18 @@
LifePlay Revival addition. Lphair files declare hairstyles, beards and body hair. Put them anywhere inside your mod folder (for example Content\Modules\<your mod>\Hairstyles\). They are read at startup; the hairstyles of a mod are available only while the mod is enabled in the Mod Manager.
HAIRSTYLE: /MyHairPack/Hairs/MyHair01.MyHair01 // full path of a skeletal mesh skinned to the Genesis 8 skeleton (an asset of the game, or of an asset mod: see Docs/Modding/FullGuides/Creating_Asset_Mods.md), or NONE for "no hair"
SEX: F // F or M (default F): which characters can use it
DAZ: true // true for hairstyles made for the Daz Genesis 8 characters (all current ones)
FIT_MORPH: MorphName 0.5 // optional: morph target applied to the hair, with its value, to fit the head
The // comments at the end of the lines above are explanations only: in a real file, a comment must be on its own line.
Several hairstyles can be declared in one file: each HAIRSTYLE line starts a new hairstyle, the SEX, DAZ and FIT_MORPH lines that follow apply to it. Lines starting with // are comments.
Beards and body hair are textures painted on the skin, listed by name (the texture must exist in the game folder used by the game for that list):
FACIAL_HAIR: Facial_Hair__1_ // beard (male)
BODY_HAIR_M: JPBH78-TorsoNG-01 // male body hair
BODY_HAIR_F: Pubes01 // female body hair
The base game list is Content\Modules\vin_Base\Hairstyles\vin_Base.lphair (MODE: BASE): do not copy that line into your own files.

View file

@ -9,4 +9,6 @@ MODULE_NAME: Official Netorare Module
MODULE_AUTHOR: Vinfamy
MODULE_LINK: www.loverslab.com
MODULE_DESCRIPTION: Netorare, cuckoldry, being cheated on - aka the most divisive fetish on the internet
MODULE_REQUIREMENTS: vin_VanillaRealistic // unique IDs of the prerequisite mods, without all these mods enabled, this mod cannot be enabled.
MODULE_REQUIREMENTS: vin_VanillaRealistic // unique IDs of the prerequisite mods, without all these mods enabled, this mod cannot be enabled.
LifePlay Revival addition:
MODULE_DEFAULT_ENABLED: true // optional: the mod is enabled the first time the game finds it (otherwise a new mod starts disabled until the player ticks it in the Mod Manager). Used by lp_Revival, shipped with the game.

34
Tools/EditMod.ps1 Normal file
View file

@ -0,0 +1,34 @@
<#
.SYNOPSIS
Ouvre l'editeur avec un mod d'assets monte (lot H3c, Docs/Modding/FullGuides/Creating_Asset_Mods.md).
.DESCRIPTION
Monte ModSources\<Nom> dans Mods\<Nom> (Tools/ModSource.ps1), lance l'editeur et attend sa fermeture, puis remet le
mod dans ModSources\<Nom> (meme si l'editeur plante). Les assets du mod apparaissent dans le navigateur de contenu
sous "<Nom> Content" (chemin /<Nom>/) ; un editeur deja ouvert ne voit pas le mod : le fermer d'abord.
.EXAMPLE
.\Tools\EditMod.ps1 -Name LPHairSample
#>
param(
[Parameter(Mandatory)] [string] $Name
)
$ErrorActionPreference = 'Stop'
$Root = Split-Path $PSScriptRoot -Parent
. (Join-Path $PSScriptRoot 'ModSource.ps1')
$Editor = 'D:\Game\Launcher\Engine\UE_5.5\Engine\Binaries\Win64\UnrealEditor.exe'
if (Get-Process UnrealEditor -ErrorAction SilentlyContinue) {
throw "Un editeur est deja ouvert : le fermer (il ne verrait pas le mod), puis relancer"
}
$stray = Get-StrayMods $Root
if ($stray) { throw "Autres plugins dans Mods\ ($($stray -join ', ')) : les remettre dans ModSources d'abord" }
Mount-ModSource $Root $Name | Out-Null
try {
Write-Host "Editeur ouvert avec /$Name/ ; le mod sera remis dans ModSources a sa fermeture."
Start-Process -FilePath $Editor -ArgumentList "`"$Root\LifePlay.uproject`"" -Wait
}
finally {
Dismount-ModSource $Root $Name
}

67
Tools/NewMod.ps1 Normal file
View file

@ -0,0 +1,67 @@
<#
.SYNOPSIS
Cree le squelette d'un mod d'assets (lot H3c, Docs/Modding/FullGuides/Creating_Asset_Mods.md).
.DESCRIPTION
Cree ModSources\<Nom>\ :
<Nom>.uplugin plugin de contenu (assets cuits a part du jeu)
Content\ assets du mod (a remplir dans l'editeur : Tools/EditMod.ps1)
Module\<Nom>.lpmod module LifePlay (MODULE_UNIQUEID = <Nom>, active depuis le gestionnaire de mods)
Module\CREDITS.txt credits et licences des assets
et, avec -Hairs, Tools\mods\<Nom>.json (configuration de Tools/HairPipeline.ps1, liste de coiffures vide).
Refuse un nom deja pris (sources, module du jeu ou plugin).
.EXAMPLE
.\Tools\NewMod.ps1 -Name MyHairPack -Title "My Hair Pack" -Author "Me" -Hairs
#>
param(
[Parameter(Mandatory)] [ValidatePattern('^[A-Za-z][A-Za-z0-9_]{2,40}$')] [string] $Name,
[Parameter(Mandatory)] [string] $Title,
[Parameter(Mandatory)] [string] $Author,
[string] $Description = '',
[string] $Link = '',
[switch] $Hairs
)
$ErrorActionPreference = 'Stop'
$Root = Split-Path $PSScriptRoot -Parent
$src = Join-Path $Root "ModSources\$Name"
foreach ($taken in $src, (Join-Path $Root "Mods\$Name"), (Join-Path $Root "Content\Modules\$Name"), (Join-Path $Root "Plugins\$Name")) {
if (Test-Path $taken) { throw "Nom deja pris : $taken" }
}
$utf8 = New-Object Text.UTF8Encoding $false
New-Item -ItemType Directory -Force (Join-Path $src 'Content'), (Join-Path $src 'Module') | Out-Null
$plugin = [ordered]@{
FileVersion = 3; Version = 1; VersionName = '1.0'
FriendlyName = $Title
Description = $(if ($Description) { $Description } else { "LifePlay mod: $Title" })
Category = 'LifePlay Mods'; CreatedBy = $Author
CanContainContent = $true; IsBetaVersion = $false; Installed = $false
}
[IO.File]::WriteAllText((Join-Path $src "$Name.uplugin"), ($plugin | ConvertTo-Json) + "`r`n", $utf8)
$lpmod = @(
"MODULE_UNIQUEID: $Name",
"MODULE_NAME: $Title",
"MODULE_AUTHOR: $Author",
"MODULE_LINK: $Link",
"MODULE_DESCRIPTION: $(if ($Description) { $Description } else { $Title })",
'MODULE_REQUIREMENTS: vin_Base')
[IO.File]::WriteAllText((Join-Path $src "Module\$Name.lpmod"), ($lpmod -join "`r`n") + "`r`n", $utf8)
[IO.File]::WriteAllText((Join-Path $src 'Module\CREDITS.txt'), "Credits and licenses of the assets in $Title (one line per asset: title, author, license, source URL, changes).`r`n", $utf8)
if ($Hairs) {
$cfgPath = Join-Path $Root "Tools\mods\$Name.json"
if (Test-Path $cfgPath) { throw "$cfgPath existe deja" }
$cfg = [ordered]@{
mod = $Name; module = $Name; folder = "/$Name/Hairs"
backup = "D:/Game/LifePlay_Backup_5.5/mods/$Name"
hairs = @()
}
New-Item -ItemType Directory -Force (Split-Path $cfgPath -Parent) | Out-Null
[IO.File]::WriteAllText($cfgPath, ($cfg | ConvertTo-Json -Depth 4) + "`r`n", $utf8)
Write-Host "Configuration des coiffures : $cfgPath (ajouter les entrees de 'hairs', voir Tools/mods/LPHairSample.json)"
}
Write-Host "Mod cree : $src"
Write-Host "Suite : .\Tools\EditMod.ps1 -Name $Name (assets dans l'editeur), puis .\Tools\BuildMod.ps1 -Name $Name"