Function
Dancer 자식..
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
|
// Creates and returns a new dancer object that can step
var makeDancer = (top, left, timeBetweenSteps) => {
const dancer = {};
const createDancerElement = () => {
let elDancer = document.createElement('span');
elDancer.className = 'dancer';
return elDancer;
};
dancer.$node = createDancerElement();
dancer.step = () => {
// the basic dancer doesn't do anything interesting at all on each step,
// it just schedules the next step
setTimeout(dancer.step, timeBetweenSteps);
};
dancer.setPosition = (top, left) => {
// Use css top and left properties to position our <span> tag
Object.assign(dancer.$node.style, {
top: `${top}px`,
left: `${left}px`
});
};
dancer.step();
// now that we have defined the dancer object, we can start setting up important parts of it by calling the methods we wrote
// this one sets the position to some random default point within the body
dancer.setPosition(top, left);
return dancer;
};
|
cs |
makeDancer 를 함수타입으로 객체를 생성한다.
인자로는 top, left, timeBetweenSteps 를 가지고 넣는다.
createDancerElement가 하는 일은 하나의 span태그로 엘리먼트를 만드는 것이다.
dancer.$node 위에서 만든 엘리먼트 만드는 함수를 실행시켜서 대입시킨다.
dancer.step => 자기 자신의 step을 호출, timeBetweenStep 인자값 가져오기 (이건 추후에 부모랑 엮으면서 완성된다.)
dancer.setPosition 메소드를 호출할떄 가져오는 top, left 값을 가지고 Object.assign() 객체를 복사할떄 사용 .. = 으로해버리면 할당 가리키는 것으로 되어버려서 오류가 생긴다.
dancer 노드 스타일과 top left 크기값을 가지고 객체를 만든다..
dancer.step (); makerDancer를 만들때 실행하게 만들기.
마찬가지로 dancer.setPosition(top, left)도 makerDancer를 만들떄 실행하게 만든다.
Dancer의 부모녀석
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
|
var makeBlinkyDancer = (top, left, timeBetweenSteps) => {
const blinkyDancer = makeDancer(top, left, timeBetweenSteps);
// we plan to overwrite the step function below, but we still want the superclass step behavior to work,
// so we must keep a copy of the old version of this function
let oldStep = blinkyDancer.step;
blinkyDancer.step = () => {
// call the old version of step at the beginning of any call to this new version of step
oldStep();
let style = blinkyDancer.$node.style;
style.display = style.display === 'none' ? 'inline-block' : 'none';
};
return blinkyDancer;
};
|
cs |
makeBlinkDancer 이건 makeDancer의 부모이다 .
const blinkyDancer = makeDancer(top , left , timeBetweenSteps); 이걸로 자식의 파라미터를 가지고 온다.
let oldStep = blinkDancer.step; 자식의 step 메소드를 가지고 온다.
blinkDancer.step = () => {
oldStep(); //자식의 메소드를 가지고와서 실행한다.
let style = blinkyDancer.$node.style; //자식노드의 스타일을 가지고 옵니다...
style.display = style.display === 'none' ? 'inline-block' : 'none' //스타일 display 값이 none 이면 inline-block으로 바꾸고 아니면 none으로 바꿉니다. 깜빡깜빡하는 이유이다.
// 자식 step 메소드를 살펴보면 자기자신을 호출한다. 호출에 호출은 반복하기 떄문..
}
그럼 ES5 는 어떤 형식으로 짜여 지게 되는지 살펴보자.
1. Dancer 자식
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
|
function Dancer (top,left,timeBetweenSteps) {
// your code here
this.timeBetweenSteps = timeBetweenSteps;
this.createDancerElement = function(){
let elDancer = document.createElement('img');
elDancer.className = 'dancer';
let src = "img"+Math.floor(Math.random()*7)+".gif";
elDancer.src = src;
return elDancer;
};
this.$node = this.createDancerElement();
this.$node.onclick = function(){
this.src = 'boom.gif';
let nodes = this;
setTimeout(
nodes.remove.bind(this)
,700);
}
this.step();
this.setPosition(top,left);
}
Dancer.prototype.step = function(){
setTimeout(this.step.bind(this),this.timeBetweenSteps)
}
Dancer.prototype.setPosition = function(top,left){
Object.assign(this.$node.style,{
top : `${top}px`,
left : `${left}px`
});
}
|
cs |
function 과 다른점
1. this로 지정해서 할당하도록했다.
2. 함수 메소드 설정시 this.step이 아니라 this.step.bind(this)인 이유는? this.step으로 설정을 하게 되면 window 객체의 step 함수가 호출 된다. 그리고 호출될떄 마다 가리키는 step의 인자값이 다를 수 있기 떄문에 꼭 bind(새로운 메소드를 만드는 함수)를 써서 this를 대입해서 메소드를 만들 필요가 있다.(매우 중요)
3.prototype으로 설정했다. 함수가 생성될떄 오브젝트 링크로 연결되어 있는 프로토타입이다. 형식이 다른 일정 부분을 따로 설명하지 않겠다.
2.부모 객체
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
|
function BlinkyDancer () {
// your code here
Dancer.call(this,...arguments); //Dancer.apply(this,arguments)
//console.log(Dancer.prototype.step);
//this.oldStep = Dancer.prototype.step.bind(this)
}
BlinkyDancer.prototype = Object.create(Dancer.prototype);
BlinkyDancer.prototype.constructor = BlinkyDancer;
BlinkyDancer.prototype.step = function(){
Dancer.prototype.step.call(this);
let style = this.$node.style;
style.display = style.display === 'none' ? 'inline-block' : 'none';
let size = Math.floor(Math.random()*100)+300;
style.width = size+"px";
style.height = size+"px";
let rotate = Math.floor(Math.random()*50);
style.transform = 'rotate( '+rotate+'deg)';
}
|
cs |
Dancer.call(this ,...arguments) 또는 Dancer.apply(this,argument) 이둘의 차이는 mdn 을 참고하면 나온다. 궁금하시면 찾아보시길..
Dancer.call(this,...arguments)가 뜻하는 것은 .. Dancer 함수를 호출한다 그리고 인자값으로 Dancer를 가리키는 값과 추가적으로 가져오는 인자값들을 대입한다.
BlinkyDancer.prototype = Object.create(Dancer.prototype) ; // Dancer.prototype을 가지고 새 객체를 만들어서 프로토타입에 떄려넣는다.
BlinkyDancer.prototype.constructor = BlinkyDancer ; // 자기자신을 생성자로 지정한다.
BlinkyDancer.prototype.step = function(){ }
Dancer.prototype.step.call(this); //Dancer.prototype.step을 호출한다 call을 가지고 그리고 this를 통해서 현재 지정해야되는 인자 값을 가지고옵니다.
ES6
1. Dancer 자식...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
|
class DancerClass {
// your code here
constructor(top,left,timeBetweenSteps){
this.timeBetweenSteps = timeBetweenSteps;
this.createDancerElement = () =>{
let elDancer = document.createElement('span');
elDancer.className = 'dancer';
return elDancer;
}
this.$node = this.createDancerElement();
this.step();
this.setPosition(top,left);
}
step(){
setTimeout(this.step.bind(this), this.timeBetweenSteps);
}
setPosition(top,left) {
Object.assign(this.$node.style,{
top : `${top}px`,
left : `${left}px`
});
}
}
|
cs |
class 타입으로 설정한것 말고는 사실.. ES5와 크게 다를건 없다.
2. 부모객체 BlinkyDancerClass
1
2
3
4
5
6
7
8
9
10
|
class BlinkyDancerClass extends DancerClass{
// your code here
step(){
super.step();
let style = this.$node.style;
style.display = style.display === 'none' ? 'inline-block' : 'none';
}
}
|
cs |
super.step() //자식의 함수를 받아왔다. 이부분이 다르다...
'프로그래밍 언어 > javascript' 카테고리의 다른 글
[javascript] 짝지어 제거하기 (1) | 2020.09.02 |
---|---|
[javascript] CommonJS & Asynchronous (0) | 2020.01.17 |
ES6 vs pseudoclassical(ES5) 상속방법에 대한 비교.. (0) | 2020.01.06 |
[javascript] Order of Execution 문제 (0) | 2020.01.04 |
[javascript] Value vs. Reference 문제 (0) | 2020.01.04 |