Passed
Push — master ( bb5d68...d9c4a7 )
by Nico
56:35 queued 26:36
created

TalSelectedTech::getDescription()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 0
dl 0
loc 3
ccs 0
cts 2
cp 0
crap 2
rs 10
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Stu\Module\Research;
6
7
use Stu\Orm\Entity\ResearchedInterface;
8
use Noodlehaus\ConfigInterface;
9
use RuntimeException;
10
use Stu\Module\Tal\StatusBarColorEnum;
11
use Stu\Module\Tal\TalStatusBar;
12
use Stu\Orm\Entity\BuildingInterface;
13
use Stu\Orm\Entity\ResearchDependencyInterface;
14
use Stu\Orm\Entity\ResearchInterface;
15
use Stu\Orm\Entity\UserInterface;
16
use Stu\Orm\Repository\BuildingRepositoryInterface;
17
use Stu\Orm\Repository\ResearchDependencyRepositoryInterface;
18
use Stu\Orm\Repository\ResearchedRepositoryInterface;
19
use Stu\Orm\Repository\ResearchRepositoryInterface;
20
21
final class TalSelectedTech implements TalSelectedTechInterface
22
{
23
    private ResearchInterface $research;
24
25
    private UserInterface $currentUser;
26
27
    private ResearchRepositoryInterface $researchRepository;
28
29
    private ResearchedRepositoryInterface $researchedRepository;
30
31
    private ResearchDependencyRepositoryInterface $researchDependencyRepository;
32
33
    private BuildingRepositoryInterface $buildingRepository;
34
35
    private ConfigInterface $config;
36
37
    private ?ResearchedInterface $state = null;
38
39
    /** @var null|array<string, TechDependency> */
40
    private ?array $excludes = null;
41
42
    /** @var null|array<string, TechDependency> */
43
    private ?array $dependencies = null;
44
45
    public function __construct(
46
        ResearchRepositoryInterface $researchRepository,
47
        ResearchedRepositoryInterface $researchedRepository,
48
        ResearchDependencyRepositoryInterface $researchDependencyRepository,
49
        BuildingRepositoryInterface $buildingRepository,
50
        ResearchInterface $research,
51
        UserInterface $currentUser,
52
        ConfigInterface $config
53
    ) {
54
        $this->researchRepository = $researchRepository;
55
        $this->researchedRepository = $researchedRepository;
56
        $this->researchDependencyRepository = $researchDependencyRepository;
57
        $this->buildingRepository = $buildingRepository;
58
        $this->research = $research;
59
        $this->currentUser = $currentUser;
60
        $this->config = $config;
61
    }
62
63
    public function getResearch(): ResearchInterface
64
    {
65
        return $this->research;
66
    }
67
68
    public function getResearchState(): ?ResearchedInterface
69
    {
70
        if ($this->state === null) {
71
            $this->state = $this->researchedRepository->getFor(
72
                $this->research->getId(),
73
                $this->currentUser->getId()
74
            );
75
        }
76
        return $this->state;
77
    }
78
79
    public function getDistinctExcludeNames(): array
80
    {
81
        if ($this->excludes === null) {
82
            $result = [];
83
84
            $techList = $this->researchDependencyRepository->getExcludesByResearch($this->research->getId());
85
86
            array_walk(
87
                $techList,
88
                function (ResearchDependencyInterface $dependecy) use (&$result): void {
89
                    $name = $dependecy->getResearchDependOn()->getName();
90
91
                    if (!array_key_exists($name, $result) && $name !== $this->research->getName()) {
92
                        $result[$name] = new TechDependency($name, $dependecy->getResearchDependOn()->getCommodity());
93
                    }
94
                }
95
            );
96
97
            $this->excludes = $result;
98
        }
99
        return $this->excludes;
0 ignored issues
show
Bug Best Practice introduced by
The expression return $this->excludes could return the type null which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
100
    }
101
102
    public function hasExcludes(): bool
103
    {
104
        return $this->getDistinctExcludeNames() !== [];
105
    }
106
107
    public function getDistinctPositiveDependencyNames(): array
108
    {
109
        if ($this->dependencies === null) {
110
            $result = [];
111
112
            $techList = $this->researchRepository->getPossibleResearchByParent(
113
                $this->research->getId()
114
            );
115
116
            array_walk(
117
                $techList,
118
                function (ResearchInterface $research) use (&$result): void {
119
                    $name = $research->getName();
120
121
                    if (!array_key_exists($name, $result) && $name !== $this->research->getName()) {
122
                        $result[$name] = new TechDependency($name, $research->getCommodity());
123
                    }
124
                }
125
            );
126
127
            $this->dependencies = $result;
128
        }
129
        return $this->dependencies;
0 ignored issues
show
Bug Best Practice introduced by
The expression return $this->dependencies could return the type null which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
130
    }
131
132
    public function hasPositiveDependencies(): bool
133
    {
134
        return $this->getDistinctPositiveDependencyNames() !== [];
135
    }
136
137
    public function getDonePoints(): int
138
    {
139
        $researchState = $this->getResearchState();
140
141
        return $researchState === null
142
            ? $this->getPoints()
143
            : $this->getPoints() - $researchState->getActive();
144
    }
145
146
    private function getPoints(): int
147
    {
148
        return $this->research->getPoints();
149
    }
150
151
    public function isResearchFinished(): bool
152
    {
153
        $researchState = $this->getResearchState();
154
155
        return $researchState === null
156
            ? false
157
            : $researchState->getFinished() > 0;
158
    }
159
160
    public function getBuilding(): ?BuildingInterface
161
    {
162
        $buildings = $this->buildingRepository->getByResearch($this->getResearch());
163
164
        if (empty($buildings)) {
165
            return null;
166
        }
167
168
        return current($buildings);
169
    }
170
171
    public function getStatusBar(): string
172
    {
173
        $researchState = $this->getResearchState();
174
        if ($researchState === null) {
175
            throw new RuntimeException('can not call when no researchState present');
176
        }
177
178
        return (new TalStatusBar())
179
            ->setColor(StatusBarColorEnum::STATUSBAR_BLUE)
180
            ->setLabel(_('Forschung'))
181
            ->setMaxValue($this->research->getPoints())
182
            ->setValue($this->research->getPoints() - $researchState->getActive())
183
            ->setSizeModifier(2)
184
            ->render();
185
    }
186
187
    public function getWikiLink(): string
188
    {
189
        return sprintf(
190
            '%s/index.php?title=Forschung:%s',
191
            $this->config->get('wiki.base_url'),
192
            str_replace(' ', '_', $this->research->getName())
193
        );
194
    }
195
}
196