Completed
Pull Request — master (#100)
by
unknown
02:35
created

layoutScrollable::prepare()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 6
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
c 0
b 0
f 0
dl 0
loc 6
rs 9.4285
ccs 0
cts 6
cp 0
cc 1
eloc 4
nc 1
nop 1
crap 2
1
<?php
2
3
namespace eXpansion\Framework\Gui\Layouts;
4
5
use eXpansion\Framework\Gui\Components\abstractUiElement;
6
use eXpansion\Framework\Gui\Components\uiScrollbar;
7
use FML\Controls\Frame;
8
use FML\Controls\Quad;
9
use FML\Script\Features\ScriptFeature;
10
use FML\Script\Script;
11
use FML\Script\ScriptLabel;
12
use FML\Types\Renderable;
13
use FML\Types\ScriptFeatureable;
14
15
class layoutScrollable extends abstractUiElement implements Renderable, ScriptFeatureable
16
{
17
18
    protected $force = false;
19
    protected $_X = 0;
20
    protected $_Y = 0;
21
    protected $offset = 0;
22
    protected $scrollbarH = true;
23
    protected $scrollbarV = true;
24
    protected $parentFrame = null;
25
    protected $frame_posX = 0;
26
    protected $frame_posY = 0;
27
28
    /**
29
     * layoutScrollable constructor.
30
     * @param $frame
31
     * @param $sizeX
32
     * @param $sizeY
33
     */
34
    public function __construct($frame, $sizeX, $sizeY)
35
    {
36
        $this->parentFrame = $frame;
37
        $this->frame_posX = $frame->getX();
38
        $this->frame_posY = $frame->getY();
39
        $this->setSize($sizeX, $sizeY);
40
41
        $frame->setPosition(0, 0);
42
    }
43
44
    /**
45
     * @param bool $x
46
     * @param bool $y
47
     */
48
    public function setAxis($x, $y)
49
    {
50
        $this->scrollbarH = $x;
51
        $this->scrollbarV = $y;
52
    }
53
54
    public function forceContainerSize($x, $y)
55
    {
56
        $this->force = true;
57
        $this->_X = $x;
58
        $this->_Y = $y;
59
    }
60
61
    /**
62
     * Render the XML element
63
     *
64
     * @param \DOMDocument $domDocument DOMDocument for which the XML element should be rendered
65
     * @return \DOMElement
66
     */
67
    public function render(\DOMDocument $domDocument)
68
    {
69
        $container = new Frame();
70
        $container->setPosition($this->frame_posX, $this->frame_posY);
71
72
        $quad = new Quad();
73
        $quad->setStyles('Bgs1', 'BgColorContour')
74
            ->setSize($this->getWidth(), $this->getHeight());
75
76
        $contentFrame = new Frame();
77
        $contentFrame->addChild($this->parentFrame);
78
79
        $container->addChild($quad);
80
        $container->addChild($contentFrame);
81 View Code Duplication
        if ($this->scrollbarV) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
82
            $contentFrame->setSize($this->width - 5, $this->height);
83
            $this->offset = 5;
84
            $container->addChild(new uiScrollbar(
85
                "Y",
86
                $this->getWidth(),
87
                0,
88
                10,
89
                $this->getHeight()
90
            ));
91
        }
92
93 View Code Duplication
        if ($this->scrollbarH) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
94
            $contentFrame->setSize($this->width - 5, $this->height - 5);
95
            $container->addChild(new uiScrollbar(
96
                "X",
97
                0,
98
                -$this->getHeight(),
99
                10,
100
                $this->getWidth() - $this->offset
101
            ));
102
        }
103
104
105
        return $container->render($domDocument);
106
    }
107
108
    /**
109
     * Get the Script Features
110
     * @todo write recursion for frames...
111
     * @return ScriptFeature[]
112
     */
113
    public function getScriptFeatures()
114
    {
115
        $features = [];
116
        if ($this->parentFrame instanceof ScriptFeatureable) {
117
            $features[] = $this->parentFrame->getScriptFeatures();
118
        }
119
        $features[] = $this;
120
121
        return ScriptFeature::collect($features);
122
    }
123
124
125
    /**
126
     * Prepare the given Script for rendering by adding the needed Labels, etc.
127
     *
128
     * @param Script $script Script to prepare
129
     * @return static
130
     */
131
    public function prepare(Script $script)
132
    {
133
        $script->addCustomScriptLabel(ScriptLabel::MouseClick, $this->getScriptMouseClick());
134
        $script->addCustomScriptLabel(ScriptLabel::OnInit, $this->getScriptInit());
135
        $script->addCustomScriptLabel(ScriptLabel::Loop, $this->getScriptLoop());
136
    }
137
138
    protected function getScriptInit()
139
    {
140
        $offset = number_format($this->offset, 1, ".", "");
141
142
        return /** @lang textmate */
143
            <<<EOL
144
            
145
            declare CMlFrame exp_scroll_frame = Null;
146
            declare CMlFrame exp_scroll_content = Null;
147
            declare Vec2 exp_scroll_content_size = <0.,0.>; 
148
            declare Boolean exp_scroll_activeY = False;
149
            declare Boolean exp_scroll_activeX = False;
150
            declare Vec2 exp_scroll_pos = <0.,0.>;
151
            declare Real exp_scroll_offset = $offset;
152
EOL;
153
    }
154
155
156
    protected function getScriptMouseClick()
157
    {
158
        return /** @lang textmate */
159
            <<<EOL
160
            
161
            if (Event.Control != Null && Event.Control.HasClass("uiScrollbar") )  {
162
                if (Event.Control.DataAttributeGet("axis") == "X") {
163
                    exp_scroll_activeX = True;
164
                    log(Now ^ "X");
165
                } else {
166
                    exp_scroll_activeY = True;																
167
                }
168
                exp_scroll_frame = Event.Control.Parent;
169
                exp_scroll_pos = <MouseX, MouseY> - Event.Control.RelativePosition_V3 ;
170
                exp_scroll_content = (exp_scroll_frame.Parent.Controls[1] as CMlFrame); // gets the bounding frame				
171
                exp_scroll_content_size = exp_scroll_content.Controls[0].Size;
172
                log(exp_scroll_content_size);
173
            }
174
EOL;
175
    }
176
177
178
    protected function getScriptLoop()
179
    {
180
        return /** @lang textmate */
181
            <<<EOL
182
183
        if (exp_scroll_activeY) {		
184
					declare Real pos = (MouseY - exp_scroll_pos.Y) ;
185
					declare Real upperLimit = exp_scroll_frame.RelativePosition_V3.Y - exp_scroll_frame.RelativePosition_V3.Y - 5.;
186
					declare Real lowerLimit =  upperLimit - exp_scroll_frame.Controls[3].Size.Y + exp_scroll_frame.Controls[0].Size.Y + 10.;
187
					
188
					if (pos > upperLimit) {
189
						pos = upperLimit;
190
					}
191
															
192
					if (pos < lowerLimit)  {  
193
						pos = lowerLimit;
194
					}
195
					
196
				declare Real start = (upperLimit - pos);
197
				declare Real diff = MathLib::Abs(lowerLimit - upperLimit);
198
								
199
				exp_scroll_frame.Controls[0].RelativePosition_V3.Y = pos; // update scrollbar position												
200
				exp_scroll_content.Controls[0].RelativePosition_V3.Y = (start / diff) * (exp_scroll_content_size.Y - exp_scroll_frame.Parent.Controls[0].Size.Y + 10.);  //  gets the content frame
201
		}
202
		
203
		if (exp_scroll_activeX) {		
204
					declare Real pos = ( MouseX - exp_scroll_pos.X);
205
					declare Real leftLimit = 5.;
206
					declare Real rightLimit =  leftLimit + exp_scroll_frame.Controls[3].Size.X - exp_scroll_frame.Controls[0].Size.X -10.;
207
					
208
					if (pos < leftLimit) {
209
						pos = leftLimit;
210
					}
211
															
212
					if (pos > rightLimit)  {  
213
						pos = rightLimit;
214
					}
215
					
216
				declare Real start =  (leftLimit - pos);
217
				declare Real diff = MathLib::Abs(leftLimit + rightLimit);
218
								
219
				exp_scroll_frame.Controls[0].RelativePosition_V3.X = pos; // update scrollbar position												
220
				exp_scroll_content.Controls[0].RelativePosition_V3.X = (start / diff) * (exp_scroll_content_size.X + 10);  //  gets the content frame
221
		}
222
		
223
		
224
		
225
		if (MouseLeftButton == False)  {
226
			exp_scroll_activeX = False;
227
			exp_scroll_activeY = False;
228
		}
229
230
EOL;
231
    }
232
233
}
234