Passed
Pull Request — master (#1933)
by Janko
21:56 queued 11:22
created

ShipSystemManager::deactivate()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 10
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 5
CRAP Score 2

Importance

Changes 0
Metric Value
cc 2
eloc 5
nc 2
nop 3
dl 0
loc 10
ccs 5
cts 5
cp 1
crap 2
rs 10
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Stu\Component\Ship\System;
6
7
use Override;
0 ignored issues
show
Bug introduced by
The type Override was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
8
use Stu\Component\Ship\System\Exception\ActivationConditionsNotMetException;
9
use Stu\Component\Ship\System\Exception\AlreadyActiveException;
10
use Stu\Component\Ship\System\Exception\AlreadyOffException;
11
use Stu\Component\Ship\System\Exception\DeactivationConditionsNotMetException;
12
use Stu\Component\Ship\System\Exception\InsufficientCrewException;
13
use Stu\Component\Ship\System\Exception\InsufficientEnergyException;
14
use Stu\Component\Ship\System\Exception\InvalidSystemException;
15
use Stu\Component\Ship\System\Exception\ShipSystemException;
16
use Stu\Component\Ship\System\Exception\SystemCooldownException;
17
use Stu\Component\Ship\System\Exception\SystemDamagedException;
18
use Stu\Component\Ship\System\Exception\SystemNotActivatableException;
19
use Stu\Component\Ship\System\Exception\SystemNotDeactivatableException;
20
use Stu\Component\Ship\System\Exception\SystemNotFoundException;
21
use Stu\Module\Control\StuTime;
22
use Stu\Module\Ship\Lib\ShipWrapperInterface;
23
use Stu\Orm\Entity\ShipInterface;
24
use Stu\Orm\Entity\ShipSystemInterface;
25
26
final class ShipSystemManager implements ShipSystemManagerInterface
27
{
28
    /**
29
     * @param array<ShipSystemTypeInterface> $systemList
30
     */
31 20
    public function __construct(private array $systemList, private StuTime $stuTime) {}
32
33 11
    #[Override]
34
    public function activate(
35
        ShipWrapperInterface $wrapper,
36
        ShipSystemTypeEnum $type,
37
        bool $force = false,
38
        bool $isDryRun = false
39
    ): void {
40 11
        $time = $this->stuTime->time();
41 11
        $system = $this->lookupSystem($type);
42
43 11
        if (!$force) {
44 11
            $this->checkActivationConditions($wrapper, $system, $type, $time);
45
        }
46
47 3
        if ($isDryRun) {
48 1
            return;
49
        }
50
51 2
        $epsSystem = $wrapper->getEpsSystemData();
52 2
        if ($epsSystem !== null) {
53 2
            $epsSystem->lowerEps($system->getEnergyUsageForActivation())->update();
54
        }
55
56
        //cooldown
57 2
        $shipSystem = $wrapper->get()->getSystems()[$type->value] ?? null;
58 2
        if ($shipSystem !== null && $system->getCooldownSeconds() !== null) {
59 1
            $shipSystem->setCooldown($time + $system->getCooldownSeconds());
60
        }
61
62 2
        $system->activate($wrapper, $this);
63
    }
64
65 7
    #[Override]
66
    public function deactivate(ShipWrapperInterface $wrapper, ShipSystemTypeEnum $type, bool $force = false): void
67
    {
68 7
        $system = $this->lookupSystem($type);
69
70 6
        if (!$force) {
71 4
            $this->checkDeactivationConditions($wrapper, $system, $type);
72
        }
73
74 3
        $system->deactivate($wrapper);
75
    }
76
77 2
    #[Override]
78
    public function deactivateAll(ShipWrapperInterface $wrapper): void
79
    {
80 2
        foreach ($wrapper->get()->getSystems() as $shipSystem) {
81
            try {
82 2
                $this->deactivate($wrapper, $shipSystem->getSystemType(), true);
83 1
            } catch (ShipSystemException) {
84 1
                continue;
85
            }
86
        }
87
    }
88
89
    #[Override]
90
    public function getEnergyUsageForActivation(ShipSystemTypeEnum $type): int
91
    {
92
        $system = $this->lookupSystem($type);
93
94
        return $system->getEnergyUsageForActivation();
95
    }
96
97
    #[Override]
98
    public function getEnergyConsumption(ShipSystemTypeEnum $type): int
99
    {
100
        $system = $this->lookupSystem($type);
101
102
        return $system->getEnergyConsumption();
103
    }
104
105 18
    #[Override]
106
    public function lookupSystem(ShipSystemTypeEnum $type): ShipSystemTypeInterface
107
    {
108 18
        $system = $this->systemList[$type->value] ?? null;
109 18
        if ($system === null) {
110 1
            throw new InvalidSystemException();
111
        }
112
113 17
        return $system;
114
    }
115
116 11
    private function checkActivationConditions(
117
        ShipWrapperInterface $wrapper,
118
        ShipSystemTypeInterface $system,
119
        ShipSystemTypeEnum $type,
120
        int $time
121
    ): void {
122 11
        $ship = $wrapper->get();
123 11
        $shipSystem = $ship->getSystems()[$type->value] ?? null;
124 11
        if ($shipSystem === null) {
125 1
            throw new SystemNotFoundException();
126
        }
127
128 10
        if ($shipSystem->getStatus() === 0) {
129 1
            throw new SystemDamagedException();
130
        }
131
132 9
        $mode = $shipSystem->getMode();
133 9
        if ($mode === ShipSystemModeEnum::MODE_ALWAYS_OFF) {
0 ignored issues
show
Bug introduced by
The type Stu\Component\Ship\System\ShipSystemModeEnum was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
134 1
            throw new SystemNotActivatableException();
135
        }
136
137
        if (
138 8
            $mode === ShipSystemModeEnum::MODE_ON
139 8
            ||  $mode === ShipSystemModeEnum::MODE_ALWAYS_ON
140
        ) {
141 1
            throw new AlreadyActiveException();
142
        }
143
144 7
        if (!$ship->hasEnoughCrew()) {
145 1
            throw new InsufficientCrewException();
146
        }
147
148 6
        $epsSystem = $wrapper->getEpsSystemData();
149 6
        if ($epsSystem === null || $epsSystem->getEps() < $system->getEnergyUsageForActivation()) {
150 1
            throw new InsufficientEnergyException($system->getEnergyUsageForActivation());
151
        }
152
153 5
        $cooldown = $shipSystem->getCooldown();
154 5
        if ($cooldown !== null && $cooldown > $time) {
155 1
            throw new SystemCooldownException($cooldown - $time);
156
        }
157
158 4
        $reason = '';
159 4
        if (!$system->checkActivationConditions($wrapper, $reason)) {
160 1
            throw new ActivationConditionsNotMetException($reason);
161
        }
162
    }
163
164 4
    private function checkDeactivationConditions(
165
        ShipWrapperInterface $wrapper,
166
        ShipSystemTypeInterface $system,
167
        ShipSystemTypeEnum $type
168
    ): void {
169 4
        $ship = $wrapper->get();
170 4
        $shipSystem = $ship->getSystems()[$type->value] ?? null;
171 4
        if ($shipSystem === null) {
172
            throw new SystemNotFoundException();
173
        }
174
175 4
        $mode = $shipSystem->getMode();
176 4
        if ($mode === ShipSystemModeEnum::MODE_ALWAYS_ON) {
177 1
            throw new SystemNotDeactivatableException();
178
        }
179
180
        if (
181 3
            $mode === ShipSystemModeEnum::MODE_OFF
182 3
            ||  $mode === ShipSystemModeEnum::MODE_ALWAYS_OFF
183
        ) {
184 1
            throw new AlreadyOffException();
185
        }
186
187 2
        $reason = '';
188 2
        if (!$system->checkDeactivationConditions($wrapper, $reason)) {
189 1
            throw new DeactivationConditionsNotMetException($reason);
190
        }
191
    }
192
193
    #[Override]
194
    public function handleDestroyedSystem(ShipWrapperInterface $wrapper, ShipSystemTypeEnum $type): void
195
    {
196
        $system = $this->lookupSystem($type);
197
198
        $system->handleDestruction($wrapper);
199
    }
200
201
    #[Override]
202
    public function handleDamagedSystem(ShipWrapperInterface $wrapper, ShipSystemTypeEnum $type): void
203
    {
204
        $system = $this->lookupSystem($type);
205
206
        $system->handleDamage($wrapper);
207
    }
208
209
    #[Override]
210
    public function getActiveSystems(ShipInterface $ship, bool $sort = false): array
211
    {
212
        $activeSystems = [];
213
        $prioArray = [];
214
        foreach ($ship->getSystems() as $system) {
215
            if ($system->getMode() > 1) {
216
                $activeSystems[] = $system;
217
                if ($sort) {
218
                    $prioArray[$system->getSystemType()->value] = $this->lookupSystem($system->getSystemType())->getPriority();
219
                }
220
            }
221
        }
222
223
        if ($sort) {
224
            usort(
225
                $activeSystems,
226
                fn(ShipSystemInterface $a, ShipSystemInterface $b): int => $prioArray[$a->getSystemType()->value] <=> $prioArray[$b->getSystemType()->value]
227
            );
228
        }
229
230
        return $activeSystems;
231
    }
232
}
233