Completed
Pull Request — master (#293)
by
unknown
07:29
created

ScriptVariableUpdateFactory::onEverySecond()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
dl 0
loc 4
rs 10
c 0
b 0
f 0
ccs 0
cts 2
cp 0
cc 1
eloc 1
nc 1
nop 0
crap 2
1
<?php
2
3
namespace eXpansion\Framework\Core\Plugins\Gui;
4
5
use eXpansion\Framework\Core\DataProviders\Listener\ListenerInterfaceExpTimer;
6
use eXpansion\Framework\Core\DataProviders\Listener\ListenerInterfaceExpUserGroup;
7
use eXpansion\Framework\Core\Model\Gui\ManialinkInterface;
8
use eXpansion\Framework\Core\Model\Gui\Script\Variable;
9
use eXpansion\Framework\Core\Model\Gui\WidgetFactoryContext;
10
use eXpansion\Framework\Core\Model\UserGroups\Group;
11
use FML\Script\Script;
12
use FML\Script\ScriptLabel;
13
14
/**
15
 * Class ScriptVariableUpdateFactory
16
 *
17
 * @author    de Cramer Oliver<[email protected]>
18
 * @copyright 2018 eXpansion
19
 * @package eXpansion\Framework\Core\Plugins\Gui
20
 */
21
class ScriptVariableUpdateFactory extends WidgetFactory implements ListenerInterfaceExpTimer, ListenerInterfaceExpUserGroup
22
{
23
    /** @var Variable[] */
24
    protected $variables = [];
25
26
    /** @var Variable */
27
    protected $checkVariable;
28
29
    /** @var float */
30
    protected $maxUpdateFrequency;
31
32
    /** @var Variable */
33
    protected $checkOldVariable;
34
35
    /** @var mixed[][] */
36
    protected $queuedForUpdate = [];
37
38
    /**
39
     * ScriptVariableUpdateFactory constructor.
40
     *
41
     * @param                      $name
42
     * @param array                $variables
43
     * @param float                $maxUpdateFrequency
44
     * @param WidgetFactoryContext $context
45
     */
46
    public function __construct(
47
        $name,
48
        array $variables,
49
        float $maxUpdateFrequency = 0.250,
50
        WidgetFactoryContext $context
51
    ) {
52
        parent::__construct($name, 0, 0, 0, 0, $context);
53
        $this->maxUpdateFrequency = $maxUpdateFrequency;
54
55
        foreach ($variables as $variable) {
56
            $this->variables[$variable['name']] = new Variable(
57
                $variable['name'],
58
                $variable['type'],
59
                'This',
60
                $variable['default']
61
            );
62
        }
63
64
        $uniqueId = uniqid('exp_', true);
65
        $this->checkVariable = new Variable('check', 'Text', 'This', "\"$uniqueId\"");
66
        $this->checkOldVariable = new Variable('check_old', 'Text', 'Page', "\"$uniqueId\"");
67
    }
68
69
    /**
70
     * Update script value.
71
     *
72
     * @param Group  $group
73
     * @param string $variableCode
74
     * @param string $newValue
75
     */
76
    public function updateValue($group, $variableCode, $newValue)
77
    {
78
        $variable = clone $this->getVariable($variableCode);
79
        $variable->setValue($newValue);
80
81
        if (!isset($this->queuedForUpdate[$group->getName()])) {
82
            $this->queuedForUpdate[$group->getName()]['time'] = microtime(true);
83
        }
84
85
        $checkVariable = clone $this->checkVariable;
86
        $uniqueId = uniqid('exp_', true);
87
        $checkVariable->setValue("\".$uniqueId\"");
88
        $this->queuedForUpdate[$group->getName()]['group'] = $group;
89
        $this->queuedForUpdate[$group->getName()]['variables'][$variableCode] = $variable;
90
        $this->queuedForUpdate[$group->getName()]['check'] = $checkVariable;
91
    }
92
93
    /**
94
     * Get a variable.
95
     *
96
     * @param $variable
97
     *
98
     * @return Variable
99
     */
100
    public function getVariable($variable)
101
    {
102
        return $this->variables[$variable];
103
    }
104
105
    /**
106
     * Get variable to use to check if data needs to be updated.
107
     *
108
     * @return Variable
109
     */
110
    public function getCheckVariable()
111
    {
112
        return $this->checkVariable;
113
    }
114
115
    /**
116
     * Get script to execute when there is a change.
117
     *
118
     * @param string $toExecute Script to execute.
119
     *
120
     * @return string
121
     */
122
    public function getScriptOnChange($toExecute)
123
    {
124
        return <<<EOL
125
            if ({$this->checkVariable->getVariableName()} != {$this->checkOldVariable->getVariableName()}) {
126
                {$this->checkOldVariable->getVariableName()} = {$this->checkVariable->getVariableName()};
127
                $toExecute
128
            }
129
EOL;
130
    }
131
132
    /**
133
     * Get initialization script.
134
     *
135
     * @param bool $defaultValues
136
     * @return string
137
     */
138
    public function getScriptInitialization($defaultValues = false)
139
    {
140
        $scriptContent = '';
141
        foreach ($this->variables as $variable) {
142
            $scriptContent .= $variable->getScriptDeclaration()."\n";
143
            if ($defaultValues) {
144
                $scriptContent .= $variable->getScriptValueSet()."\n";
145
            }
146
        }
147
        $scriptContent .= $this->checkVariable->getScriptDeclaration()."\n";
148
        $scriptContent .= $this->checkOldVariable->getScriptDeclaration()."\n";
149
        if ($defaultValues) {
150
            $scriptContent .= $this->checkVariable->getScriptValueSet()."\n";
151
            $scriptContent .= $this->checkOldVariable->getScriptValueSet()."\n";
152
        }
153
154
        return $scriptContent;
155
    }
156
157
    /**
158
     * @inheritdoc
159
     */
160
    protected function updateContent(ManialinkInterface $manialink)
161
    {
162
        // Empty existing script.
163
        parent::updateContent($manialink);
164
        $manialink->getFmlManialink()->removeAllChildren();
165
166
        // Get script with new values.
167
        $scriptContent = $this->getScriptInitialization(true);
168
169
        // Update FML Manialink
170
        $script = new Script();
171
        $script->addCustomScriptLabel(ScriptLabel::OnInit, $scriptContent);
172
        $manialink->getFmlManialink()->setScript($script);
173
174
        $this->queuedForUpdate = null;
0 ignored issues
show
Documentation Bug introduced by
It seems like null of type null is incompatible with the declared type array<integer,array<integer,*>> of property $queuedForUpdate.

Our type inference engine has found an assignment to a property that is incompatible with the declared type of that property.

Either this assignment is in error or the assigned type should be added to the documentation/type hint for that property..

Loading history...
175
    }
176
177
    /**
178
     * @inheritdoc
179
     */
180
    public function onPreLoop()
181
    {
182
        if (!empty($this->queuedForUpdate)) {
183
            foreach ($this->queuedForUpdate as $groupName => $updateData) {
184
                if (microtime(true) - $updateData['time'] >= $this->maxUpdateFrequency) {
185
                    // Save original data.
186
                    $variables = $this->variables;
187
                    $checkVariable = $this->checkVariable;
188
189
                    // Update variables temporarily with player data.
190
                    $this->variables = [];
191
                    foreach ($updateData['variables'] as $variableCode => $variable) {
192
                        $this->variables[$variableCode] = $variable;
193
                    }
194
                    $this->checkVariable = $updateData['check'];
195
                    $this->create($updateData['group']);
196
197
                    // Put back original data.
198
                    $this->variables = $variables;
199
                    $this->checkVariable = $checkVariable;
200
201
                    unset($this->queuedForUpdate[$groupName]);
202
                }
203
            }
204
        }
205
    }
206
207
    /**
208
     * @inheritdoc
209
     */
210
    public function onPostLoop()
211
    {
212
        // Nothing
213
    }
214
215
    /**
216
     * @inheritdoc
217
     */
218
    public function onEverySecond()
219
    {
220
221
    }
222
223
    /**
224
     * @inheritdoc
225
     */
226
    public function onExpansionGroupAddUser(Group $group, $loginAdded)
227
    {
228
        // This will be handled by the gui handler.
229
    }
230
231
    /**
232
     * @inheritdoc
233
     */
234
    public function onExpansionGroupRemoveUser(Group $group, $loginRemoved)
235
    {
236
        // This will be handled by the gui handler.
237
    }
238
239
    /**
240
     * @inheritdoc
241
     */
242
    public function onExpansionGroupDestroy(Group $group, $lastLogin)
243
    {
244
        if (isset($this->queuedForUpdate[$group->getName()])) {
245
            unset($this->queuedForUpdate[$group->getName()]);
246
        }
247
    }
248
}
249