본문 바로가기

IT/javascript

계산기 - Vanilla, Vue

반응형

출처 : Vue.js 코딩 공작소

Vanilla

<!DOCTYPE html>
<html>
    <head>
        <title>자바스크립트 계산기</title>
        <style>
            p, input {font-family: monospace;}
            p, { white-space: pre;}
        </style>
    </head>
    <body>
        <div id="myCalc">
            <p>x <input class="calc-x-input" value="0"></p>
            <p>y <input class="calc-y-input" value="0"></p>
            <p>---------------------</p>
            <p>= <span class="calc-result"></span></p>
        </div>
        <script type="text/javascript">
            (function(){
                function Calc(xInput, yInput, output){
                    this.xInput = xInput;
                    this.yInput = yInput;
                    this.output = output;
                }

                Calc.xName = 'xInput';
                Calc.yName = 'yInput';

                Calc.prototype = {
                    render: function(result){
                        this.output.innerText = String(result);
                    }
                };

                function CalcValue(calc, x, y ){
                    this.calc = calc;
                    this.x = x;
                    this.y = y;
                    this.result = x+y;
                }

                CalcValue.prototype = {
                    copyWith: function(name, value){
                        var number = parseFloat(value);

                        if(isNaN(number) || !isFinite(number))
                            return this;

                        if(name == Calc.xName )
                            return new CalcValue(this.calc, number, this.y);

                        if(name == Calc.yName )
                            return new CalcValue(this.calc, this.x , number);

                        return this;
                    },
                    render: function(){
                        this.calc.render(this.result);
                    }
                };

                function initCalc(elem){

                    var calc = new Calc(
                        elem.querySelector('input.calc-x-input'),
                        elem.querySelector('input.calc-y-input'),
                        elem.querySelector('span.calc-result')
                    );

                    var lastValues = new CalcValue(
                        calc,
                        parseFloat(calc.xInput.value),
                        parseFloat(calc.yInput.value)
                    );

                    var handleCalcEvnet = function handleCalcEvent(e){
                        var newValues = lastValues,
                        elem = e.target;

                        switch(elem){
                            case calc.xInput:
                                newValues = lastValues.copyWith(
                                    Calc.xName,
                                    elem.value
                                );
                            break;
                            case calc.yInput:
                                newValues = lastValues.copyWith(
                                    Calc.yName,
                                    elem.value
                                );
                            break;
                        }

                        if (newValues !== lastValues){
                            lastValues = newValues;
                            lastValues.render();
                        }
                    };

                    elem.addEventListener('keyup', handleCalcEvnet, false);
                    return lastValues;
                }

                window.addEventListener(
                    'load',
                    function(){
                        var cv = initCalc(document.getElementById('myCalc'));
                        console.log(cv);
                        cv.render();
                    },
                    false
                );
            }());
        </script>
    </body>
</html>

Vue

<!DOCTYPE html>
<html>
    <head>
        <title>Vue.js 계산기</title>
        <style>
            p, input{ font-family: monospace; }
            p, { white-space: pre; }
        </style>
    </head>
    <body>
        <div id="app">
            <p>x <input v-model="x"></p>
            <p>y <input v-model="y"></p>
            <p>-------------------------</p>
            <p>= <span v-text="result"></span></p>
        </div>

        <script src="https://unpkg.com/vue/dist/vue.js"></script>
        <script type="text/javascript">
            function isNotNumericValue(value){
                return isNaN(value) || !isFinite(value);
            }

            var calc = new Vue({
                el: '#app',
                data: {x:0, y:0, lastResult: 0},
                computed: {
                    result: function(){
                        let x = parseFloat(this.x);
                        if(isNotNumericValue(x))
                            return this.lastResult;
                        let y = parseFloat(this.y);
                        if(isNotNumericValue(y))
                            return this.lastResult;

                        this.lastResult = x + y;

                        return this.lastResult;
                    }
                }
            });
        </script>
    </body>
</html>

Vanilla 에서 querySelector, addEventListener, prototype 사용법을 익혀두자~!

반응형