90
90
import mekhq .campaign .personnel .ranks .RankSystem ;
91
91
import mekhq .campaign .personnel .ranks .RankValidator ;
92
92
import mekhq .campaign .personnel .ranks .Ranks ;
93
+ import mekhq .campaign .personnel .skills .Attributes ;
93
94
import mekhq .campaign .personnel .skills .Skill ;
94
95
import mekhq .campaign .personnel .skills .SkillType ;
95
96
import mekhq .campaign .personnel .skills .Skills ;
97
+ import mekhq .campaign .personnel .skills .enums .SkillAttribute ;
96
98
import mekhq .campaign .randomEvents .personalities .enums .Aggression ;
97
99
import mekhq .campaign .randomEvents .personalities .enums .Ambition ;
98
100
import mekhq .campaign .randomEvents .personalities .enums .Greed ;
@@ -199,6 +201,7 @@ public class Person {
199
201
private int wealth ;
200
202
private int reputation ;
201
203
private int unlucky ;
204
+ private Attributes atowAttributes ;
202
205
203
206
private PersonnelStatus status ;
204
207
private int xp ;
@@ -427,6 +430,7 @@ public Person(final String preNominal, final String givenName, final String surn
427
430
wealth = 0 ;
428
431
reputation = 0 ;
429
432
unlucky = 0 ;
433
+ atowAttributes = new Attributes ();
430
434
dateOfDeath = null ;
431
435
recruitment = null ;
432
436
joinedCampaign = null ;
@@ -2339,6 +2343,10 @@ public void writeToXML(final PrintWriter pw, int indent, final Campaign campaign
2339
2343
MHQXMLUtility .writeSimpleXMLTag (pw , indent , "unlucky" , unlucky );
2340
2344
}
2341
2345
2346
+ MHQXMLUtility .writeSimpleXMLOpenTag (pw , indent ++, "atowAttributes" );
2347
+ atowAttributes .writeAttributesToXML (pw , indent );
2348
+ MHQXMLUtility .writeSimpleXMLCloseTag (pw , --indent , "atowAttributes" );
2349
+
2342
2350
MHQXMLUtility .writeSimpleXMLTag (pw , indent , "minutesLeft" , minutesLeft );
2343
2351
2344
2352
if (overtimeLeft > 0 ) {
@@ -2748,6 +2756,8 @@ public static Person generateInstanceFromXML(Node wn, Campaign campaign, Version
2748
2756
person .reputation = MathUtility .parseInt (wn2 .getTextContent ());
2749
2757
} else if (wn2 .getNodeName ().equalsIgnoreCase ("unlucky" )) {
2750
2758
person .unlucky = MathUtility .parseInt (wn2 .getTextContent ());
2759
+ } else if (wn2 .getNodeName ().equalsIgnoreCase ("atowAttributes" )) {
2760
+ person .atowAttributes = new Attributes ().generateAttributesFromXML (wn2 );
2751
2761
} else if (wn2 .getNodeName ().equalsIgnoreCase ("pilotHits" )) {
2752
2762
person .hits = MathUtility .parseInt (wn2 .getTextContent ());
2753
2763
} else if (wn2 .getNodeName ().equalsIgnoreCase ("skill" )) {
@@ -3493,18 +3503,18 @@ public int getExperienceLevel(final Campaign campaign, final boolean secondary)
3493
3503
SkillType .EXP_NONE ;
3494
3504
case MECHANIC :
3495
3505
if (isTechsHaveAdministration ) {
3496
- if (hasSkill (SkillType .S_TECH_MECHANIC ) && hasSkill (SkillType . S_ADMIN )) {
3506
+ if (hasSkill (SkillType .S_TECH_MECHANIC ) && hasSkill (S_ADMIN )) {
3497
3507
if (isAlternativeQualityAveraging ) {
3498
3508
int rawScore = (int ) Math .floor ((getSkill (SkillType .S_TECH_MECHANIC ).getLevel () +
3499
- getSkill (SkillType . S_ADMIN ).getLevel ()) / 2.0 );
3509
+ getSkill (S_ADMIN ).getLevel ()) / 2.0 );
3500
3510
if (getSkill (SkillType .S_TECH_MECHANIC ).getType ().getExperienceLevel (rawScore ) ==
3501
- getSkill (SkillType . S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3511
+ getSkill (S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3502
3512
return getSkill (SkillType .S_TECH_MECHANIC ).getType ().getExperienceLevel (rawScore );
3503
3513
}
3504
3514
}
3505
3515
3506
3516
return (int ) Math .floor ((getSkill (SkillType .S_TECH_MECHANIC ).getExperienceLevel () +
3507
- getSkill (SkillType . S_ADMIN ).getExperienceLevel ()) / 2.0 );
3517
+ getSkill (S_ADMIN ).getExperienceLevel ()) / 2.0 );
3508
3518
} else {
3509
3519
return SkillType .EXP_NONE ;
3510
3520
}
@@ -3579,18 +3589,18 @@ public int getExperienceLevel(final Campaign campaign, final boolean secondary)
3579
3589
SkillType .EXP_NONE ;
3580
3590
case VESSEL_CREW :
3581
3591
if (isTechsHaveAdministration ) {
3582
- if (hasSkill (SkillType .S_TECH_VESSEL ) && hasSkill (SkillType . S_ADMIN )) {
3592
+ if (hasSkill (SkillType .S_TECH_VESSEL ) && hasSkill (S_ADMIN )) {
3583
3593
if (isAlternativeQualityAveraging ) {
3584
3594
int rawScore = (int ) Math .floor ((getSkill (SkillType .S_TECH_VESSEL ).getLevel () +
3585
- getSkill (SkillType . S_ADMIN ).getLevel ()) / 2.0 );
3595
+ getSkill (S_ADMIN ).getLevel ()) / 2.0 );
3586
3596
if (getSkill (SkillType .S_TECH_VESSEL ).getType ().getExperienceLevel (rawScore ) ==
3587
- getSkill (SkillType . S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3597
+ getSkill (S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3588
3598
return getSkill (SkillType .S_TECH_VESSEL ).getType ().getExperienceLevel (rawScore );
3589
3599
}
3590
3600
}
3591
3601
3592
3602
return (int ) Math .floor ((getSkill (SkillType .S_TECH_VESSEL ).getExperienceLevel () +
3593
- getSkill (SkillType . S_ADMIN ).getExperienceLevel ()) / 2.0 );
3603
+ getSkill (S_ADMIN ).getExperienceLevel ()) / 2.0 );
3594
3604
} else {
3595
3605
return SkillType .EXP_NONE ;
3596
3606
}
@@ -3603,18 +3613,18 @@ public int getExperienceLevel(final Campaign campaign, final boolean secondary)
3603
3613
return hasSkill (SkillType .S_NAV ) ? getSkill (SkillType .S_NAV ).getExperienceLevel () : SkillType .EXP_NONE ;
3604
3614
case MEK_TECH :
3605
3615
if (isTechsHaveAdministration ) {
3606
- if (hasSkill (SkillType .S_TECH_MEK ) && hasSkill (SkillType . S_ADMIN )) {
3616
+ if (hasSkill (SkillType .S_TECH_MEK ) && hasSkill (S_ADMIN )) {
3607
3617
if (isAlternativeQualityAveraging ) {
3608
3618
int rawScore = (int ) Math .floor ((getSkill (SkillType .S_TECH_MEK ).getLevel () +
3609
- getSkill (SkillType . S_ADMIN ).getLevel ()) / 2.0 );
3619
+ getSkill (S_ADMIN ).getLevel ()) / 2.0 );
3610
3620
if (getSkill (SkillType .S_TECH_MEK ).getType ().getExperienceLevel (rawScore ) ==
3611
- getSkill (SkillType . S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3621
+ getSkill (S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3612
3622
return getSkill (SkillType .S_TECH_MEK ).getType ().getExperienceLevel (rawScore );
3613
3623
}
3614
3624
}
3615
3625
3616
3626
return (int ) Math .floor ((getSkill (SkillType .S_TECH_MEK ).getExperienceLevel () +
3617
- getSkill (SkillType . S_ADMIN ).getExperienceLevel ()) / 2.0 );
3627
+ getSkill (S_ADMIN ).getExperienceLevel ()) / 2.0 );
3618
3628
} else {
3619
3629
return SkillType .EXP_NONE ;
3620
3630
}
@@ -3625,18 +3635,18 @@ public int getExperienceLevel(final Campaign campaign, final boolean secondary)
3625
3635
}
3626
3636
case AERO_TEK :
3627
3637
if (isTechsHaveAdministration ) {
3628
- if (hasSkill (SkillType .S_TECH_AERO ) && hasSkill (SkillType . S_ADMIN )) {
3638
+ if (hasSkill (SkillType .S_TECH_AERO ) && hasSkill (S_ADMIN )) {
3629
3639
if (isAlternativeQualityAveraging ) {
3630
3640
int rawScore = (int ) Math .floor ((getSkill (SkillType .S_TECH_AERO ).getLevel () +
3631
- getSkill (SkillType . S_ADMIN ).getLevel ()) / 2.0 );
3641
+ getSkill (S_ADMIN ).getLevel ()) / 2.0 );
3632
3642
if (getSkill (SkillType .S_TECH_AERO ).getType ().getExperienceLevel (rawScore ) ==
3633
- getSkill (SkillType . S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3643
+ getSkill (S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3634
3644
return getSkill (SkillType .S_TECH_AERO ).getType ().getExperienceLevel (rawScore );
3635
3645
}
3636
3646
}
3637
3647
3638
3648
return (int ) Math .floor ((getSkill (SkillType .S_TECH_AERO ).getExperienceLevel () +
3639
- getSkill (SkillType . S_ADMIN ).getExperienceLevel ()) / 2.0 );
3649
+ getSkill (S_ADMIN ).getExperienceLevel ()) / 2.0 );
3640
3650
} else {
3641
3651
return SkillType .EXP_NONE ;
3642
3652
}
@@ -3647,18 +3657,18 @@ public int getExperienceLevel(final Campaign campaign, final boolean secondary)
3647
3657
}
3648
3658
case BA_TECH :
3649
3659
if (isTechsHaveAdministration ) {
3650
- if (hasSkill (SkillType .S_TECH_BA ) && hasSkill (SkillType . S_ADMIN )) {
3660
+ if (hasSkill (SkillType .S_TECH_BA ) && hasSkill (S_ADMIN )) {
3651
3661
if (isAlternativeQualityAveraging ) {
3652
3662
int rawScore = (int ) Math .floor ((getSkill (SkillType .S_TECH_BA ).getLevel () +
3653
- getSkill (SkillType . S_ADMIN ).getLevel ()) / 2.0 );
3663
+ getSkill (S_ADMIN ).getLevel ()) / 2.0 );
3654
3664
if (getSkill (SkillType .S_TECH_BA ).getType ().getExperienceLevel (rawScore ) ==
3655
- getSkill (SkillType . S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3665
+ getSkill (S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3656
3666
return getSkill (SkillType .S_TECH_BA ).getType ().getExperienceLevel (rawScore );
3657
3667
}
3658
3668
}
3659
3669
3660
3670
return (int ) Math .floor ((getSkill (SkillType .S_TECH_BA ).getExperienceLevel () +
3661
- getSkill (SkillType . S_ADMIN ).getExperienceLevel ()) / 2.0 );
3671
+ getSkill (S_ADMIN ).getExperienceLevel ()) / 2.0 );
3662
3672
} else {
3663
3673
return SkillType .EXP_NONE ;
3664
3674
}
@@ -3673,18 +3683,18 @@ public int getExperienceLevel(final Campaign campaign, final boolean secondary)
3673
3683
SkillType .EXP_NONE ;
3674
3684
case DOCTOR :
3675
3685
if (isDoctorsHaveAdministration ) {
3676
- if (hasSkill (SkillType .S_DOCTOR ) && hasSkill (SkillType . S_ADMIN )) {
3686
+ if (hasSkill (SkillType .S_DOCTOR ) && hasSkill (S_ADMIN )) {
3677
3687
if (isAlternativeQualityAveraging ) {
3678
3688
int rawScore = (int ) Math .floor ((getSkill (SkillType .S_DOCTOR ).getLevel () +
3679
- getSkill (SkillType . S_ADMIN ).getLevel ()) / 2.0 );
3689
+ getSkill (S_ADMIN ).getLevel ()) / 2.0 );
3680
3690
if (getSkill (SkillType .S_DOCTOR ).getType ().getExperienceLevel (rawScore ) ==
3681
- getSkill (SkillType . S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3691
+ getSkill (S_ADMIN ).getType ().getExperienceLevel (rawScore )) {
3682
3692
return getSkill (SkillType .S_DOCTOR ).getType ().getExperienceLevel (rawScore );
3683
3693
}
3684
3694
}
3685
3695
3686
3696
return (int ) Math .floor ((getSkill (SkillType .S_DOCTOR ).getExperienceLevel () +
3687
- getSkill (SkillType . S_ADMIN ).getExperienceLevel ()) / 2.0 );
3697
+ getSkill (S_ADMIN ).getExperienceLevel ()) / 2.0 );
3688
3698
} else {
3689
3699
return SkillType .EXP_NONE ;
3690
3700
}
@@ -4619,7 +4629,7 @@ public double calculateTechTimeMultiplier(boolean isTechsUseAdministration) {
4619
4629
4620
4630
double administrationMultiplier = 1.0 - (TECH_ADMINISTRATION_MULTIPLIER * REGULAR_EXPERIENCE_LEVEL );
4621
4631
4622
- Skill administration = skills .getSkill (SkillType . S_ADMIN );
4632
+ Skill administration = skills .getSkill (S_ADMIN );
4623
4633
int experienceLevel = SkillLevel .NONE .getExperienceLevel ();
4624
4634
4625
4635
if (administration != null ) {
@@ -4667,7 +4677,7 @@ public int getDoctorMedicalCapacity(final boolean doctorsUseAdministration, fina
4667
4677
4668
4678
double administrationMultiplier = 1.0 - (DOCTOR_ADMINISTRATION_MULTIPLIER * REGULAR_EXPERIENCE_LEVEL );
4669
4679
4670
- Skill administration = skills .getSkill (SkillType . S_ADMIN );
4680
+ Skill administration = skills .getSkill (S_ADMIN );
4671
4681
int experienceLevel = SkillLevel .NONE .getExperienceLevel ();
4672
4682
4673
4683
if (administration != null ) {
@@ -4901,6 +4911,99 @@ public void setUnlucky(final int unlucky) {
4901
4911
this .unlucky = unlucky ;
4902
4912
}
4903
4913
4914
+ /**
4915
+ * Retrieves the character's {@link Attributes} object containing the character's attribute scores.
4916
+ *
4917
+ * <p><b>Usage:</b> In most cases you'll want to use {@link #getAttributeScore(SkillAttribute)} instead, as that
4918
+ * will allow you to jump straight to the exact score you need.</p>
4919
+ *
4920
+ * @return the character's {@link Attributes} object.
4921
+ *
4922
+ * @since 0.50.5
4923
+ */
4924
+ public Attributes getATOWAttributes () {
4925
+ return atowAttributes ;
4926
+ }
4927
+
4928
+ /**
4929
+ * Retrieves the score of a specified attribute.
4930
+ *
4931
+ * <p>The method maps the provided {@link SkillAttribute} to its corresponding attribute in
4932
+ * the {@link Attributes} object and returns its value. If the {@link SkillAttribute} is {@code NONE}, the method
4933
+ * returns a score of 0. If the {@code attribute} is {@code null}, an error is logged, and the method returns a
4934
+ * score of 0.</p>
4935
+ *
4936
+ * @param attribute the {@link SkillAttribute} to retrieve the score for.
4937
+ *
4938
+ * @return the score of the specified attribute, or 0 if the attribute is {@code NONE} or {@code null}.
4939
+ *
4940
+ * @since 0.50.5
4941
+ */
4942
+ public int getAttributeScore (final SkillAttribute attribute ) {
4943
+ if (attribute == null ) {
4944
+ logger .error ("(getAttributeScore) SkillAttribute is null." );
4945
+ return 0 ;
4946
+ }
4947
+
4948
+ return switch (attribute ) {
4949
+ case NONE -> 0 ;
4950
+ case STRENGTH -> atowAttributes .getStrength ();
4951
+ case BODY -> atowAttributes .getBody ();
4952
+ case REFLEXES -> atowAttributes .getReflexes ();
4953
+ case DEXTERITY -> atowAttributes .getDexterity ();
4954
+ case INTELLIGENCE -> atowAttributes .getIntelligence ();
4955
+ case WILLPOWER -> atowAttributes .getWillpower ();
4956
+ case CHARISMA -> atowAttributes .getCharisma ();
4957
+ };
4958
+ }
4959
+
4960
+ /**
4961
+ * Sets the character's {@link Attributes} object which contains their ATOW Attribute scores.
4962
+ *
4963
+ * <p><b>Usage:</b> This completely wipes the character's attribute scores and is likely not the method you're
4964
+ * looking for. Consider{@link #changeAttributeScore(SkillAttribute, int)} if you just want to increment or
4965
+ * decrement a specific attribute by a certain value.</p>
4966
+ *
4967
+ * @param atowAttributes the {@link Attributes} object to set.
4968
+ *
4969
+ * @since 0.50.5
4970
+ */
4971
+ public void setATOWAttributes (final Attributes atowAttributes ) {
4972
+ this .atowAttributes = atowAttributes ;
4973
+ }
4974
+
4975
+ /**
4976
+ * Modifies the score of a specified attribute by applying a delta value.
4977
+ *
4978
+ * <p>This method maps the provided {@link SkillAttribute} to its corresponding attribute in the
4979
+ * {@link Attributes} object and adjusts its value by the specified delta. If the {@code attribute} is {@code NONE},
4980
+ * the method does nothing. If {@code attribute} is {@code null}, an error is logged, and the method returns without
4981
+ * performing any operation.</p>
4982
+ *
4983
+ * @param attribute the {@link SkillAttribute} to modify the score for.
4984
+ * @param delta the value to add to (or subtract from) the current score of the specified attribute.
4985
+ *
4986
+ * @since 0.50.5
4987
+ */
4988
+ public void changeAttributeScore (final SkillAttribute attribute , final int delta ) {
4989
+ if (attribute == null ) {
4990
+ logger .error ("(changeAttributeScore) SkillAttribute is null." );
4991
+ return ;
4992
+ }
4993
+
4994
+ switch (attribute ) {
4995
+ case NONE -> {
4996
+ }
4997
+ case STRENGTH -> atowAttributes .changeStrength (delta );
4998
+ case BODY -> atowAttributes .changeBody (delta );
4999
+ case REFLEXES -> atowAttributes .changeReflexes (delta );
5000
+ case DEXTERITY -> atowAttributes .changeDexterity (delta );
5001
+ case INTELLIGENCE -> atowAttributes .changeIntelligence (delta );
5002
+ case WILLPOWER -> atowAttributes .changeWillpower (delta );
5003
+ case CHARISMA -> atowAttributes .changeCharisma (delta );
5004
+ }
5005
+ }
5006
+
4904
5007
public void resetSkillTypes () {
4905
5008
skills .getSkills ().forEach (Skill ::updateType );
4906
5009
}
0 commit comments