티스토리 뷰

PHP

PHP - 좋아요 구현 (1) 버튼 생성

오이연우오 2022. 4. 17. 22:37

1. 코드펜에서 버튼 가져오기

https://codepen.io/aaroniker/pen/ZEbLZrK 

 

Thumbs up button

...

codepen.io

2. 버튼 구조 정리하기

HTML

원본

<button class="button dark">
    <div class="hand">
        <div class="thumb"></div>
    </div>
    <span>Like<span>d</span></span>
</button>

<button class="button">
    <div class="hand">
        <div class="thumb"></div>
    </div>
    <span>Like<span>d</span></span>
</button>

<!-- dribbble - twitter -->
<a class="dribbble" href="https://dribbble.com/ai" target="_blank"><img src="..." alt=""></a>
<a class="twitter" target="_top" href="https://twitter.com/aaroniker_me"><svg xmlns="http://www.w3.org/2000/svg" width="72" height="72" viewBox="0 0 72 72"><path d="..."></path></svg></a>

수정

dark모드와 dribbble, twitter은 지운다.

<button class="button">
    <div class="hand">
        <div class="thumb"></div>
    </div>
    <span>Like<span>d</span></span>
</button>

CSS

원본

.button {
    --color: #1E2235;
    --color-hover: #1E2235;
    --color-active: #fff;
    --icon: #BBC1E1;
    --icon-hover: #8A91B4;
    --icon-active: #fff;
    --background: #fff;
    --background-hover: #fff;
    --background-active: #362A89;
    --border: #E1E6F9;
    --border-active: #362A89;
    --shadow: rgba(0, 17, 119, 0.025);
    display: block;
    outline: none;
    cursor: pointer;
    position: relative;
    border: 0;
    background: none;
    padding: 8px 20px 8px 24px;
    border-radius: 9px;
    line-height: 27px;
    font-family: inherit;
    font-weight: 600;
    font-size: 14px;
    color: var(--color);
    -webkit-appearance: none;
    -webkit-tap-highlight-color: transparent;
    transition: color 0.2s linear;
    }
    .button.dark {
    --color: #F6F8FF;
    --color-hover: #F6F8FF;
    --color-active: #fff;
    --icon: #8A91B4;
    --icon-hover: #BBC1E1;
    --icon-active: #fff;
    --background: #1E2235;
    --background-hover: #171827;
    --background-active: #275EFE;
    --border: transparent;
    --border-active: transparent;
    --shadow: rgba(0, 17, 119, 0.16);
    }
    .button:hover {
    --icon: var(--icon-hover);
    --color: var(--color-hover);
    --background: var(--background-hover);
    --border-width: 2px;
    }
    .button:active {
    --scale: .95;
    }
    .button:not(.liked):hover {
    --hand-rotate: 8;
    --hand-thumb-1: -12deg;
    --hand-thumb-2: 36deg;
    }
    .button.liked {
    --span-x: 2px;
    --span-d-o: 1;
    --span-d-x: 0;
    --icon: var(--icon-active);
    --color: var(--color-active);
    --border: var(--border-active);
    --background: var(--background-active);
    }
    .button:before {
    content: "";
    min-width: 103px;
    position: absolute;
    left: 0;
    top: 0;
    right: 0;
    bottom: 0;
    border-radius: inherit;
    transition: background 0.2s linear, transform 0.2s, box-shadow 0.2s linear;
    transform: scale(var(--scale, 1)) translateZ(0);
    background: var(--background);
    box-shadow: inset 0 0 0 var(--border-width, 1px) var(--border), 0 4px 8px var(--shadow), 0 8px 20px var(--shadow);
    }
    .button .hand {
    width: 11px;
    height: 11px;
    border-radius: 2px 0 0 0;
    background: var(--icon);
    position: relative;
    margin: 10px 8px 0 0;
    transform-origin: -5px -1px;
    transition: transform 0.25s, background 0.2s linear;
    transform: rotate(calc(var(--hand-rotate, 0) * 1deg)) translateZ(0);
    }
    .button .hand:before, .button .hand:after {
    content: "";
    background: var(--icon);
    position: absolute;
    transition: background 0.2s linear, box-shadow 0.2s linear;
    }
    .button .hand:before {
    left: -5px;
    bottom: 0;
    height: 12px;
    width: 4px;
    border-radius: 1px 1px 0 1px;
    }
    .button .hand:after {
    right: -3px;
    top: 0;
    width: 4px;
    height: 4px;
    border-radius: 0 2px 2px 0;
    background: var(--icon);
    box-shadow: -0.5px 4px 0 var(--icon), -1px 8px 0 var(--icon), -1.5px 12px 0 var(--icon);
    transform: scaleY(0.6825);
    transform-origin: 0 0;
    }
    .button .hand .thumb {
    background: var(--icon);
    width: 10px;
    height: 4px;
    border-radius: 2px;
    transform-origin: 2px 2px;
    position: absolute;
    left: 0;
    top: 0;
    transition: transform 0.25s, background 0.2s linear;
    transform: scale(0.85) translateY(-0.5px) rotate(var(--hand-thumb-1, -45deg)) translateZ(0);
    }
    .button .hand .thumb:before {
    content: "";
    height: 4px;
    width: 7px;
    border-radius: 2px;
    transform-origin: 2px 2px;
    background: var(--icon);
    position: absolute;
    left: 7px;
    top: 0;
    transition: transform 0.25s, background 0.2s linear;
    transform: rotate(var(--hand-thumb-2, -45deg)) translateZ(0);
    }
    .button .hand,
    .button span {
    display: inline-block;
    vertical-align: top;
    }
    .button .hand span,
    .button span span {
    opacity: var(--span-d-o, 0);
    transition: transform 0.25s, opacity 0.2s linear;
    transform: translateX(var(--span-d-x, 4px)) translateZ(0);
    }
    .button > span {
    transition: transform 0.25s;
    transform: translateX(var(--span-x, 4px)) translateZ(0);
    }
    
    html {
    box-sizing: border-box;
    -webkit-font-smoothing: antialiased;
    }
    
    * {
    box-sizing: inherit;
    }
    *:before, *:after {
    box-sizing: inherit;
    }
    
    body {
    min-height: 100vh;
    display: flex;
    font-family: "Inter", Arial;
    justify-content: center;
    align-items: center;
    background: #F6F8FF;
    }
    body .button {
    margin: 0 12px;
    }
    body .dribbble {
    position: fixed;
    display: block;
    right: 20px;
    bottom: 20px;
    }
    body .dribbble img {
    display: block;
    height: 28px;
    }
    body .twitter {
    position: fixed;
    display: block;
    right: 64px;
    bottom: 14px;
    }
    body .twitter svg {
    width: 32px;
    height: 32px;
    fill: #1da1f2;
    }

수정

dark모드와 dribbble, twitter은 지운다.

html, *, body 설정도 지운다.

.button {
    --color: #1E2235;
    --color-hover: #1E2235;
    --color-active: #fff;
    --icon: #BBC1E1;
    --icon-hover: #8A91B4;
    --icon-active: #fff;
    --background: #fff;
    --background-hover: #fff;
    --background-active: #362A89;
    --border: #E1E6F9;
    --border-active: #362A89;
    --shadow: rgba(0, 17, 119, 0.025);
    display: block;
    outline: none;
    cursor: pointer;
    position: relative;	//button을 추가할 상위 박스에 position: absolute를 주고,
    //left,top값을 주어서 위치 조정 한다.
    border: 0;
    background: none;
    padding: 8px 20px 8px 24px;
    border-radius: 9px;
    line-height: 27px;
    font-family: inherit;
    font-weight: 600;
    font-size: 14px;
    color: var(--color);
    -webkit-appearance: none;
    -webkit-tap-highlight-color: transparent;
    transition: color 0.2s linear;
    }
    .button:hover {
    --icon: var(--icon-hover);
    --color: var(--color-hover);
    --background: var(--background-hover);
    --border-width: 2px;
    }
    .button:active {
    --scale: .95;
    }
    .button:not(.liked):hover {
    --hand-rotate: 8;
    --hand-thumb-1: -12deg;
    --hand-thumb-2: 36deg;
    }
    .button.liked {
    --span-x: 2px;
    --span-d-o: 1;
    --span-d-x: 0;
    --icon: var(--icon-active);
    --color: var(--color-active);
    --border: var(--border-active);
    --background: var(--background-active);
    }
    .button:before {
    content: "";
    min-width: 103px;
    position: absolute;
    left: 0;
    top: 0;
    right: 0;
    bottom: 0;
    border-radius: inherit;
    transition: background 0.2s linear, transform 0.2s, box-shadow 0.2s linear;
    transform: scale(var(--scale, 1)) translateZ(0);
    background: var(--background);
    box-shadow: inset 0 0 0 var(--border-width, 1px) var(--border), 0 4px 8px var(--shadow), 0 8px 20px var(--shadow);
    }
    .button .hand {
    width: 11px;
    height: 11px;
    border-radius: 2px 0 0 0;
    background: var(--icon);
    position: relative;
    margin: 10px 8px 0 0;
    transform-origin: -5px -1px;
    transition: transform 0.25s, background 0.2s linear;
    transform: rotate(calc(var(--hand-rotate, 0) * 1deg)) translateZ(0);
    }
    .button .hand:before, .button .hand:after {
    content: "";
    background: var(--icon);
    position: absolute;
    transition: background 0.2s linear, box-shadow 0.2s linear;
    }
    .button .hand:before {
    left: -5px;
    bottom: 0;
    height: 12px;
    width: 4px;
    border-radius: 1px 1px 0 1px;
    }
    .button .hand:after {
    right: -3px;
    top: 0;
    width: 4px;
    height: 4px;
    border-radius: 0 2px 2px 0;
    background: var(--icon);
    box-shadow: -0.5px 4px 0 var(--icon), -1px 8px 0 var(--icon), -1.5px 12px 0 var(--icon);
    transform: scaleY(0.6825);
    transform-origin: 0 0;
    }
    .button .hand .thumb {
    background: var(--icon);
    width: 10px;
    height: 4px;
    border-radius: 2px;
    transform-origin: 2px 2px;
    position: absolute;
    left: 0;
    top: 0;
    transition: transform 0.25s, background 0.2s linear;
    transform: scale(0.85) translateY(-0.5px) rotate(var(--hand-thumb-1, -45deg)) translateZ(0);
    }
    .button .hand .thumb:before {
    content: "";
    height: 4px;
    width: 7px;
    border-radius: 2px;
    transform-origin: 2px 2px;
    background: var(--icon);
    position: absolute;
    left: 7px;
    top: 0;
    transition: transform 0.25s, background 0.2s linear;
    transform: rotate(var(--hand-thumb-2, -45deg)) translateZ(0);
    }
    .button .hand,
    .button span {
    display: inline-block;
    vertical-align: top;
    }
    .button .hand span,
    .button span span {
    opacity: var(--span-d-o, 0);
    transition: transform 0.25s, opacity 0.2s linear;
    transform: translateX(var(--span-d-x, 4px)) translateZ(0);
    }
    .button > span {
    transition: transform 0.25s;
    transform: translateX(var(--span-x, 4px)) translateZ(0);
    }

javascript

원본

document.querySelectorAll(".button").forEach((button) => {
    button.addEventListener("click", (e) => {   //버튼에 클릭 이벤트가 발생하면
        button.classList.toggle("liked");       //liked 클래스가 붙었다 지워졌다함
        if (button.classList.contains("liked")) {
            gsap.fromTo(
                button,
                {
                    "--hand-rotate": 8
                },
                {
                    ease: "none",
                    keyframes: [
                        {
                            "--hand-rotate": -45,
                            duration: 0.16,
                            ease: "none"
                        },
                        {
                            "--hand-rotate": 15,
                            duration: 0.12,
                            ease: "none"
                        },
                        {
                            "--hand-rotate": 0,
                            duration: 0.2,
                            ease: "none",
                            clearProps: true
                        }
                    ]
                }
            );
        }
    });
});

수정

youlikeCheck라는 논리형 변수를 추가

document.querySelectorAll(".button").forEach((button) => {
    if(youlikeCheck == true) {                      //사용자가 좋아요를 안 눌렀을 때 버튼을 클릭하면
        button.classList.add("liked");              //버튼에 미리 like클래스 붙여놓음
        button.addEventListener("click", (e) => {   //클래스를 붙였다 지웠다 할 수 있게 함
            button.classList.toggle("liked");
        });
    } else if(youlikeCheck == false){               //사용자가 좋아요를 이미 눌렀을 때
        button.addEventListener("click", (e) => {   //버튼을 클릭하면
            button.classList.toggle("liked");       //liked클래스를 붙였다 지웠다
            if (button.classList.contains("liked")) {
                gsap.fromTo(
                    button, {
                        "--hand-rotate": 8
                    }, {
                        ease: "none",
                        keyframes: [{
                                "--hand-rotate": -45,
                                duration: 0.16,
                                ease: "none"
                            },
                            {
                                "--hand-rotate": 15,
                                duration: 0.12,
                                ease: "none"
                            },
                            {
                                "--hand-rotate": 0,
                                duration: 0.2,
                                ease: "none",
                                clearProps: true
                            }
                        ]
                    }
                );
            }
        });
    }
});

좋아요 구현 (2) 테이블 추가, 불러오기 >>

 

PHP - 좋아요 구현 (2) 테이블 셋팅, 데이터 불러오기

테이블 셋팅하기 <?php include "../connect/connect.php"; // 데이터 베이스 연결 $sql = "CREATE TABLE blogLike ("; $sql .= "likeID int(10) unsigned auto_increment,"; $sql .= "memberID int(10) NOT NULL..

ohcodingoh.tistory.com

 

'PHP' 카테고리의 다른 글

PHP - 좋아요 구현 (3) 데이터 조작하기 (jQuery)  (0) 2022.04.18
PHP - 좋아요 구현 (2) 테이블 셋팅, 데이터 불러오기  (0) 2022.04.17
PHP - 조건문  (0) 2022.04.16
php - form  (0) 2022.04.16
PHP - 연산자  (0) 2022.04.16
댓글
© 2018 webstoryboy