All Things WinBatch > WinBatch
Read data from an XML file.
mlburgoon71:
I am trying to write a program to help me with modding some games I play. I am struggling with figuring out the best way to read in values from the default .xml file, provided by the game, so I can change and manipulate them. small snippet Example below of the xml file.
But what I want to be able to do is pull the value like so..
eg = (some command) (/entity_classes/entity_class(@name="zombieNurseFeral")/property(@name="ExperienceGain")
how is this possible to do?? been looking at the wbOmnibus extender and it sounded promising. but having issues getting it to work. I am hoping I don't have to create my own parser to do this.....
excerpt from the game .xml.
<entity_classes>
<entity_class name="zombieNurse" extends="zombieTemplateMale">
<property name="Tags" value="entity,zombie,walker"/>
<property name="Mesh" value="#Entities/Zombies?Prefabs/ZNurse.prefab"/>
<property name="SoundRandom" value="Enemies/Base_Zombie_Female/zombiefemaleroam"/>
<property name="SoundAlert" value="Enemies/Base_Zombie_Female/zombiefemalealert"/>
<property name="SoundAttack" value="Enemies/Base_Zombie_Female/zombiefemaleattack"/>
<property name="SoundHurt" value="Enemies/Base_Zombie_Female/zombiefemalepain"/>
<property name="SoundDeath" value="Enemies/Base_Zombie_Female/zombiefemaledeath"/>
<property name="SoundSense" value="Enemies/Base_Zombie_Female/zombiefemalesense"/>
<property name="AvatarController" value="AvatarZombie01Controller"/>
<property name="ModelType" value="Standard"/>
<property name="WalkType" value="7"/>
<property name="Mass" value="130"/>
<property name="RootMotion" value="true"/>
<property name="HasDeathAnim" value="true"/>
<property name="AIPathCostScale" value=".5, .65"/>
<property name="DanceType" value="2" />
<!-- Gameplay zombieNurse -->
<property name="MoveSpeedAggro" value="0.3, 1.35"/> <!-- slim, regular -->
<property name="HandItem" value="meleeHandZombie01"/>
<effect_group name="Base Effects">
<passive_effect name="HealthMax" operation="base_set" value="125"/>
</effect_group>
</entity_class>
<entity_class name="zombieNurseFeral" extends="zombieNurse">
<property name="Tags" value="entity,zombie,walker,feral"/>
<property name="Mesh" value="#Entities/Zombies?Prefabs/ZNurseFeral.prefab"/>
<!-- Gameplay zombieNurseFeral -->
<property name="DismemberMultiplierHead" value=".7"/><property name="DismemberMultiplierArms" value=".7"/><property name="DismemberMultiplierLegs" value=".7"/><!-- Feral -->
<property name="PainResistPerHit" value=".7"/><!-- Feral -->
<property name="MoveSpeedAggro" value="0.6, 1.45"/> <!-- slim, feral -->
<property name="JumpMaxDistance" value="4.6, 5"/>
<property name="HandItem" value="meleeHandZombieFeral"/>
<property name="ExperienceGain" value="750"/><!-- XP grunt feral -->
<property name="LootDropProb" value=".03"/> <!-- Feral -->
<effect_group name="Base Effects">
<passive_effect name="HealthMax" operation="base_set" value="237"/>
<!--<passive_effect name="EntityDamage" operation="perc_add" value="0"/>--> <!-- Feral damage -->
</effect_group>
</entity_class>
<entity_class name="zombieNurseRadiated" extends="zombieNurseFeral">
<property name="Tags" value="entity,zombie,walker,feral,radiated"/>
<property name="Mesh" value="#Entities/Zombies?Prefabs/ZNurseRadiated.prefab"/>
<!-- Gameplay zombieNurseRadiated -->
<property name="DismemberMultiplierHead" value=".4"/><property name="DismemberMultiplierArms" value=".4"/><property name="DismemberMultiplierLegs" value=".4"/><!-- Radiated -->
<property name="PainResistPerHit" value=".9"/><!-- Radiated -->
<property name="ExperienceGain" value="1200"/><!-- XP grunt radiated -->
<effect_group name="Base Effects">
<passive_effect name="HealthMax" operation="base_set" value="451"/>
<!--<passive_effect name="EntityDamage" operation="perc_add" value="0"/>--><!-- Feral damage -->
<triggered_effect trigger="onOtherDamagedSelf" action="ModifyCVar" target="self" cvar="RadiatedRegenAmount" operation="set" value="4"/>
<triggered_effect trigger="onOtherDamagedSelf" action="AddBuff" target="self" buff="buffRadiatedRegen"/>
</effect_group>
</entity_class>
</entity_classes>
stanl:
I'm sure Jim would like to hear more specifics about issues you encountered using his Extender. I would think you could write your own parser using the WB CLR and .net assemblies. But you are also interested in changing 'values' [if I read your initial post correctly] which would imply an xml editor of sorts. Thanks for providing the sample .xml - can take a stab at it.
[EDIT]
from Tech DB
https://techsupt.winbatch.com/webcgi/webbatch.exe?techsupt/nftechsupt.web+WinBatch/dotNet/System_XML+ReadXmlFile~Sample.txt
JTaylor:
I will try to take a look soon. If you are wanting to change your XML, my extender is not a good choice though. Perhaps the following will help provide a solution.
Jim
--- Code: Winbatch ---
;https://learn.microsoft.com/en-us/previous-versions/windows/desktop/ms754585(v=vs.85)
#DefineFunction Load_MSXMLData(xtxt)
MSXML = ObjectOpen("MSXML2.DOMDocument.6.0")
MSXML.Async = "False"
MSXML.preserveWhiteSpace = "False"
MSXML.validateOnParse = "False"
MSXML.resolveExternals = "False"
Loaded = MSXML.LoadXML(xtxt)
If !Loaded Then
If !IsDefined(stxt) Then stxt = ""
xPE = MSXML.parseError
strErrText = "Your XML Document failed to load due the following error.":@CRLF:"Error #: ":xPE.errorCode:": ":xPE.reason:"Line #: ":xPE.Line:@CRLF:"Line Position: ":xPE.linepos:@CRLF:"Position In File: ":xPE.filepos:@CRLF:"Source Text: ":xPE.srcText:@CRLF:"Document URL: ":xPE.url
clipput(strErrText)
Message("Error",strErrText)
xtxt = ""
Return
End If
; Get root of document
XML_Root = MSXML.documentElement
Return XML_Root
#EndFunction
xtxt = FileGet("xml_test.xml")
XML_Root = Load_MSXMLData(xtxt)
loaded_txt = XML_Root.xml
Message("XML",loaded_txt)
td:
The .Net System.Xml namespace with WinBatch CLR hosting should be able to perform what the OP requires. The C# examples on the page indicated by the MSFT link below provide a good starting point for a WIL script.
https://learn.microsoft.com/en-us/dotnet/api/system.xml.xmldocument?view=netframework-4.8.1
[edit] Jim's COM Automation suggestion is also worth checking out. It can do most/all of what is needed and is likely easier to understand unless you are already familiar with dotNet script in WinBatch. You can dump the progid "MSXML2.DOMDocument.6.0" into The WIL Typeviewer to get some idea of the available properties and methods.
stanl:
Here is some quickie PS code to parse the xml data OP provided with output attached. My thoughts were to quickly collect the properties, queue up any changes then just write back to the xml file with replace functions. Maybe a bit simplistic. Oh, and WB can easily call the PS code. I suspect as Jim suggested that MSXML and xpath could accomplish the same in pure WB.
--- Code: ---
#parse xml into bar-delimited text for properties
#change xml and txt output as needed
$file = "c:\temp\zombies.txt"
$data = "class|property|value" | out-file $file
[xml] $info = Get-Content -Path C:\temp\zombies.xml
$base = $info.entity_classes.entity_class
ForEach ($class in $base)
{
$name = $class.name
$props = $class.property
ForEach ($prop in $props)
{
$data = $name + "|" +$prop.name + "|" + $prop.value
$data | Out-File $file -Append
}
}
Exit
--- End code ---
Navigation
[0] Message Index
[#] Next page
Go to full version