ango commited on
Commit
b8aecdd
·
1 Parent(s): 025687f

04.08 commit

Browse files
base/attribute.py CHANGED
@@ -1,9 +1,96 @@
1
  from base.constant import *
2
 
3
 
4
- class Attribute:
5
- level: int = 120
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
6
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
7
  _all_major_base: int = 0
8
  _all_major_gain: int = 0
9
  _agility_base: int = 0
@@ -19,13 +106,6 @@ class Attribute:
19
  _spunk_gain: int = 0
20
  _spunk: int = 0
21
 
22
- surplus: int = 0
23
-
24
- _strain_base: int = 0
25
- _strain_percent: float = 0
26
- _strain_gain: int = 0
27
- _strain: float = 0
28
-
29
  _physical_attack_power_base: int = 0
30
  _base_physical_attack_power: int = 0
31
  _physical_attack_power_gain: int = 0
@@ -53,18 +133,6 @@ class Attribute:
53
  _magical_critical_strike_gain: int = 0
54
  _magical_critical_strike: float = 0
55
 
56
- _all_critical_power_base: int = 0
57
- _all_critical_power_gain: int = 0
58
-
59
- _physical_critical_power_base: int = 0
60
- _physical_critical_power_percent: float = 0
61
- _physical_critical_power_gain: int = 0
62
- _physical_critical_power: float = 0
63
- _magical_critical_power_base: int = 0
64
- _magical_critical_power_percent: float = 0
65
- _magical_critical_power_gain: int = 0
66
- _magical_critical_power: float = 0
67
-
68
  _physical_overcome_base: int = 0
69
  _base_physical_overcome: int = 0
70
  _final_physical_overcome: int = 0
@@ -78,36 +146,8 @@ class Attribute:
78
  _extra_magical_overcome: int = 0
79
  _magical_overcome: float = 0
80
 
81
- _weapon_damage_rand: int = 0
82
- _weapon_damage_base: int = 0
83
- _weapon_damage_gain: int = 0
84
- _weapon_damage: int = 0
85
-
86
- _all_shield_ignore: float = 0
87
-
88
- _physical_shield_ignore: float = 0
89
- _magical_shield_ignore: float = 0
90
-
91
- _all_damage_addition: float = 0
92
- _physical_damage_addition: float = 0
93
- _magical_damage_addition: float = 0
94
-
95
- _pve_addition: float = 0
96
-
97
- target_level: int = 124
98
-
99
- _physical_shield_gain: int = 0
100
- _magical_shield_gain: int = 0
101
-
102
- _all_vulnerable: float = 0
103
- _physical_vulnerable: float = 0
104
- _magical_vulnerable: float = 0
105
-
106
- def __init__(self):
107
- self.all_major_base += MAJOR_BASE
108
-
109
  """ Major Attr Function"""
110
-
111
  @property
112
  def all_major_base(self):
113
  return self._all_major_base
@@ -250,43 +290,6 @@ class Attribute:
250
  self.base_magical_attack_power = self.magical_attack_power_base + spunk * SPUNK_TO_ATTACK_POWER
251
  self.base_magical_overcome = self.magical_overcome_base + spunk * SPUNK_TO_OVERCOME
252
 
253
- """ Minor Function """
254
-
255
- @property
256
- def strain_base(self):
257
- return self._strain_base
258
-
259
- @strain_base.setter
260
- def strain_base(self, strain_base):
261
- self._strain_base = strain_base
262
- self.strain_percent = strain_base / STRAIN_SCALE
263
-
264
- @property
265
- def strain_percent(self):
266
- return self._strain_percent
267
-
268
- @strain_percent.setter
269
- def strain_percent(self, strain_percent):
270
- self._strain_percent = strain_percent
271
- self.strain = strain_percent + self.strain_gain
272
-
273
- @property
274
- def strain_gain(self):
275
- return self._strain_gain / BINARY_SCALE
276
-
277
- @strain_gain.setter
278
- def strain_gain(self, strain_gain):
279
- self._strain_gain = strain_gain
280
- self.strain = self.strain_percent + self.strain_gain
281
-
282
- @property
283
- def strain(self):
284
- return self._strain
285
-
286
- @strain.setter
287
- def strain(self, strain):
288
- self._strain = strain
289
-
290
  """ Attack Power Function """
291
 
292
  @property
@@ -539,104 +542,6 @@ class Attribute:
539
  def magical_critical_strike(self, magical_critical_strike):
540
  self._magical_critical_strike = magical_critical_strike
541
 
542
- """ Critical Power Function"""
543
-
544
- @property
545
- def critical_power(self):
546
- raise NotImplementedError
547
-
548
- @property
549
- def all_critical_power_base(self):
550
- return self._all_critical_power_base
551
-
552
- @all_critical_power_base.setter
553
- def all_critical_power_base(self, all_critical_power_base):
554
- residual = all_critical_power_base - self._all_critical_power_base
555
- self.physical_critical_power_base += residual
556
- self.magical_critical_power_base += residual
557
- self._all_critical_power_base = all_critical_power_base
558
-
559
- @property
560
- def all_critical_power_gain(self):
561
- return self._all_critical_power_gain
562
-
563
- @all_critical_power_gain.setter
564
- def all_critical_power_gain(self, all_critical_power_gain):
565
- residual = all_critical_power_gain - self._all_critical_power_gain
566
- self.physical_critical_power_gain += residual
567
- self.magical_critical_power_gain += residual
568
- self._all_critical_power_gain = all_critical_power_gain
569
-
570
- @property
571
- def physical_critical_power_base(self):
572
- return self._physical_critical_power_base
573
-
574
- @physical_critical_power_base.setter
575
- def physical_critical_power_base(self, physical_critical_power_base):
576
- self._physical_critical_power_base = physical_critical_power_base
577
- self.physical_critical_power_percent = self.physical_critical_power_base / CRITICAL_POWER_SCALE
578
-
579
- @property
580
- def physical_critical_power_percent(self):
581
- return CRITICAL_POWER_BASE + self._physical_critical_power_percent
582
-
583
- @physical_critical_power_percent.setter
584
- def physical_critical_power_percent(self, physical_critical_power_percent):
585
- self._physical_critical_power_percent = physical_critical_power_percent
586
- self.physical_critical_power = self.physical_critical_power_percent + self.physical_critical_power_gain
587
-
588
- @property
589
- def physical_critical_power_gain(self):
590
- return self._physical_critical_power_gain / BINARY_SCALE
591
-
592
- @physical_critical_power_gain.setter
593
- def physical_critical_power_gain(self, physical_critical_power_gain):
594
- self._physical_critical_power_gain = physical_critical_power_gain
595
- self.physical_critical_power = self.physical_critical_power_percent + self.physical_critical_power_gain
596
-
597
- @property
598
- def physical_critical_power(self):
599
- return self._physical_critical_power
600
-
601
- @physical_critical_power.setter
602
- def physical_critical_power(self, physical_critical_power):
603
- self._physical_critical_power = physical_critical_power
604
-
605
- @property
606
- def magical_critical_power_base(self):
607
- return self._magical_critical_power_base
608
-
609
- @magical_critical_power_base.setter
610
- def magical_critical_power_base(self, magical_critical_power_base):
611
- self._magical_critical_power_base = magical_critical_power_base
612
- self.magical_critical_power_percent = self.magical_critical_power_base / CRITICAL_POWER_SCALE
613
-
614
- @property
615
- def magical_critical_power_percent(self):
616
- return CRITICAL_POWER_BASE + self._magical_critical_power_percent
617
-
618
- @magical_critical_power_percent.setter
619
- def magical_critical_power_percent(self, magical_critical_power_percent):
620
- self._magical_critical_power_percent = magical_critical_power_percent
621
- self.magical_critical_power = self.magical_critical_power_percent + self.magical_critical_power_gain
622
-
623
- @property
624
- def magical_critical_power_gain(self):
625
- return self._magical_critical_power_gain / BINARY_SCALE
626
-
627
- @magical_critical_power_gain.setter
628
- def magical_critical_power_gain(self, magical_critical_power_gain):
629
- self._magical_critical_power_gain = magical_critical_power_gain
630
- self.magical_critical_power = self.magical_critical_power_percent + self.magical_critical_power_gain
631
-
632
- @property
633
- def magical_critical_power(self):
634
- return self._magical_critical_power
635
-
636
- @magical_critical_power.setter
637
- def magical_critical_power(self, magical_critical_power):
638
- self._magical_critical_power = magical_critical_power
639
-
640
  """ Overcome Function"""
641
 
642
  @property
@@ -761,6 +666,178 @@ class Attribute:
761
  def magical_overcome(self, magical_overcome):
762
  self._magical_overcome = magical_overcome
763
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
764
  """ Weapon Damage Function """
765
 
766
  @property
@@ -870,73 +947,90 @@ class Attribute:
870
  def pve_addition(self, pve_addition):
871
  self._pve_addition = pve_addition
872
 
 
 
 
 
 
 
 
 
873
  @property
874
- def shield_base(self):
875
- raise NotImplementedError
 
876
 
 
877
  @property
878
- def physical_shield_base(self):
879
- return SHIELD_BASE_MAP[self.target_level]
880
 
881
  @property
882
- def magical_shield_base(self):
883
- return SHIELD_BASE_MAP[self.target_level]
884
 
885
  @property
886
- def shield_gain(self):
887
- raise NotImplementedError
888
 
889
  @property
890
- def physical_shield_gain(self):
891
- return self._physical_shield_gain / BINARY_SCALE
892
 
893
- @physical_shield_gain.setter
894
- def physical_shield_gain(self, physical_shield_gain):
895
- self._physical_shield_gain = physical_shield_gain
896
 
897
  @property
898
- def magical_shield_gain(self):
899
- return self._magical_shield_gain / BINARY_SCALE
900
 
901
- @magical_shield_gain.setter
902
- def magical_shield_gain(self, magical_shield_gain):
903
- self._magical_shield_gain = magical_shield_gain
 
 
 
 
904
 
905
  @property
906
  def vulnerable(self):
907
- raise NotImplementedError
 
908
 
 
909
  @property
910
- def all_vulnerable(self):
911
- return self._all_vulnerable
912
 
913
- @all_vulnerable.setter
914
- def all_vulnerable(self, all_vulnerable):
915
- residual = all_vulnerable - self._all_vulnerable
916
- self.physical_vulnerable += residual
917
- self.magical_vulnerable += residual
918
- self._all_vulnerable = all_vulnerable
919
 
920
  @property
921
- def physical_vulnerable(self):
922
- return self._physical_vulnerable / BINARY_SCALE
923
 
924
- @physical_vulnerable.setter
925
- def physical_vulnerable(self, physical_vulnerable):
926
- self._physical_vulnerable = physical_vulnerable
927
 
928
  @property
929
- def magical_vulnerable(self):
930
- return self._magical_vulnerable / BINARY_SCALE
931
 
932
- @magical_vulnerable.setter
933
- def magical_vulnerable(self, magical_vulnerable):
934
- self._magical_vulnerable = magical_vulnerable
935
 
936
  @property
937
- def level_reduction(self):
938
- return LEVEL_REDUCTION * (self.target_level - self.level)
939
 
940
  @property
941
- def shield_constant(self):
942
- return SHIELD_SCALE * (LEVEL_SCALE * self.level - LEVEL_CONSTANT)
 
 
 
 
 
1
  from base.constant import *
2
 
3
 
4
+ class Target:
5
+ target_level: int = 124
6
+
7
+ _physical_shield_base: int = 0
8
+ _magical_shield_base: int = 0
9
+
10
+ _physical_shield_gain: int = 0
11
+ _magical_shield_gain: int = 0
12
+
13
+ _all_vulnerable: float = 0
14
+ _physical_vulnerable: float = 0
15
+ _magical_vulnerable: float = 0
16
+
17
+ @property
18
+ def shield_base(self):
19
+ raise NotImplementedError
20
+
21
+ @property
22
+ def physical_shield_base(self):
23
+ return SHIELD_BASE_MAP[self.target_level] + self._physical_shield_base
24
+
25
+ @physical_shield_base.setter
26
+ def physical_shield_base(self, physical_shield_base):
27
+ self._physical_shield_base = physical_shield_base
28
+
29
+ @property
30
+ def magical_shield_base(self):
31
+ return SHIELD_BASE_MAP[self.target_level] + self._magical_shield_base
32
+
33
+ @magical_shield_base.setter
34
+ def magical_shield_base(self, magical_shield_base):
35
+ self._magical_shield_base = magical_shield_base
36
+
37
+ @property
38
+ def shield_gain(self):
39
+ raise NotImplementedError
40
+
41
+ @property
42
+ def physical_shield_gain(self):
43
+ return self._physical_shield_gain / BINARY_SCALE
44
+
45
+ @physical_shield_gain.setter
46
+ def physical_shield_gain(self, physical_shield_gain):
47
+ self._physical_shield_gain = physical_shield_gain
48
+
49
+ @property
50
+ def magical_shield_gain(self):
51
+ return self._magical_shield_gain / BINARY_SCALE
52
+
53
+ @magical_shield_gain.setter
54
+ def magical_shield_gain(self, magical_shield_gain):
55
+ self._magical_shield_gain = magical_shield_gain
56
+
57
+ @property
58
+ def vulnerable(self):
59
+ raise NotImplementedError
60
+
61
+ @property
62
+ def all_vulnerable(self):
63
+ return self._all_vulnerable
64
+
65
+ @all_vulnerable.setter
66
+ def all_vulnerable(self, all_vulnerable):
67
+ residual = all_vulnerable - self._all_vulnerable
68
+ self.physical_vulnerable += residual
69
+ self.magical_vulnerable += residual
70
+ self._all_vulnerable = all_vulnerable
71
+
72
+ @property
73
+ def physical_vulnerable(self):
74
+ return self._physical_vulnerable / BINARY_SCALE
75
 
76
+ @physical_vulnerable.setter
77
+ def physical_vulnerable(self, physical_vulnerable):
78
+ self._physical_vulnerable = physical_vulnerable
79
+
80
+ @property
81
+ def magical_vulnerable(self):
82
+ return self._magical_vulnerable / BINARY_SCALE
83
+
84
+ @magical_vulnerable.setter
85
+ def magical_vulnerable(self, magical_vulnerable):
86
+ self._magical_vulnerable = magical_vulnerable
87
+
88
+ @property
89
+ def shield_constant(self):
90
+ return SHIELD_SCALE * (LEVEL_SCALE * self.target_level - LEVEL_CONSTANT)
91
+
92
+
93
+ class Major:
94
  _all_major_base: int = 0
95
  _all_major_gain: int = 0
96
  _agility_base: int = 0
 
106
  _spunk_gain: int = 0
107
  _spunk: int = 0
108
 
 
 
 
 
 
 
 
109
  _physical_attack_power_base: int = 0
110
  _base_physical_attack_power: int = 0
111
  _physical_attack_power_gain: int = 0
 
133
  _magical_critical_strike_gain: int = 0
134
  _magical_critical_strike: float = 0
135
 
 
 
 
 
 
 
 
 
 
 
 
 
136
  _physical_overcome_base: int = 0
137
  _base_physical_overcome: int = 0
138
  _final_physical_overcome: int = 0
 
146
  _extra_magical_overcome: int = 0
147
  _magical_overcome: float = 0
148
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
149
  """ Major Attr Function"""
150
+
151
  @property
152
  def all_major_base(self):
153
  return self._all_major_base
 
290
  self.base_magical_attack_power = self.magical_attack_power_base + spunk * SPUNK_TO_ATTACK_POWER
291
  self.base_magical_overcome = self.magical_overcome_base + spunk * SPUNK_TO_OVERCOME
292
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
293
  """ Attack Power Function """
294
 
295
  @property
 
542
  def magical_critical_strike(self, magical_critical_strike):
543
  self._magical_critical_strike = magical_critical_strike
544
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
545
  """ Overcome Function"""
546
 
547
  @property
 
666
  def magical_overcome(self, magical_overcome):
667
  self._magical_overcome = magical_overcome
668
 
669
+
670
+ class Minor:
671
+ surplus: int = 0
672
+
673
+ _strain_base: int = 0
674
+ _strain_percent: float = 0
675
+ _strain_gain: int = 0
676
+ _strain: float = 0
677
+
678
+ _all_critical_power_base: int = 0
679
+ _all_critical_power_gain: int = 0
680
+
681
+ _physical_critical_power_base: int = 0
682
+ _physical_critical_power_percent: float = 0
683
+ _physical_critical_power_gain: int = 0
684
+ _physical_critical_power: float = 0
685
+ _magical_critical_power_base: int = 0
686
+ _magical_critical_power_percent: float = 0
687
+ _magical_critical_power_gain: int = 0
688
+ _magical_critical_power: float = 0
689
+
690
+ _weapon_damage_rand: int = 0
691
+ _weapon_damage_base: int = 0
692
+ _weapon_damage_gain: int = 0
693
+ _weapon_damage: int = 0
694
+
695
+ _all_shield_ignore: float = 0
696
+
697
+ _physical_shield_ignore: float = 0
698
+ _magical_shield_ignore: float = 0
699
+
700
+ _all_damage_addition: float = 0
701
+ _physical_damage_addition: float = 0
702
+ _magical_damage_addition: float = 0
703
+
704
+ _pve_addition: float = 0
705
+
706
+ """ Minor Function """
707
+
708
+ @property
709
+ def strain_base(self):
710
+ return self._strain_base
711
+
712
+ @strain_base.setter
713
+ def strain_base(self, strain_base):
714
+ self._strain_base = strain_base
715
+ self.strain_percent = strain_base / STRAIN_SCALE
716
+
717
+ @property
718
+ def strain_percent(self):
719
+ return self._strain_percent
720
+
721
+ @strain_percent.setter
722
+ def strain_percent(self, strain_percent):
723
+ self._strain_percent = strain_percent
724
+ self.strain = strain_percent + self.strain_gain
725
+
726
+ @property
727
+ def strain_gain(self):
728
+ return self._strain_gain / BINARY_SCALE
729
+
730
+ @strain_gain.setter
731
+ def strain_gain(self, strain_gain):
732
+ self._strain_gain = strain_gain
733
+ self.strain = self.strain_percent + self.strain_gain
734
+
735
+ @property
736
+ def strain(self):
737
+ return self._strain
738
+
739
+ @strain.setter
740
+ def strain(self, strain):
741
+ self._strain = strain
742
+
743
+ """ Critical Power Function"""
744
+
745
+ @property
746
+ def critical_power(self):
747
+ raise NotImplementedError
748
+
749
+ @property
750
+ def all_critical_power_base(self):
751
+ return self._all_critical_power_base
752
+
753
+ @all_critical_power_base.setter
754
+ def all_critical_power_base(self, all_critical_power_base):
755
+ residual = all_critical_power_base - self._all_critical_power_base
756
+ self.physical_critical_power_base += residual
757
+ self.magical_critical_power_base += residual
758
+ self._all_critical_power_base = all_critical_power_base
759
+
760
+ @property
761
+ def all_critical_power_gain(self):
762
+ return self._all_critical_power_gain
763
+
764
+ @all_critical_power_gain.setter
765
+ def all_critical_power_gain(self, all_critical_power_gain):
766
+ residual = all_critical_power_gain - self._all_critical_power_gain
767
+ self.physical_critical_power_gain += residual
768
+ self.magical_critical_power_gain += residual
769
+ self._all_critical_power_gain = all_critical_power_gain
770
+
771
+ @property
772
+ def physical_critical_power_base(self):
773
+ return self._physical_critical_power_base
774
+
775
+ @physical_critical_power_base.setter
776
+ def physical_critical_power_base(self, physical_critical_power_base):
777
+ self._physical_critical_power_base = physical_critical_power_base
778
+ self.physical_critical_power_percent = self.physical_critical_power_base / CRITICAL_POWER_SCALE
779
+
780
+ @property
781
+ def physical_critical_power_percent(self):
782
+ return CRITICAL_POWER_BASE + self._physical_critical_power_percent
783
+
784
+ @physical_critical_power_percent.setter
785
+ def physical_critical_power_percent(self, physical_critical_power_percent):
786
+ self._physical_critical_power_percent = physical_critical_power_percent
787
+ self.physical_critical_power = self.physical_critical_power_percent + self.physical_critical_power_gain
788
+
789
+ @property
790
+ def physical_critical_power_gain(self):
791
+ return self._physical_critical_power_gain / BINARY_SCALE
792
+
793
+ @physical_critical_power_gain.setter
794
+ def physical_critical_power_gain(self, physical_critical_power_gain):
795
+ self._physical_critical_power_gain = physical_critical_power_gain
796
+ self.physical_critical_power = self.physical_critical_power_percent + self.physical_critical_power_gain
797
+
798
+ @property
799
+ def physical_critical_power(self):
800
+ return self._physical_critical_power
801
+
802
+ @physical_critical_power.setter
803
+ def physical_critical_power(self, physical_critical_power):
804
+ self._physical_critical_power = physical_critical_power
805
+
806
+ @property
807
+ def magical_critical_power_base(self):
808
+ return self._magical_critical_power_base
809
+
810
+ @magical_critical_power_base.setter
811
+ def magical_critical_power_base(self, magical_critical_power_base):
812
+ self._magical_critical_power_base = magical_critical_power_base
813
+ self.magical_critical_power_percent = self.magical_critical_power_base / CRITICAL_POWER_SCALE
814
+
815
+ @property
816
+ def magical_critical_power_percent(self):
817
+ return CRITICAL_POWER_BASE + self._magical_critical_power_percent
818
+
819
+ @magical_critical_power_percent.setter
820
+ def magical_critical_power_percent(self, magical_critical_power_percent):
821
+ self._magical_critical_power_percent = magical_critical_power_percent
822
+ self.magical_critical_power = self.magical_critical_power_percent + self.magical_critical_power_gain
823
+
824
+ @property
825
+ def magical_critical_power_gain(self):
826
+ return self._magical_critical_power_gain / BINARY_SCALE
827
+
828
+ @magical_critical_power_gain.setter
829
+ def magical_critical_power_gain(self, magical_critical_power_gain):
830
+ self._magical_critical_power_gain = magical_critical_power_gain
831
+ self.magical_critical_power = self.magical_critical_power_percent + self.magical_critical_power_gain
832
+
833
+ @property
834
+ def magical_critical_power(self):
835
+ return self._magical_critical_power
836
+
837
+ @magical_critical_power.setter
838
+ def magical_critical_power(self, magical_critical_power):
839
+ self._magical_critical_power = magical_critical_power
840
+
841
  """ Weapon Damage Function """
842
 
843
  @property
 
947
  def pve_addition(self, pve_addition):
948
  self._pve_addition = pve_addition
949
 
950
+
951
+ class Attribute(Major, Minor, Target):
952
+ level: int = 120
953
+ grad_attrs: dict = None
954
+
955
+ def __init__(self):
956
+ self.all_major_base += MAJOR_BASE
957
+
958
  @property
959
+ def level_reduction(self):
960
+ return LEVEL_REDUCTION * (self.target_level - self.level)
961
+
962
 
963
+ class PhysicalAttribute(Attribute):
964
  @property
965
+ def attack_power(self):
966
+ return self.physical_attack_power
967
 
968
  @property
969
+ def critical_strike(self):
970
+ return self.physical_critical_strike
971
 
972
  @property
973
+ def critical_power(self):
974
+ return self.physical_critical_power
975
 
976
  @property
977
+ def overcome(self):
978
+ return self.physical_overcome
979
 
980
+ @property
981
+ def shield_ignore(self):
982
+ return self.physical_shield_ignore
983
 
984
  @property
985
+ def damage_addition(self):
986
+ return self.physical_damage_addition
987
 
988
+ @property
989
+ def shield_base(self):
990
+ return self.physical_shield_base
991
+
992
+ @property
993
+ def shield_gain(self):
994
+ return self.physical_shield_gain
995
 
996
  @property
997
  def vulnerable(self):
998
+ return self.physical_vulnerable
999
+
1000
 
1001
+ class MagicalAttribute(Attribute):
1002
  @property
1003
+ def attack_power(self):
1004
+ return self.magical_attack_power
1005
 
1006
+ @property
1007
+ def critical_strike(self):
1008
+ return self.magical_critical_strike
 
 
 
1009
 
1010
  @property
1011
+ def critical_power(self):
1012
+ return self.magical_critical_power
1013
 
1014
+ @property
1015
+ def overcome(self):
1016
+ return self.magical_overcome
1017
 
1018
  @property
1019
+ def shield_ignore(self):
1020
+ return self.magical_shield_ignore
1021
 
1022
+ @property
1023
+ def damage_addition(self):
1024
+ return self.magical_damage_addition
1025
 
1026
  @property
1027
+ def shield_base(self):
1028
+ return self.magical_shield_base
1029
 
1030
  @property
1031
+ def shield_gain(self):
1032
+ return self.magical_shield_gain
1033
+
1034
+ @property
1035
+ def vulnerable(self):
1036
+ return self.magical_vulnerable
base/calculator.py CHANGED
@@ -2,30 +2,48 @@ from base.attribute import Attribute
2
  from parse import Parser
3
 
4
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
5
  def analyze_details(parser: Parser, attribute: Attribute):
6
  existed_buffs = []
7
- for skill, status in parser.summary.items():
8
  skill_id, skill_level = skill
9
  skill = parser.skills[skill_id]
10
  skill.skill_level = skill_level
11
- for buffs, count in status.items():
12
- for buff in [buff for buff in existed_buffs if buff not in buffs]:
13
- existed_buffs.remove(buff)
14
- buff_id, buff_level, buff_stack = buff
15
- buff = parser.buffs[buff_id]
16
- buff.buff_level = buff_level
17
- for _ in range(buff_stack):
18
- attribute, parser.skills = (attribute, parser.skills) - buff
19
-
20
- for buff in [buff for buff in buffs if buff not in existed_buffs]:
21
- existed_buffs.append(buff)
22
- buff_id, buff_level, buff_stack = buff
23
- buff = parser.buffs[buff_id]
24
- buff.buff_level = buff_level
25
- for _ in range(buff_stack):
26
- attribute, parser.skills = (attribute, parser.skills) + buff
27
 
28
  damage, critical_damage, expected_damage = skill(attribute)
 
29
  status[buffs] = {
30
- "damage": damage, "critical_damage": critical_damage, "expected_damage": expected_damage, "count": count
 
 
31
  }
 
 
 
 
 
 
 
 
 
 
 
 
2
  from parse import Parser
3
 
4
 
5
+ def refresh_status(existed_buffs, buffs, attribute, parser: Parser):
6
+ for buff in [buff for buff in existed_buffs if buff not in buffs]:
7
+ existed_buffs.remove(buff)
8
+ buff_id, buff_level, buff_stack = buff
9
+ buff = parser.buffs[buff_id]
10
+ buff.buff_level = buff_level
11
+ for _ in range(buff_stack):
12
+ attribute, parser.skills = (attribute, parser.skills) - buff
13
+
14
+ for buff in [buff for buff in buffs if buff not in existed_buffs]:
15
+ existed_buffs.append(buff)
16
+ buff_id, buff_level, buff_stack = buff
17
+ buff = parser.buffs[buff_id]
18
+ buff.buff_level = buff_level
19
+ for _ in range(buff_stack):
20
+ attribute, parser.skills = (attribute, parser.skills) + buff
21
+
22
+
23
  def analyze_details(parser: Parser, attribute: Attribute):
24
  existed_buffs = []
25
+ for skill, status in parser.records.items():
26
  skill_id, skill_level = skill
27
  skill = parser.skills[skill_id]
28
  skill.skill_level = skill_level
29
+ for buffs, timeline in status.items():
30
+ refresh_status(existed_buffs, buffs, attribute, parser)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
31
 
32
  damage, critical_damage, expected_damage = skill(attribute)
33
+
34
  status[buffs] = {
35
+ "damage": damage, "critical_damage": critical_damage, "expected_damage": expected_damage,
36
+ "timeline": [round(t / 1000, 2) for t in timeline],
37
+ "gradients": analyze_gradients(skill, attribute)
38
  }
39
+ refresh_status(existed_buffs, [], attribute, parser)
40
+
41
+
42
+ def analyze_gradients(skill, attribute):
43
+ results = {}
44
+ for attr, value in attribute.grad_attrs.items():
45
+ origin_value = getattr(attribute, attr)
46
+ setattr(attribute, attr, origin_value + value)
47
+ _, _, results[attr] = skill(attribute)
48
+ setattr(attribute, attr, origin_value)
49
+ return results
base/skill.py CHANGED
@@ -70,7 +70,10 @@ class Skill:
70
  cof = self._surplus_cof[self.skill_level - 1]
71
  else:
72
  cof = self._surplus_cof
73
- return ((cof + int(cof < 0)) / BINARY_SCALE + BINARY_SCALE) / BINARY_SCALE * SURPLUS_SCALE
 
 
 
74
 
75
  @surplus_cof.setter
76
  def surplus_cof(self, surplus_cof):
 
70
  cof = self._surplus_cof[self.skill_level - 1]
71
  else:
72
  cof = self._surplus_cof
73
+ if cof:
74
+ return ((cof + int(cof < 0)) / BINARY_SCALE + BINARY_SCALE) / BINARY_SCALE * SURPLUS_SCALE
75
+ else:
76
+ return cof
77
 
78
  @surplus_cof.setter
79
  def surplus_cof(self, surplus_cof):
get_assets.py ADDED
@@ -0,0 +1,155 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import json
2
+ import os
3
+ from functools import cache
4
+
5
+ import requests
6
+ from tqdm import tqdm
7
+
8
+ from qt.constant import MAX_BASE_ATTR, MAX_MAGIC_ATTR, MAX_EMBED_ATTR, MAX_ENCHANT_ATTR, MAX_STONE_ATTR, \
9
+ MAX_STONE_LEVEL, ATTR_TYPE_MAP, ATTR_TYPE_TRANSLATE, STONE_ATTR
10
+ from qt.constant import EQUIPMENTS_DIR, ENCHANTS_DIR, STONES_DIR
11
+
12
+ EQUIP_ATTR_MAP = {
13
+ "Overcome": "破防",
14
+ "Critical": "会心",
15
+ "CriticalDamage": "会效",
16
+ "Haste": "加速",
17
+ "Surplus": "破招",
18
+ "Strain": "无双"
19
+ }
20
+
21
+ POSITION_MAP = {
22
+ "hat": 3,
23
+ "jacket": 2,
24
+ "belt": 6,
25
+ "wrist": 10,
26
+ "bottoms": 8,
27
+ "shoes": 9,
28
+ "necklace": 4,
29
+ "pendant": 7,
30
+ "ring": 5,
31
+ "tertiary_weapon": 1,
32
+ "primary_weapon": 0
33
+ }
34
+
35
+ SUFFIX_MAP = {
36
+ 3: 'armor',
37
+ 2: 'armor',
38
+ 6: 'armor',
39
+ 10: 'armor',
40
+ 8: 'armor',
41
+ 9: 'armor',
42
+ 4: 'trinket',
43
+ 7: 'trinket',
44
+ 5: 'trinket',
45
+ 1: 'weapon',
46
+ 0: 'weapon'
47
+ }
48
+ SPECIAL_ENCHANT_MAP = {
49
+ "3": {
50
+ 12800: "15436-11",
51
+ 11500: "15436-10",
52
+ 10600: "15436-9"
53
+ },
54
+ "2": {
55
+ 12800: "22151-11",
56
+ 11500: "22151-10",
57
+ 10600: "22151-9"
58
+ },
59
+ "6": {
60
+ 0: "22169"
61
+ },
62
+ "10": {
63
+ 0: "22166"
64
+ },
65
+ "9": {
66
+ 0: "33247"
67
+ },
68
+ }
69
+
70
+ equip_min_level = 11000
71
+ equip_params = {
72
+ "client": "std",
73
+ "pv_type": 1,
74
+ "pz": 1,
75
+ "page": 1,
76
+ "per": 300,
77
+ "min_level": 9000,
78
+ "max_level": 15000
79
+ }
80
+
81
+ enchant_params = {
82
+ "client": "std",
83
+ "subtype": 1,
84
+ "latest_enhance": 1
85
+ }
86
+
87
+
88
+ # @cache
89
+ def get_equips_list(position):
90
+ position_id = POSITION_MAP[position]
91
+ url = f"https://node.jx3box.com/equip/{SUFFIX_MAP[position_id]}"
92
+ params = equip_params.copy()
93
+ params['position'] = position_id
94
+ equips = []
95
+ res = requests.get(url, params=params).json()
96
+ equips.extend(res['list'])
97
+ while res['pages'] > params['page']:
98
+ params['page'] += 1
99
+ res = requests.get(url, params=params).json()
100
+ equips.extend(res['list'])
101
+ return equips
102
+
103
+
104
+ @cache
105
+ def get_enchants_list(position):
106
+ position_id = POSITION_MAP[position]
107
+ url = f"https://node.jx3box.com/enchant/primary"
108
+ params = enchant_params.copy()
109
+ params['position'] = position_id
110
+ res = requests.get(url, params=params)
111
+ enchants = [e for e in sorted(res.json(), key=lambda x: x['Score'], reverse=True) if
112
+ e['Attribute1ID'] in ATTR_TYPE_MAP]
113
+ return enchants
114
+
115
+
116
+ def get_stones_list():
117
+ url = "https://node.jx3box.com/enchant/stone"
118
+
119
+ result = {}
120
+ for level in tqdm(range(MAX_STONE_LEVEL)):
121
+ level = level + 1
122
+ stones = []
123
+ params = {
124
+ "client": "std",
125
+ "level": level,
126
+ "page": 1,
127
+ "per": 100
128
+ }
129
+ res = requests.get(url, params=params).json()
130
+ stones.extend(res['list'])
131
+ while res['pages'] > params['page']:
132
+ params['page'] += 1
133
+ res = requests.get(url, params=params).json()
134
+ stones.extend(res['list'])
135
+
136
+ return result
137
+
138
+
139
+ if __name__ == '__main__':
140
+ if not os.path.exists(EQUIPMENTS_DIR):
141
+ os.makedirs(EQUIPMENTS_DIR)
142
+ if not os.path.exists(ENCHANTS_DIR):
143
+ os.makedirs(ENCHANTS_DIR)
144
+
145
+ for pos in tqdm(POSITION_MAP):
146
+ json.dump(
147
+ get_equips_list(pos),
148
+ open(os.path.join(EQUIPMENTS_DIR, pos), "w", encoding="utf-8"), ensure_ascii=False
149
+ )
150
+ json.dump(
151
+ get_enchants_list(pos),
152
+ open(os.path.join(ENCHANTS_DIR, pos), "w", encoding="utf-8"), ensure_ascii=False
153
+ )
154
+
155
+ json.dump(get_stones_list(), open(STONES_DIR, "w", encoding="utf-8"), ensure_ascii=False)
parse.py CHANGED
@@ -11,7 +11,7 @@ class Parser:
11
  self.skills = skills
12
  self.buffs = buffs
13
 
14
- self.summary = {}
15
  self.status = {}
16
 
17
  self.start_time = 0
@@ -19,9 +19,9 @@ class Parser:
19
 
20
  def parse_time(self, detail, timestamp):
21
  if detail[1]:
22
- self.start_time = timestamp
23
  else:
24
- self.end_time = timestamp
25
  return True
26
 
27
  def parse_buff(self, detail):
@@ -33,26 +33,27 @@ class Parser:
33
  else:
34
  self.status[(buff_id, buff_level)] = buff_stack
35
 
36
- def parse_skill(self, detail):
37
  skill = detail[4], detail[5]
38
  if skill[0] not in self.skills:
39
  return
40
 
41
- if skill not in self.summary:
42
- self.summary[skill] = {}
43
  status = tuple(
44
  (buff_id, buff_level, buff_stack) for (buff_id, buff_level), buff_stack in self.status.items()
45
  )
46
- if status not in self.summary[skill]:
47
- self.summary[skill][status] = 0
48
- self.summary[skill][status] += 1
49
 
50
- def __call__(self, logs):
51
- for row in logs:
 
52
  if row[4] == "5" and self.parse_time(unserialize(row[-1]), row[3]):
53
  break
54
  elif row[4] == "13":
55
  self.parse_buff(unserialize(row[-1]))
56
  elif row[4] == "21":
57
- self.parse_skill(unserialize(row[-1]))
58
- return self.summary
 
11
  self.skills = skills
12
  self.buffs = buffs
13
 
14
+ self.records = {}
15
  self.status = {}
16
 
17
  self.start_time = 0
 
19
 
20
  def parse_time(self, detail, timestamp):
21
  if detail[1]:
22
+ self.start_time = int(timestamp)
23
  else:
24
+ self.end_time = int(timestamp)
25
  return True
26
 
27
  def parse_buff(self, detail):
 
33
  else:
34
  self.status[(buff_id, buff_level)] = buff_stack
35
 
36
+ def parse_skill(self, detail, timestamp):
37
  skill = detail[4], detail[5]
38
  if skill[0] not in self.skills:
39
  return
40
 
41
+ if skill not in self.records:
42
+ self.records[skill] = {}
43
  status = tuple(
44
  (buff_id, buff_level, buff_stack) for (buff_id, buff_level), buff_stack in self.status.items()
45
  )
46
+ if status not in self.records[skill]:
47
+ self.records[skill][status] = []
48
+ self.records[skill][status].append(int(timestamp) - self.start_time)
49
 
50
+ def __call__(self, file_name):
51
+ for line in open(file_name):
52
+ row = line.split("\t")
53
  if row[4] == "5" and self.parse_time(unserialize(row[-1]), row[3]):
54
  break
55
  elif row[4] == "13":
56
  self.parse_buff(unserialize(row[-1]))
57
  elif row[4] == "21":
58
+ self.parse_skill(unserialize(row[-1]), row[3])
59
+ return self.records
schools/first/__init__.py CHANGED
@@ -0,0 +1,2 @@
 
 
 
1
+ from schools.first.skills import SKILLS
2
+ from schools.first.buffs import BUFFS
schools/first/attribute.py CHANGED
@@ -1,27 +1,27 @@
1
- from base.attribute import Attribute
2
  from base.constant import *
3
 
4
 
5
- class BeiAoJue(Attribute):
6
  STRENGTH_TO_ATTACK_POWER = 1587 / BINARY_SCALE
7
  STRENGTH_TO_OVERCOME = 369 / BINARY_SCALE
8
 
9
  def __init__(self):
10
  super().__init__()
11
  self.physical_attack_power_base += 3725
12
- self.pve_addition += 143 / BINARY_SCALE
13
 
14
- self.grad_attrs = [
15
- "agility_base",
16
- "strength_base",
17
- "surplus",
18
- "strain_base",
19
- "physical_attack_power_base",
20
- "physical_critical_strike_base",
21
- "physical_critical_power_base",
22
- "physical_overcome_base",
23
- "weapon_damage_base"
24
- ]
25
 
26
  @property
27
  def strength(self):
@@ -36,38 +36,3 @@ class BeiAoJue(Attribute):
36
  self._extra_physical_overcome = int(strength * self.STRENGTH_TO_OVERCOME)
37
  self.base_physical_overcome = self._physical_overcome_base + strength * STRENGTH_TO_OVERCOME
38
 
39
- @property
40
- def attack_power(self):
41
- return self.physical_attack_power
42
-
43
- @property
44
- def critical_strike(self):
45
- return self.physical_critical_strike
46
-
47
- @property
48
- def critical_power(self):
49
- return self.physical_critical_power
50
-
51
- @property
52
- def overcome(self):
53
- return self.physical_overcome
54
-
55
- @property
56
- def shield_ignore(self):
57
- return self.physical_shield_ignore
58
-
59
- @property
60
- def damage_addition(self):
61
- return self.physical_damage_addition
62
-
63
- @property
64
- def shield_base(self):
65
- return self.physical_shield_base
66
-
67
- @property
68
- def shield_gain(self):
69
- return self.physical_shield_gain
70
-
71
- @property
72
- def vulnerable(self):
73
- return self.physical_vulnerable
 
1
+ from base.attribute import PhysicalAttribute
2
  from base.constant import *
3
 
4
 
5
+ class BeiAoJue(PhysicalAttribute):
6
  STRENGTH_TO_ATTACK_POWER = 1587 / BINARY_SCALE
7
  STRENGTH_TO_OVERCOME = 369 / BINARY_SCALE
8
 
9
  def __init__(self):
10
  super().__init__()
11
  self.physical_attack_power_base += 3725
12
+ self.pve_addition += 143
13
 
14
+ self.grad_attrs = {
15
+ "agility_base": MAJOR_DELTA,
16
+ "strength_base": MAJOR_DELTA,
17
+ "surplus": MINOR_DELTA,
18
+ "strain_base": MINOR_DELTA,
19
+ "physical_attack_power_base": PHYSICAL_DELTA,
20
+ "physical_critical_strike_base": MINOR_DELTA,
21
+ "physical_critical_power_base": MINOR_DELTA,
22
+ "physical_overcome_base": MINOR_DELTA,
23
+ "weapon_damage_base": WEAPON_DELTA
24
+ }
25
 
26
  @property
27
  def strength(self):
 
36
  self._extra_physical_overcome = int(strength * self.STRENGTH_TO_OVERCOME)
37
  self.base_physical_overcome = self._physical_overcome_base + strength * STRENGTH_TO_OVERCOME
38
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
schools/first/buffs.py CHANGED
@@ -1,6 +1,6 @@
1
  from base.buff import Buff
2
 
3
- buffs = {
4
  18384: {
5
  "buff_name": "含风",
6
  "gain_attributes": {
@@ -27,7 +27,7 @@ buffs = {
27
  }
28
  }
29
 
30
- for buff_id, detail in buffs.items():
31
- buffs[buff_id] = Buff(buff_id, detail.pop("buff_name"))
32
  for attr, value in detail.items():
33
- setattr(buffs[buff_id], attr, value)
 
1
  from base.buff import Buff
2
 
3
+ BUFFS = {
4
  18384: {
5
  "buff_name": "含风",
6
  "gain_attributes": {
 
27
  }
28
  }
29
 
30
+ for buff_id, detail in BUFFS.items():
31
+ BUFFS[buff_id] = Buff(buff_id, detail.pop("buff_name"))
32
  for attr, value in detail.items():
33
+ setattr(BUFFS[buff_id], attr, value)
schools/first/skills.py CHANGED
@@ -1,6 +1,6 @@
1
  from base.skill import PhysicalDamage, PhysicalDotDamage
2
 
3
- skills = {
4
  32823: {
5
  "skill_class": PhysicalDamage,
6
  "skill_name": "破",
@@ -282,7 +282,7 @@ skills = {
282
  }
283
  }
284
 
285
- for skill_id, detail in skills.items():
286
- skills[skill_id] = detail.pop('skill_class')(skill_id, detail.pop('skill_name'))
287
  for attr, value in detail.items():
288
- setattr(skills[skill_id], attr, value)
 
1
  from base.skill import PhysicalDamage, PhysicalDotDamage
2
 
3
+ SKILLS = {
4
  32823: {
5
  "skill_class": PhysicalDamage,
6
  "skill_name": "破",
 
282
  }
283
  }
284
 
285
+ for skill_id, detail in SKILLS.items():
286
+ SKILLS[skill_id] = detail.pop('skill_class')(skill_id, detail.pop('skill_name'))
287
  for attr, value in detail.items():
288
+ setattr(SKILLS[skill_id], attr, value)
schools/first/test.py CHANGED
@@ -1,8 +1,8 @@
1
  from base.calculator import analyze_details
2
  from parse import Parser
3
  from schools.first.attribute import BeiAoJue
4
- from schools.first.buffs import buffs
5
- from schools.first.skills import skills
6
 
7
 
8
  if __name__ == '__main__':
@@ -17,7 +17,7 @@ if __name__ == '__main__':
17
  attribute.physical_overcome_base += 24303
18
  attribute.physical_critical_power_base += 7905
19
 
20
- parser = Parser(skills, buffs)
21
- summary = parser([line.split("\t") for line in open("logs.jcl")])
22
  analyze_details(parser, attribute)
23
- print(parser.summary)
 
1
  from base.calculator import analyze_details
2
  from parse import Parser
3
  from schools.first.attribute import BeiAoJue
4
+ from schools.first.buffs import BUFFS
5
+ from schools.first.skills import SKILLS
6
 
7
 
8
  if __name__ == '__main__':
 
17
  attribute.physical_overcome_base += 24303
18
  attribute.physical_critical_power_base += 7905
19
 
20
+ parser = Parser(SKILLS, BUFFS)
21
+ parser("logs.jcl")
22
  analyze_details(parser, attribute)
23
+ print(parser.records)