728x90

인도영화에 흠취하여 쥐뿔도 모르는데 번역해본다고 삽질하고 도움받아가면서 번역해본 허접 자막입니다.

요즈음 번역한 것 아니고 몇년전에 잠깐 해보고 지금은 전혀 손도 안대고 있으니 질문 사절합니다.

오역은 직접 수정해서 보시라고 영문자막도 같이 첨부합니다.


Yamla.Pagla.Deewana.2011.BluRay.nHD.x264-NhaNc3.srt

Yamla.Pagla.Deewana.2011.BluRay.nHD.x264-NhaNc3_Eng.srt


까르팅콜링까르틱

Karthik Calling Karthik 2010 Upscale.srt

Karthik Calling Karthik 2010 Upscale_eng.srt


보디가드 타밀버전

Kaavalan 2011.srt

Kaavalan 2011 ENG.srt


처음으로 번역해본 자막

Hum.Ko.Deewana.Kar.Gaye.2006.720p.BluRay.nHD.x264-NhaNc3.srt

Hum.Ko.Deewana.Kar.Gaye.2006.720p.BluRay.nHD.x264-NhaNc3_Eng.srt



구글 드라이브에 인도영화 M/V 올린 샘플 링크 (다운로드 받아서 PC에서 들어보세요)

https://drive.google.com/file/d/1zP86kRyWV_95L9LL74F9XPb1sWOiNdxu/view?usp=sharing


https://drive.google.com/file/d/1hAC21XQnm52-N1iCugkd8CQkLd3t70M2/view


https://drive.google.com/file/d/1LJQ9viPBB-6uUKc9WKv-vD3AylSaYHWZ/view?usp=sharing


https://drive.google.com/file/d/1FM4lgXTLpOl8hsBcYOjU8ERt2b6vEyNZ/view?usp=sharing



자막 받아가는 분은 O고 좀 눌러주면 감솨하겠어요~~

'영화 > 인도영화' 카테고리의 다른 글

인도관련 서적  (0) 2018.12.29
PIKU (피쿠) - 아빠를 부탁해  (0) 2016.08.08
인도영화 한글자막 구할 수 있는 곳  (0) 2015.03.14
종교를 다룬 인도영화 PK  (0) 2015.01.11
블로그 이미지

Link2Me

,
728x90

부트스트랩에서 메뉴버튼을 누르면 왼쪽 화면에 사이드바 메뉴화면이 나오고 없어지는 예제에 대한 설명이다.


출처 : https://bootsnipp.com/snippets/featured/fancy-sidebar-navigation


CSS 부분 주석을 달아 향후 다시 볼 때 이해를 높이도록 했다.

overflow 속성은 http://triki.net/wiki/792# 에 설명이 잘 되어 있다.

아래 사이드 메뉴에 대한 설명은 https://bootstrapious.com/p/bootstrap-sidebar 에 잘 설명되어 있는 편이다.

http://link2me.tistory.com/1194 게시글을 참조하여 수정/활용하면 좋을 것이다.


<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link href="//maxcdn.bootstrapcdn.com/bootstrap/3.3.0/css/bootstrap.min.css" rel="stylesheet" id="bootstrap-css">
<style>
body {
    position: relative;
    overflow-x: hidden;
}
body,
html { height: 100%;}
.nav .open > a,
.nav .open > a:hover,
.nav .open > a:focus {background-color: transparent;}

/*-------------------------------*/
/*           Wrappers            */
/*-------------------------------*/

#wrapper {
    padding-left: 0;
    -webkit-transition: all 0.5s ease;
    -moz-transition: all 0.5s ease;
    -o-transition: all 0.5s ease;
    transition: all 0.5s ease;
}

#wrapper.toggled {
    padding-left: 220px;
}

#sidebar-wrapper {
   /* z-index는 태그들이 겹칠 때 누가 더 위로 올라가는지를 결정하는 속성, 기본값은 0 */
    z-index: 1000; /* z축 상의 위치를 나타내며, 정수값(음수, 양수). 높은 번호를 가진 레이어는 낮은 번호를 가진 레이어 위에 렌더링된다 */
    left: 220px;
    width: 0;
    height: 100%;
    margin-left: -220px;
    overflow-y: auto; /* 본문에 표시되는 내용에 따라 세로 스크롤이 생긴다. */
    overflow-x: hidden; /* 부모요소의 범위를 넘어가는 자식요소의 부분은 보이지 않도록 처리 */
    background: #1a1a1a;
    -webkit-transition: all 0.5s ease; /* CSS 속성을 변경할 때 애니메이션 속도를 조절하는 방법을 제공 */
    -moz-transition: all 0.5s ease;
    -o-transition: all 0.5s ease;
    transition: all 0.5s ease;
}

#sidebar-wrapper::-webkit-scrollbar {
  display: none; /* 보이지 않음 */
}

#wrapper.toggled #sidebar-wrapper {
    width: 220px;
}

#page-content-wrapper {
    width: 100%;
    padding-top: 70px;
}

#wrapper.toggled #page-content-wrapper {
    position: absolute; /* 가장 가까운 곳에 위치한 조상 엘리먼트에 상대적으로 위치가 지정된다. */
    /* relative가 static인 상태를 기준으로 주어진 픽셀만큼 움직였다면, */
    /* absolute는 position: static 속성을 가지고 있지 않은 부모를 기준으로 움직인다. */
    /* 만약 부모 중에 포지션이 relative, absolute, fixed인 태그가 없다면 가장 위의 태그(body)가 기준이 된다. */
    margin-right: -220px;
}

/*-------------------------------*/
/*     Sidebar nav styles        */
/*-------------------------------*/

.sidebar-nav {
    position: absolute;
    top: 0;
    width: 220px;
    margin: 0;
    padding: 0;
    list-style: none;
}

.sidebar-nav li {
    position: relative;
    line-height: 20px;
    display: inline-block;
    width: 100%;
}

.sidebar-nav li:before {
    content: '';
    position: absolute;
    top: 0;
    left: 0;
    z-index: -1;
    height: 100%;
    width: 3px;
    background-color: #1c1c1c;
    -webkit-transition: width .2s ease-in;
      -moz-transition:  width .2s ease-in;
       -ms-transition:  width .2s ease-in;
            transition: width .2s ease-in;

}
.sidebar-nav li:first-child a {
    color: #fff;
    background-color: #1a1a1a;
}

.sidebar-nav li:before {
    background-color: #D8D8D8;  
}
.sidebar-nav li:hover:before,
.sidebar-nav li.open:hover:before {
    width: 100%;
    -webkit-transition: width .2s ease-in;
      -moz-transition:  width .2s ease-in;
       -ms-transition:  width .2s ease-in;
            transition: width .2s ease-in;

}

.sidebar-nav li a {
    display: block; /* 요소를 block 요소처럼 표시한다. 요소 앞뒤로 줄바꿈 된다. */
    color: #ddd;
    text-decoration: none; /* 선을 만들지 않는다. */
    padding: 10px 15px 10px 30px;    
}

.sidebar-nav li a:hover,
.sidebar-nav li a:active,
.sidebar-nav li a:focus,
.sidebar-nav li.open a:hover,
.sidebar-nav li.open a:active,
.sidebar-nav li.open a:focus{
    color: #fff;
    text-decoration: none;
    background-color: transparent;
}

.sidebar-nav > .sidebar-brand {
    height: 45px;
    font-size: 16px;
    line-height: 24px;
}
.sidebar-nav .dropdown-menu {
    position: relative;
    width: 100%;
    padding: 0;
    margin: 0;
    border-radius: 0;
    border: none;
    background-color: #222;
    box-shadow: none;
}

/*-------------------------------*/
/*       Link2me-Cross         */
/*-------------------------------*/

.link2me {
  position: fixed; /* fixed: 스크롤과 상관없이 항상 문서 최 좌측상단을 기준으로 좌표를 고정 */
  top: 20px;  
  z-index: 999; /* z-index는 태그들이 겹칠 때 누가 더 위로 올라가는지를 결정하는 속성, 기본값은 0 */
  display: block; /* 요소를 block 요소처럼 표시한다. 요소 앞뒤로 줄바꿈 된다. */
  width: 32px;
  height: 32px;
  margin-left: 15px;
  background: transparent;
  border: none;
}
.link2me:hover,
.link2me:focus,
.link2me:active {
  outline: none;
}
.link2me.is-closed:before {
  content: '';
  display: block;
  width: 100px;
  font-size: 14px;
  color: #fff;
  line-height: 32px;
  text-align: center;
  opacity: 0;
  -webkit-transform: translate3d(0,0,0);
  -webkit-transition: all .35s ease-in-out;
}
.link2me.is-closed:hover:before {
  opacity: 1;
  display: block;
  -webkit-transform: translate3d(-100px,0,0);
  -webkit-transition: all .35s ease-in-out;
}

.link2me.is-closed .hamb-top,
.link2me.is-closed .hamb-middle,
.link2me.is-closed .hamb-bottom,
.link2me.is-open .hamb-top,
.link2me.is-open .hamb-middle,
.link2me.is-open .hamb-bottom {
  position: absolute;
  left: 0;
  height: 4px;
  width: 100%;
}
.link2me.is-closed .hamb-top,
.link2me.is-closed .hamb-middle,
.link2me.is-closed .hamb-bottom {
  background-color: #1a1a1a;
}
.link2me.is-closed .hamb-top {
  top: 5px;
  -webkit-transition: all .35s ease-in-out;
}
.link2me.is-closed .hamb-middle {
  top: 50%;
  margin-top: -2px;
}
.link2me.is-closed .hamb-bottom {
  bottom: 5px;  
  -webkit-transition: all .35s ease-in-out;
}

.link2me.is-closed:hover .hamb-top {
  top: 0;
  -webkit-transition: all .35s ease-in-out;
}
.link2me.is-closed:hover .hamb-bottom {
  bottom: 0;
  -webkit-transition: all .35s ease-in-out;
}
.link2me.is-open .hamb-top,
.link2me.is-open .hamb-middle,
.link2me.is-open .hamb-bottom {
  background-color: #1a1a1a;
}
.link2me.is-open .hamb-top,
.link2me.is-open .hamb-bottom {
  top: 50%;
  margin-top: -2px;  
}
.link2me.is-open .hamb-top {
  -webkit-transform: rotate(45deg);
  -webkit-transition: -webkit-transform .2s cubic-bezier(.73,1,.28,.08);
}
.link2me.is-open .hamb-middle { display: none; }
.link2me.is-open .hamb-bottom {
  -webkit-transform: rotate(-45deg);
  -webkit-transition: -webkit-transform .2s cubic-bezier(.73,1,.28,.08);
}
.link2me.is-open:before {
  content: '';
  display: block;
  width: 100px;
  font-size: 14px;
  color: #fff;
  line-height: 32px;
  text-align: center;
  opacity: 0;
  -webkit-transform: translate3d(0,0,0);
  -webkit-transition: all .35s ease-in-out;
}
.link2me.is-open:hover:before {
  opacity: 1;
  display: block;
  -webkit-transform: translate3d(-100px,0,0);
  -webkit-transition: all .35s ease-in-out;
}

/*-------------------------------*/
/*            Overlay            */
/*-------------------------------*/

.overlay {
    position: fixed; /* fixed: 스크롤과 상관없이 항상 문서 최 좌측상단을 기준으로 좌표를 고정 */
    display: none;
    width: 100%;
    height: 100%;
    top: 0;
    left: 0;
    right: 0;
    bottom: 0;
    background-color: rgba(250,250,250,.8);
    z-index: 1;
}
</style>
<script src="//maxcdn.bootstrapcdn.com/bootstrap/3.3.0/js/bootstrap.min.js"></script>
<script src="//code.jquery.com/jquery-1.11.1.min.js"></script>
<script>
$(document).ready(function () {
  var trigger = $('.link2me'),
      overlay = $('.overlay'),
     isClosed = false;

    trigger.click(function () {
      link2me_cross();      
    });

    function link2me_cross() {

      if (isClosed == true) {          
        overlay.hide();
        trigger.removeClass('is-open');
        trigger.addClass('is-closed');
        isClosed = false;
      } else {   
        overlay.show();
        trigger.removeClass('is-closed');
        trigger.addClass('is-open');
        isClosed = true;
      }
  }
 
  $('[data-toggle="offcanvas"]').click(function () {
        $('#wrapper').toggleClass('toggled');
  });  
});
</script>
</body>
    <div id="wrapper">
        <div class="overlay"></div>
    
        <!-- Sidebar 숨김으로 보였다 보이지 않았다 하는 부분 -->
        <nav class="navbar navbar-inverse navbar-fixed-top" id="sidebar-wrapper" role="navigation">
            <ul class="nav sidebar-nav">
                <li class="sidebar-brand">
                    <a href="#">
                       Brand
                    </a>
                </li>
                <li>
                    <a href="#">Home</a>
                </li>
                <li>
                    <a href="#">About</a>
                </li>
                <li>
                    <a href="#">메뉴1</a>
                </li>
                <li>
                    <a href="#">메뉴2</a>
                </li>
                <li class="dropdown">
                  <a href="#" class="dropdown-toggle" data-toggle="dropdown">메뉴3<span class="caret"></span></a>
                  <ul class="dropdown-menu" role="menu">
                    <li class="dropdown-header">Dropdown heading</li>
                    <li><a href="#">서브메뉴3.1</a></li>
                    <li><a href="#">서브메뉴3.2</a></li>
                    <li><a href="#">서브메뉴3.3</a></li>
                    <li><a href="#">서브메뉴3.4</a></li>
                    <li><a href="#">서브메뉴3.5</a></li>
                  </ul>
                </li>
                <li>
                    <a href="#">메뉴4</a>
                </li>
                <li>
                    <a href="#">메뉴5</a>
                </li>
                <li>
                    <a href="https://twitter.com/maridlcrmn">메뉴6</a>
                </li>
            </ul>
        </nav>
        <!-- /#sidebar-wrapper -->

        <!-- Page Content -->
        <div id="page-content-wrapper">
            <button type="button" class="link2me is-closed" data-toggle="offcanvas">
                <span class="hamb-top"></span>
                <span class="hamb-middle"></span>
                <span class="hamb-bottom"></span>
            </button>
            <div class="container">
                <div class="row">
                    <div class="col-lg-8 col-lg-offset-2">
                        <h1>Toggle Sidebar Navigation</h1>
                        <p>토글 사이드바 네비게이션에 대한 본문 내용입니다.</p>
                    </div>
                </div>
            </div>
        </div>
        <!-- /#page-content-wrapper -->

    </div>
    <!-- /#wrapper -->
</body>
</html>


블로그 이미지

Link2Me

,
728x90

출처 : https://www.w3schools.com/howto/tryit.asp?filename=tryhow_js_sidenav

에서 테스트해볼 수 있다.

CSS에 대한 설명을 약간 추가하기 위해서 적었다.


 <!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1">
<style>
body {
    font-family: "Lato", sans-serif;
}

.sidenav {
    height: 100%;
    width: 0;
    position: fixed; /* fixed: 스크롤과 상관없이 항상 문서 최 좌측상단을 기준으로 좌표를 고정 */
    z-index: 1; /* z-index는 태그들이 겹칠 때 누가 더 위로 올라가는지를 결정하는 속성, 기본값은 0 */
    top: 0;
    left: 0;
    background-color: #111;
    overflow-x: hidden; /* 부모요소의 범위를 넘어가는 자식요소의 부분은 보이지 않도록 처리 */
    /* 자식 요소가 부모요소의 범위를 초과 할 때 어떻게 처리 할지를 결정 하므로 부모요소에 overflow 속성 값을 결정해 주어야 한다. */
    transition: 0.5s;
    padding-top: 60px;
}

.sidenav a {
    padding: 8px 8px 8px 32px;
    text-decoration: none;
    font-size: 25px;
    color: #818181;
    display: block;
    transition: 0.3s;
}

.sidenav a:hover {
    color: #f1f1f1;
}

.sidenav .closebtn {
    position: absolute;
    top: 0;
    right: 25px;
    font-size: 36px;
    margin-left: 50px;
}

@media screen and (max-height: 450px) {
  .sidenav {padding-top: 15px;}
  .sidenav a {font-size: 18px;}
}
</style>
</head>
<body>

<div id="mySidenav" class="sidenav">
  <a href="javascript:void(0)" class="closebtn" onclick="closeNav()">&times;</a>
  <a href="#">About</a>
  <a href="#">Services</a>
  <a href="#">Clients</a>
  <a href="#">Contact</a>
</div>

<h2>Animated Sidenav Example</h2>
<p>Click on the element below to open the side navigation menu.</p>
<span style="font-size:30px;cursor:pointer" onclick="openNav()">&#9776; open</span>

<script>
function openNav() {
    document.getElementById("mySidenav").style.width = "250px";
}

function closeNav() {
    document.getElementById("mySidenav").style.width = "0";
}
</script>
     
</body>
</html>


블로그 이미지

Link2Me

,

MySQL 사용자 권한 부여

SQL 2018. 11. 26. 16:16
728x90

MySQL 사용자 권한 부여 방법인데 찾기가 귀찮아서 여기에 적어둔다.


<?php

$DB['host'] = 'localhost';

$DB['name'] = 'kkkope2018';

$DB['user'] = 'kkkope';

$DB['pass'] = '!kkkope@#';

$DB['head'] = 'rb';

$DB['port'] = '3306';

$DB['type'] = 'MyISAM';


//use mysql;

//grant all privileges on kkkope2018.* to kkkope@localhost identified by '!kkkope@#';

//flush privileges;

?>

'SQL' 카테고리의 다른 글

SQL 테이블 칼럼 추가/삭제 방법  (0) 2020.03.14
테이블명 변경  (0) 2019.03.11
MySQL 두 테이블 불일치 데이터 찾는 SQL  (0) 2018.08.18
Toad for MySQL - Database Diagram  (0) 2017.06.02
[강좌] 한방에 개념잡는 SQL 조인  (0) 2017.02.26
블로그 이미지

Link2Me

,
728x90


jQuery mobile 을 이용하여 화면 프레임을 구성하면 비교적 깔끔하게 보이는 걸 알 수 있다.

먼저 구글에서 jQeury mobile 을 검색하여 https://jquerymobile.com/ 로 접속한다.

데모를 눌러서 가장 최신버전의 안정적 버전 데모를 눌러 jQuery mobile의 기본적인 기능을 익힌다.


index.html 파일을 아래와 같이 변경해보자.

header, content, footer 영역으로 나누어 구성한다.

header 와 footer 영역을 고정하는 것은 data-position="fixed" 를 추가하면 된다.

sub.html 파일에서 헤더 영역을 <div data-role="header" data-theme="f" data-position="fixed" data-add-back-btn="true">와 같이 수정해보면 백버튼이 생기고 누르면 뒤로 가기가 되는 걸 확인할 수 있다.


<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<meta name="viewport" content="user-scalable=no, initial-scale=1, maximum-scale=1, minimum-scale=1, width=device-width" />
<link rel="stylesheet" href="http://code.jquery.com/mobile/1.4.5/jquery.mobile-1.4.5.min.css" />
<script src="http://code.jquery.com/jquery-1.9.1.min.js"></script>
<script src="http://code.jquery.com/mobile/1.4.5/jquery.mobile-1.4.5.min.js"></script>
</head>
<body>
<div data-role="page">
    <div data-role="header" data-theme="b" data-position="fixed">
        <a href="#" data-icon="back">이전</a>
        <h1>Header</h1>
        <a href="#" data-icon="home" data-iconpos="notext" data-theme="b">홈</a>
    </div>
    <div data-role="content">
        <ul data-role="listview" >
            <li data-role="list-divider"> 내부 도메인</li>
            <li><a href="sub.html" data-transition="slide">내부 페이지</a></li>
            <li><a href="sub.html" data-rel="dialog" data-icon="grid">다이어로그 페이지</a></li>
            <li data-role="list-divider"> 외부 도메인</li>
            <li><a href="sub.html" rel="external" data-transition="slide">외부링크 사용 내부페이지 열기</a></li>
        </ul>
    </div>
    <div data-role="footer" data-theme="b" data-position="fixed">
        <h2>Footer</h2>
    </div>
</div>
</body>
</html>

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<meta name="viewport" content="user-scalable=no, initial-scale=1, maximum-scale=1, minimum-scale=1, width=device-width" />
<link rel="stylesheet" href="http://code.jquery.com/mobile/1.4.5/jquery.mobile-1.4.5.min.css" />
<script src="http://code.jquery.com/jquery-1.9.1.min.js"></script>
<script src="http://code.jquery.com/mobile/1.4.5/jquery.mobile-1.4.5.min.js"></script>
</head>

<body>
<div data-role="page" id="page">
    <div data-role="header" data-theme="f" data-position="fixed">
        <h1>Sub 페이지</h1>
    </div>
    <div data-role="content">
        <h1>페이지 링크 연습</h1>
        <p>다양한 종류의 링크 연습</p>
        <a href="#" data-role="button" data-rel="back" data-icon="back" data-theme="a" >돌아가기</a>
    </div>
    <div data-role="footer" data-theme="d"  data-position="fixed">
        <h2>Footer</h2>
    </div>
</div>
</body>
</html>


'하이브리드앱' 카테고리의 다른 글

Flutter란  (0) 2019.12.27
PhoneGap 안드로이드 APK 정렬하기  (0) 2018.11.23
PhoneGap CLI 설치 과정  (0) 2018.11.22
블로그 이미지

Link2Me

,
728x90

배포용 keystore 를 생성시 

구글 플레이 스토어에 배포할 앱을 만들때는 유효기간이 항상 2033년 10월 22일 이후로 끝나야 하는 점을 주의해서 해야 한단다.


폰갭에서 Android APK 파일을 만들어서 배포하기 전에 정렬을 해야 한다고 동영상 강좌에 나와서 찾아봤다.


Android SDK 폴더를 검색해보니 zipalign.exe 파일이 존재한다.


배포용 APK 파일을 Android Studio 에서 생성하면 zipalign 기능을 자동으로 해주기 때문에 별도에 신경쓰지 않아도 된다고 한다.


수동으로 하는 방법은 

$ zipalign -v 4 application_unaligned.apk application_aligned.apk

출처: http://wingsnote.com/85 [날개의 노트 (Wing's Note)]

zipalign -v 4 app_unaligned.apk app_aligned.apk



'하이브리드앱' 카테고리의 다른 글

Flutter란  (0) 2019.12.27
[jQuery mobile] UI Layout 구성  (0) 2018.11.23
PhoneGap CLI 설치 과정  (0) 2018.11.22
블로그 이미지

Link2Me

,
728x90

하이브리드 앱은 HTML, CSS, Javascript/jQuery 기술을 이용하며
모바일웹 + 모바일 프레임워크를 사용하여 네이티브앱으로 변환한 앱이다.

PhoneGap은 Adobe에서 웹 개발 기술로 네이티브 앱을 개발할 수 있는 오픈소스 프레임워크이다.
PhoneGap은 웹 API로 모바일 앱을 개발 할 수 있는 프레임워크이다. 즉 웹 개발 기술로 프로그램을 작성해서 네이티브 앱을 만든다는 개념이다.

1. Node.js command prompt 를 실행한다.

2. npm install -g phonegap 를 입력하고 엔터키를 친다.



3. npm install -g cordova 를 입력하고 엔터키를 친다.


4. 구글 플레이스토어에서 PhoneGap Developer App을 검색하여 설치한다.


5. projects 디렉토리를 생성하고 이동한다.

   md projects

   cd projects


6. phonegap create hello_world 를 입력한다.


7. cd hello_world 로 폴더를 이동한 다음

   phonegap serve 를 실행하면 아래 화면이 나온다.


8. 이제 안드로이드폰에서 PhoneGap Developer 앱에서 해당 IP주소로 주소변경을 하고 나서 Connect를 누르면 어플이 실행된 것을 확인할 수 있다.

내 PC환경은 IPTime 공유기환경이라 안드로이드폰에서 Wi-Fi 접속모드를 활성화시켜야 한다.


폴더의 구조를 살펴보면 아래 그림과 같다.

우리가 개발을 손봐야 하는 것은 www 폴더에 있는 파일을 수정 개발하면 된다.


9. 해당 폴더로 이동하여 index.html 파일을 수정해보자.



수정하면 바로 앱에서 내용이 아래와 같이 변경되는 걸 확인할 수 있다.




PhoneGap Desktop 버전은 https://phonegap.com/ 에서 윈도우용과 맥용을 선택하여 받아 설치한다.


'하이브리드앱' 카테고리의 다른 글

Flutter란  (0) 2019.12.27
[jQuery mobile] UI Layout 구성  (0) 2018.11.23
PhoneGap 안드로이드 APK 정렬하기  (0) 2018.11.23
블로그 이미지

Link2Me

,
728x90

직장 동료가 예약을 해줘서 3개월 예약이 밀렸다는 용인한의원 진료를 받았다.

한의원에 예약한 시간에 와야 한다고 해서 휴가를 내고 한의원에 다녀왔다.

위치는 수지구청역 1번출구, 수지보건소 맞은편 3층에 위치한다.

도착해서 보니 환자(?)들이 엄청나게 많아서 놀랐고, 침치료를 받는데 앉는 의자에서 치료를 받는데 놀랐다.

보통 한의원은 엎드리거나 누워서 하는 침상치료가 대부분인데 이곳은 발과 팔 중심으로 침치료를 하는 곳이란다.

원장님이 진맥을 하고 나서 먹어야 할 음식이 뭔지 알려주셨다.

무, 배, 소고기, 도라지, 청국장 많이 먹어라.

피가 탁해지기 쉬운 체질이니 매운음식, 밀가루음식 절대 먹지 마라.

생채 말고 무밥, 소고기 무국 먹어라. 닭고기, 오리고기, 돼지고기 먹지 마라.

오미자차, 도라지차가 몸에 좋다. 유자차, 생강차, 대추차 몸에 안좋다. 커피는 블랙으로 하루 한잔정도는 괜찮다.


그동안 별 생각없이 먹었던 유자차, 대추차가 몸에 안좋단다. 요즈음 말린 대추도 씹어먹고 그랬는데 내 몸에 맞는 음식이 아니었다보다.

몸에 맞지 않은 빵을 먹으면서 살이 찌기 시작했던 거 같다.

군대 제대하고 복학을 바로 못하는 바람에 거의 1년을 쉬면서 라마다 르네상스 호텔에서 서빙 아르바이트를 잠깐 했다.

거기에 맛있는 케익 등을 먹으면서 몸무게가 늘었고, 회사 입사하면서도 조금씩 조금씩 늘었다.

아내는 자주 움직여야 하는데 움직이지 않고 거의 책상앞에 있으니까 살이 찐다고 한다. 맞는 말이다.

앞으로는 내 몸에 좋지 않은 음식은 삼가하고 몸에 맞은 음식을 주로 섭취하고 걷기를 열심히 하면 좋을 거 같다.


오미자의 효능


오미자는 기침, 가래, 허약체질, 당뇨 등에 좋은 효과가 있다고 한다.

거친 피부를 개선해주고 머리를 맑게 해주고 숙취해소 및 면역력을 높여주는 효능이 있다.

오미자는 해발 500 ~ 700m 의 준고냉지 배수가 잘되는 곳에서 자생하고 있다.

오미자 껍질은 신맛, 과육에는 단맛, 씨에는 맵고 쓴맛, 전체적으로 짠맛 총 5가지 맛이 난다하여 오미자라는 이름이 붙여졌다.



만성피로 회복 및 정력 증강 오미자는 단백질, 칼슘, 인, 철, 비타민 B1 등이 함유되어 있으며, 사과산과 주석산 등 유기산도 함유되어 있어 피로 회복을 돕는다. 현대인의 모든 병의 근원은 만성피로라 해도 과언이 아니다. 오미자는 신체 원기를 회복시켜주고 특히 남성들의 정력을 회복하는 데도 아주 좋다.

기억력 증가 뇌와 간의 단백질 함량을 증가시켜 항노화의 기능을 한다.기억력을 증가시키고 집중력 또한 향상하게 시키는 효능이 있어서 치매나 건망증에도 효과가 좋다.  외에도 뇌파를 자극하여 졸음을 달아나게 하는 효과도 있어 공부하는 학생들에게도 매우 좋으며 스트레스 또한 감소시켜 준다

기관지 건강 평소에 목이  좋거나 기침이 심한 경우 등 오미자가 기관지 강화에 효능이 있다. 특히 말을 많이 해야 하는 직업을 가지고 있는 선생님이나 강사들이라면 오미자차를 꾸준히 마시면 효과를 볼 수 있다. 또한 감기 예방 효과도 있어 환절기 미리 챙기면 좋다.

피부 미용 오미자는 많은 감염이나 오염에 노출된 피부 면역력을 증가시켜준다. 오미자가 아름다운 피부를 유지하도록 돕고 피부 트러블이 심한 경우 치료에도 도움이 된다.


이 외에도 오미자에는 식물성 에스트로젠인 리그난이 함유되어 있어, 간 보호와 간의 재활을 촉진하고 간암 억제를 돕는다.  기능도 원활하게 하고 신장기능 향상, 혈행의 개선 숙취 해소까지 해주는 효과가 있다. 또한, 혈당치도 낮춰주는 효능이 있으므로 당뇨 환자들에게도 굉장히 좋다고 한.


오미자 참고 사이트

https://m.post.naver.com/viewer/postView.nhn?volumeNo=16015137&memberNo=21480402&vType=VERTICAL


'건강 정보' 카테고리의 다른 글

따뜻한 성질의 음식, 차가운 성질의 음식  (0) 2021.12.19
블로그 이미지

Link2Me

,
728x90

객체 배열의 특징
내장객체 Array 객체를의미한다.
배열이름[인덱스] : 인덱스는0부터시작한다.
배열이름= new Array(개수); // 생성하는 방법
Arr_Name = new Array(10);

- join(): 배열을 하나의 문자열로 만들어 준다.
- sort(): 배열의 값들을 순서대로 정렬한다.
- reverse(): 배열안에 값들을 순서대로 재정렬시킨다.
- concat(): 두개 배열을 하나의 배열로 만든다.
- slice(): 배열의 일부분의 값을 추출한다.

<SCRIPT LANGUAGE="JAVASCRIPT">
array1 = new Array("사과", "배", "바나나")
document.write("<h4>" + array1.join() + "<br>")
document.write(array1.join("와") + "<br>")
document.write(array1.join("&") + "</h4>")
</SCRIPT>

<SCRIPT LANGUAGE="JAVASCRIPT">
array1 = new Array("오징어", "낙지", "문어","꼴뜨기");
array2 = array1.slice(1,3);
document.write(array2);
</SCRIPT>

블로그 이미지

Link2Me

,
728x90

선동렬 전 야구대표팀 감독은 14일 KBO에서 기자회견을 열고 자진사퇴를 발표했다.

초등학교 4학년때부터 야구만 생각했다는 선동열은 국내 최고의 투수로 화려한 경력을 남겼다. 1983년도에 해태에 입단하여 1986년 투수 3관왕을 시작으로 20승 3번, 다승왕 4번을 기록했고, 총 6번의 우승을 차지했다. 11시즌 통산 146승, 132세이브, 승률 0.785, 평균자책점 1.20, 탈삼진 1698개 등 엄청난 대기록을 작성했다. 하지만 감독으로서의 자질은 좋은 편이 못된다. 삼성에서는 우수한 선수들로 2번의 우승을 했지만 KIA로 옮기고는 588로 초라한 성적을 남겼다. 이 세상의 모든 선수들이 본인만큼 재능이 뛰어나면 본인이 원하는 선수로 경기에 임하겠지만, 뛰어나지 않는 선수들을 조련하고 지도하면서 성장시켜야 하는 것이 감독이라고 본다.

KIA 감독시절 선수가 실수하면 썩소를 날리던 모습이 TV로 잡힌 걸 보면 피가 거꾸로 솟았다.

감독보다는 투수코치 역할이었다면 최고의 선택이 아니었을까 싶다. 전체를 바라보는 감독의 역할로서는 미흡한 점이 보인다.


우수한 선수들을 선발하여 2018년 자카르타 아시안게임에서 야구 금메달을 땄다.

문제는 경찰야구단, 상무 등 야구를 계속 할 수 있는 군 제도가 있음에도 불구하고 오지환, 박해민은 아시안 게임 금메달에 초점을 맞추고 경찰야구단, 상무에 입대하지 않았고, 선동열 전임감독 사단은 국민정서를 무시한채 오지환, 박해민을 야구대표팀에 뽑았다.

금메달만 따면 모든게 해결될 것이라는 편향된 사고때문에 국정감사에도 불려나가고 결국 사퇴까지 하게 되었다.

선수로서는 정말 훌륭했는데 감독으로서는 다양한 걸 고려해야 하는데 그걸 간과하거나 무시한 것이 너무나도 큰 잘못이다.


대만, 일본은 프로선수없이 사회인 야구선수로 아시안 게임에 출전했는데 프로야구 경기까지 중단해가면서 공정하지 못한 선수선발을 한 건 정말 잘못한 것이라고 본다. 성인과 중학생이 싸움하는 수준으로 국민들은 이해하고 있다.

프로야구가 출범하고 나서 들러리가 된 대학야구 선수는 단 한명도 선발하지 않았다.

축구는 군복무중인 황인범 선수를 차출했다. 야구도 군복무 선수가 실력있고 도움된다면 뽑아서 기용했어야 된다고 본다. 그런데 병역기피하고자 하는 선수를 도와주는 역할을 하고, 금메달만 따면 모든게 해결될 것이라는 안일한 생각을 한 것 자체가 국민의 분노를 산 것이라는 모르는 거 같다.


2017년도 아시아프로야구챔피언십(APBC)에 뽑인 선수들을 우선적으로 자카르타 아시안게임 대표선수를 구성하겠다고 약속했던 선동열 감독은 아시안게임 대표선수 선발에 APBC 선수들을 별로 고려하지 않았다.

APBC 에 무리하게 출전했던 박세웅(롯데), 장현식(NC) 등 20대 초반 기대주들은 후유증에 시달려 팀 순위에 보탬이 되지 못했다. APBC 후유증을 경험한 임기영(KIA)은 어깨통증으로 시즌을 정상적으로 시작하지 못했고 2018년도 성적도 5승 8패1홀드 평균자책점 5.98로 부진했다. 이미 군 제대를 한 임기영을 선발하는 것 보다는 고영표(KT)를 선발하는 것이 더 합리적인 건 아닌가 싶었다. 밤새도록 술을 퍼마시고 다음날 완투승을 하는 선동열 본인처럼 야구선수들의 체력이 강철체력이면 좋겠지만, 지난해(2017년)에 많은 이닝을 던진 투수들이 관리 노하우가 부족하여 후유증으로 고생하고 팀에 보탬이 되지 못했다.

최원태(넥센)는 부상으로 아시안게임에서 별로 기여도 못했다.최원태는 아시안게임 대표선수로 선발되고자 무리한 것이 아닌가 싶다. 이후 포스트시즌에서 던지지도 못하고 부상 후유증에 시달리고 있다.


LG에서 김현수 데려가려면 오지환 뽑으라고 해서 선발한 것인지는 모르겠지만 김현수는 아시안게임에서 제 실력을 발휘하지 못했고 도움이 되지 못했다.

프로야구에 3할 타자가 즐비한 것은 공인구 반발력 문제라는 것이 아시안게임 국제대회에서 타자들이 보여준 실력으로 증명된 셈이다.

아시안게임에서 타자들의 실력이 형편없을 것을 본 이후로 야구를 정말 잘하는 줄 았았던 국민들의 실망감은 상당히 컸다고 본다. 야구 흥행을 위해서 공인구 반발력 높은 걸 사용해서 홈런 등 장타가 많이 나오게 하고, 심판들의 자질문제 등 야구는 홍역을 치르면서 이제서야 공인구 반발력을 조정하겠다고 한다. 참으로 다행이라고 본다.


선동열 감독 본인 생각은 참으로 억울하다고 느낄 지 모르지만, 대표팀 수장으로서 오지환, 박해민을 뽑은 대가를 톡톡히 치르고 있다고 봐야 한다.

야구에 대한 여론이 안좋아져서 병무청에서는 경찰야구단 폐지를 앞당기고 있어 2019년도 선수 선발도 하지 않은 상황으로 치닫고 있다.

그동안 야구는 금메달을 따겠다는 목표아래 팀별 병역면제 안배를 했고, 부상임에도 숨기고 출전했던 나지완(KIA)은 입을 잘못 털다가 팬들로부터 묻매를 맞았다. 나지완은 병역 면제를 받고 FA 계약으로 40억을 챙겼으니 선수 본인으로서는 영광스러운 일이겠지만, 나지완, 오지환, 박해민으로 인해 야구 후배들 앞길을 막아버린 꼴이 된 셈이니....

프로야구는 FA로 100억을 넘게 받는 선수들이 생기면서 국민들의 정서엔 그런 선수들에게 금메달 땄다고 우리가 세금으로 연금까지 주어야 하느냐는 마음가짐도 있다. 프로야구 선수중에서 손흥민 축구선수처럼 육군에 1억을 기부하는 그런 선수가 있는가? 오로지 자기 자신만을 위한 프로야구가 팬들로부터 외면을 받지 않으려면 자기반성을 많이 해야 한다고 본다.

야구에서 메달 따는 것이 국위선양인지도 잘 모르겠고 그냥 등따시고 배부른 야구 선수에게 연금주는 건 아닌거 같다.

블로그 이미지

Link2Me

,
728x90

자바스크립트에서 속성 읽기, 설정, 제거하는 방법이다.

<a id="target" href="http://abc.com">tutorials</a>

<script>

var t = document.getElementById('target');

t.getAttribute('href'); // href 속성의 값을 가져온다.

t.setAttribute('title', 'abcdef'); // title 속성의 값을 설정한다.

t.removeAttribute('title'); // title 속성을 제거한다.

</script>


jQuery는 HTML 요소에 대해 객체를 통하여 속성 값을 제어할 수 있는 attr()함수를 제공한다.


var 변수 = $("요소").attr("속성이름"); // 속성 값 읽기

var 변수 = $("요소").attr("속성이름","값"); // 속성 값 변경/추가


예제1

<div id="ajaxPath" data-path="<?php echo $g['path_page'].'process/'; ?>" ></div>


var loginpath =$("#ajaxPath").attr('data-path');
$.ajax({
    url: loginpath+'updateUser.php',
    type: 'POST',
    data: {
        idx:$("#memberidx").val(),
        userNM:$("#memberName").val(),
        mobileNO:$("#memberMobile").val()
    },
    dataType: "json",
    contentType: 'application/x-www-form-urlencoded; charset=UTF-8',
    success: function (response) {
        if(response.result == 1){
            alert('수정 완료');
            location.replace('index.php'); // 화면 갱신
        } else if(response.result == 0){
            alert('수정 실패');
        }
    },
    error: function(jqXHR, textStatus, errorThrown){
        alert("ajax error : " + textStatus + "\n" + errorThrown);
    }
});


예제2

<span class="button" id="errorChk" data-uid="<?=$R['uid']?>">오류</span>


$("#errorChk").click(function(){
    uid=$(this).attr("data-uid");
    ErrorDisplay(uid);
});

function ErrorDisplay(_uid){
    $.get("ErrorChk.php", {uid:_uid}, function(data){
        $("#dialog").dialog("open").html(data);
    });
}

function ErrorChk(_uid,_mod){
    $.get("ErrorChk.php", {uid:_uid, mod:_mod}, function(data){
        $("#dialog").dialog("open").html(data);
    });
}


prop() 함수 : 선택한 요소에 속성을 반환/생성/변환한다.

주의할 점은 HTML 입장에서의 속성(attribute)이 아닌 Javascript 입장에서의 속성(property)이다.

jQuery 1.6 부터 prop()함수가 추가되어 attr()함수의 역할을 나누게 되었다.


다음 예제를 통해 결과가 어떻게 다른지 확인해보자.

<!DOCTYPE html>
<html>
<head>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script>
$(document).ready(function(){
    var prop_id = $(":text").prop("id");
    var attr_id = $(":text").attr("id");

    alert("prop id값  : " + prop_id + " , attr id값 : " +  attr_id);


    var prop_class = $(":text").prop("class");
    var attr_class = $(":text").attr("class");

    alert("prop class값 : " + prop_class + " , attr class값 : " +  attr_class);


    var prop_readonly = $(":text").prop("readonly");
    var attr_readonly = $(":text").attr("readonly");

    alert("prop readonly값 : " + prop_readonly + " , attr readonly값 : " +  attr_readonly);


    var prop_disabled = $(":text").prop("disabled");
    var attr_disabled = $(":text").attr("disabled");
    alert("prop disabled값 : " + prop_disabled + " , attr disabled값 : " +  attr_disabled);
})
</script>
</head>
<body>
<input type="text" id="text_field" class="text_class" readonly="readonly" disabled="disabled" />
</body>
</html>


prop id값  : text_field , attr id값 : text_field

prop class값 : text_class , attr class값 : text_class


prop readonly값 : true , attr readonly값 : readonly

prop disabled값 : true , attr disabled값 : disabled


<input id="chk" type="checkbox" checked="checked" />
먼저 attr 함수로 checked 속성 값을 가져오면 그 결과 값은 checked(HTML이 가지고 있는 속성의 text 값)로 나온다.
하지만, prop 함수로 checked 속성 값을 가져오면 그 결과 값은 true(속성이 실제 의미하는 값)가 된다.

먼저 attr 함수로 checked 속성 값을 가져오면 그 결과 값은 checked(HTML이 가지고 있는 속성의 text 값)로 나온다.

하지만, prop 함수로 checked 속성 값을 가져오면 그 결과 값은 true(속성이 실제 의미하는 값)가 된다.



출처: http://ggmouse.tistory.com/92 [초보개발자꽁쥐]

true / false체크 같은 것을 사용할 때 아주 유용하다.
prop가 나온후로는
$("요소").prop("checked",true);
$("요소").prop("checked",false);
로 변경을 해주어야 체크박스 핸들링이 가능하다.

블로그 이미지

Link2Me

,

MCU

정보통신/IoT 2018. 11. 10. 08:58
728x90

출처 : http://www.ddaily.co.kr/news/article.html?no=114736


MCU는 Micro Controller Unit의 약자이며 일반적으로 마이크로컨트롤러라 부른다. 다양한 전자 기기에 탑재되는 핵심 부품으로 프로그래밍을 통해 다양한 ‘제어’ 나 ‘연산 작업’이 가능하다. 사람의 두뇌가 인체를 조정하는 것과 같이 MCU는 전자 회로 혹은 전자 기기를 구성하는 기계 부품의 기능을 조정하는 역할을 한다.

MCU의 시작은 최초의 계산기에 탑재된 바 있는 집적회로(ICs: Integrated Circuits)였다. 이후 부품을 더 적게 사용하는 더 나은 계산기 개발이 시도되면서 MCU도 함께 발전하고 진화해왔다.

MCU의 활용 예
▲밥솥이나 TV 녹화 장치의 타이머 기능
▲리모콘의 적외선 신호 방출
▲휴대폰의 배터리 전압 측정 및 잔여 배터리 용량 표시
▲시계의 시간 표시
▲버튼을 누르면 기능 수행 
▲USB를 통한 컴퓨터와의 데이터 교환(좀더 높은 수준의 애플리케이션)

MCU가 특정한 기능을 구현하려면 프로그래밍 과정을 거쳐야 한다. 예약 기능을 갖춘 밥솥을 개발해 한시간 안에 조리가 시작되도록 설정하려면 밥솥의 MCU가 이러한 일을 수행하도록 프로그램을 짜 넣어야 한다는 것. 오늘날 대부분의 전자 제품은 MCU를 탑재하고 있다.

▲<그림1.1, 그림1.2 : 인쇄회로기판 위에 부착된 MCU>

 

▲<그림1.3 : 다양한 형태와 사이즈로 제조 가능한 MCU>

전자 기기를 분해하는 것을 권하지는 않지만, 혹시 그럴 기회가 있다면 <그림1.2>와 같은 인쇄회로기판(PCB)위에 <그림1.1>과 같이 검정색 물체가 탑재된 것을 찾을 수 있을 것이다. 이 검정색 물체가 바로 MCU다. <그림1.3>에서 볼 수 있 듯 MCU는 다양한 형태와 크기로 제조할 수 있다.

◆MCU는 무엇을 하나

한마디로 무궁무진하다. 전자제품에서 우리가 익숙하게 사용하는 대부분의 기능이 MCU로 구현된다고 해도 과언이 아니다.

▲시각적 기능
시각적 기능은 사용자가 전자 기기의 동작 상태 정보를 확인할 수 있다는 점에서 매우 중요하다. 이 기능은 사용자가 동작 중인 기기의 상태를 확인하고 동작을 하지 않을 때에는 시간 확인의 용도로도 사용할 수 있다. 액정표시장치(LCD)나 발광다이오드(LEDs)상에 텍스트를 표시할 수 있다. 일부 가전제품에는 MCU가 단순히 LED빛을 켜거나 플래시 용도로 사용되기도 한다.

▲청각적 기능
전자레인지, 화재 알람 등 많은 전자제품이 음성 기능(speech synthesis functionality)을 제공한다. 음악이나 알람 소리를 통해 사용자에게 기기의 동작 상태를 알리기도 한다. 청각적 기능은 온도계, 혈압계와 같은 건강 기기에서도 흔히 찾아볼 수 있다.

▲모터/밸브 통제
MCU는 모터나 밸브를 제어하는 신호를 출력할 수 있다. 좀더 구체적으로 말하면, 모터의 방향이나 속도를 변환하거나, 밸브를 열고 닫는 신호를 출력할 수 있다. TV 리모콘의 적외선 빔 신호 역시 MCU가 출력하는 것이다.

▲전자 신호 측정 및 출력
MCU는 센서 부품의 전압을 직접 측정하는 기능을 가지고 있다. 예를 들어, 온도계와 같은 온도 센서와 직접 연결되면 MCU로 온도를 측정할 수 있다. 이와 마찬가지로, 빛(밝기) 센서와 연결되는 경우, MCU로 빛의 밝기 역시 측정할 수 있다. 배터리 전압을 측정해 교체 시기를 알려주기도 한다. 동시에 MCU는 특정 전압을 출력할 수 있다. 일정한 전압 출력이 가능하기 때문에, 다른 전자 부품에 기준 전압을 제공하는 레귤레이터 역할 수행도 가능하다.

▲통신
PC 사용이 증가함에 따라 USB(Universal Serial Bus)가 PC와 다른 디바이스를 연결하는 통신 인터페이스의 표준이 됐다. 이 때문에 MCU 역시 USB 연결 기능을 갖고 있다. MCU와 다른 MCU 사이의 간단한 데이터 교환도 가능하다. 자동차가 좋은 예다. 오늘날의 자동차는 ‘움직이는 통신 네트워크’다. 자동차 하나에는 수 많은 MCU가 사용되는데, 이 많은 MCU가 CAN(계측 제어기 통신망 Controller area networks), LIN(로컬 상호 연결 네트워크 Local interconnect network)을 지원해 차량 전체가 하나의 시스템으로 작동하게 한다.

▲계산
계산은 MCU가 만들어지게 된 본래 목적이다. 특정 작업을 처리하기 위해 MCU는 위에 언급한 여러 가지 기능을 통합하고 조율한다. 예를 들어 온도 센서에 의해 측정된 전압을 온도로 변환하여 표시하거나, 모터 사용량을 계산해 해당 모터의 성능을 조절하기도 한다. 하나의 작업을 처리하기 위해 필요한 여러 가지 기능을 통합하는 것이 MCU의 가장 중요한 기능 중 하나이다.

◆MCU의 활용 분야는

▲<그림2.1 : MCU가 탑재된 일상 가전 도구>

▲<그림2.1 : MCU가 탑재된 일상 가전 도구>

▲<그림2.1 : MCU가 탑재된 일상 가전 도구>

▲<그림2.1 : MCU가 탑재된 일상 가전 도구>

▲<그림2.2 : MCU가 탑재된 일상 가전 도구>


▲<그림2.2 : MCU가 탑재된 일상 가전 도구>

▲<그림2.2 : MCU가 탑재된 일상 가전 도구>

MCU의 활용 분야는 프로그래밍을 어떻게 하느냐에 따라 달라진다. 분명한 것은 그 범위가 매우 넓다는 것이다. <그림2.1>과 <그림2.2>는 MCU가 탑재된 일상 가전 도구의 예를 설명한 것이다.

MCU는 전자기기의 디스플레이, 타이머, 컴프레서 및 냉장고, 세탁기, 에어컨 등과 같은 주요 가전제품의 모터를 제어한다. 예를 들어 혈압기에 탑재된 MCU는 모터, 밸브, 디지털 디스플레이를 제어하고, 온도계의 MCU 는 온도 센서의 신호를 측정한다.

MCU가 가장 많이 사용되는 전자제품은 바로 리모콘일 것이다. 오늘날의 리모콘은 단순히 TV, 에어컨뿐 아니라, 전등, 선풍기의 동작까지도 제어한다. 또한 버튼의 누름을 탐지하고 리모콘이 전송하는 적외선 신호를 제어하는 것도 바로 MCU의 역할이다.

카메라 장비, 사이클링과 같은 취미 생활 도구에도 적용된다. 카메라에서 활용되는MCU는 자동 초점 기능, 셔터 스피드 및 떨림 방지 기능을 제어하며, 자전거는 속도계와 기어 변속기 부문에서 활용된다. 값이 비싼 자전거의 경우는 서스펜션까지도 MCU가 제어한다.

사무용 전자제품에서도 MCU 활용 사례를 쉽게 찾아 볼 수 있다. 산업 장비 뿐만 아니라,  가정용 전동 드릴 역시 MCU를 사용해 모터 스피드와 배터리 잔량을 체크한다. MCU는 계산기용으로 처음 개발됐다. 그렇기 때문에 MCU의 본래 목적은 고급 계산 작업을 처리하는 것이었다. 비록 일상 생활에서는 이러한 높은 수준의 계산은 크게 필요하지 않지만, 다양한 분야에서 활용이 가능하다.

▲<그림3 : 김매기에 특화된 아이가모 로봇(AIGAMO ROBOT)>

▲<그림4.1 : 휴대용 수면 무호흡증 테스트 기기>


▲<그림4.2 : 모델 헬리콥터>

ST마이크로일렉트로닉스의 STM32 시리즈 MCU는 <그림3>에서 볼 수 있듯이, 아이가모 로봇(AIGAMO ROBOT)에 탑재됐다. 이 작은 로봇은 일본 경제통상산업부를 대신해 기후지역 정보기술 연구소(Gifu Prefectural Research Institute of Information Technology)가 개발한 김매기 로봇이다. 또한, 같은 MCU가 휴대용 수면 무호흡증 테스트 기기<그림4.1> 및 모형 헬리콥터<그림4.2>의 자이로센서(Gyro sensor)와 거버너센서(Governor sensor)로 사용됐다.  위와 같은 예를 볼 때, MCU는 프로그래밍에 따라 단순 기기부터 최첨단 기술까지 광범위하게 활용될 수 있음을 알 수 있다.

◆가전제품 속 MCU의 역할

몇 가지 예를 통해 실제 생활 가전제품에서 MCU가 어떻게 활용되는지 좀 더 자세히 살펴보자.

▲혈압 모니터기
혈압 모니터기 한 대에는 상당히 많은 MCU 기능들을 활용되고 있다. <그림5>는 혈압 모니터기에 들어 있는 전자회로를 예로 보여준다. 아래 혈압 모니터기의 MCU 처리 동작들은 실제 혈압 모니터기가 작동하고 있을 때 사용되는 기능들이다. 처리 순서 번호는 <그림5>의 MCU 회로 번호와 일치하다.

▲<그림5 : 혈압 모니터기의 전자회로>

○사용자가 전원 스위치를 눌러 혈압 모니터를 작동시킨다.
○사용자가 검사 받는 이에 대한 정보를 입력하기 위해 버튼을 누른다. 여기서 MCU는 어떤 버튼이 눌리는지를 식별한다.
○사용자가 혈압 측정을 위해 시작 버튼을 누른다.
○모터가 작동을 시작하며 혈압기 소매에 공기를 주입한다. MCU는 드라이버(트랜지스터)에 신호를 보내고 드라이버는 모터를 작동시킨다.
○박동 수 체크 센서는 박동 수의 변화를 읽는다. 박동 수 센서가 읽은 신호는 전압으로 변환되고 MCU는 그 전압을 측정한다.
○혈압기 공기 밸브는 박동수 센서의 데이터에 맞게 조절된다. MCU는 드라이버(트랜지스터)에 신호를 보내고 드라이버는 공기 밸브를 조절한다.
○혈압기 모니터는 혈압 측정이 완료됨에 따라 알람을 울린다. MCU가 알람 작동 명령 신호를 보낸다.
○LCD에 측정 결과가 표시된다. MCU 가 LCD를 켠다.
○EEPROM(전기적 소거 및 프로그램이 가능한 읽기 전용 기억장치)이라 불리는 저장 기기에 측정 결과가 저장된다. MCU는 통신 기능을 이용해 EEPROM에 데이터를 전송한다.
○고급형 제품은 데이터 분석을 위해 PC에 측정 결과를 전송하는 기능을 가진다.
○미작동 중일시 혈압기 모니터는 현재 시각을 LCD 화면에 표시한다. MCU 가 시간을 측정하고 표시한다.
○혈압 측정과 직접적 연관은 없지만, 잔여 배터리 용량 역시 정기적으로 체크된다. MCU는 정기적으로 전력 공급 전압을 측정한다.

위의 항목을 통해 알 수 있듯이 한 개의 MCU는 수 많은 역할을 수행한다.

▲리모콘
<그림6>은 적외선 리모콘의 전자 회로다. 적외선 리모콘의 MCU가 처리하는 동작은 아래와 같다. 처리 순서 번호는 <그림6>의 MCU 회로 번호와 일치한다.

▲<그림6 : 리모콘의 전자회로>

○리모콘은 전원 스위치가 없다. 배터리가 장착됨과 동시에 사용 가능하기 때문이다. 리모콘이 사용되지 않을 때, MCU는 대기 모드로 변환되며, 전원버튼이 눌릴 때까지 배터리 전력을 최대한 절약한다.
○사용자가 버튼을 눌러 실행시킨다. MCU의 차단 기능은 어떤 버튼이 눌려졌는지를 식별하고, 대기 모드에서 벗어나 일반 동작 모드에 바뀐다. 이후 MCU는 눌린 버튼에 따라 동작을 수행한다.
○입력된 실행정보에 따라 적외선 신호가 전송된다. MCU는 적외선 신호를 출력하여 적외선LED화면을 켠다.
○LCD에 입력된 동작의 정보가 표시된다. MCU가 LCD를 동작 시킨다.
○만약 리모콘이 시계 기능을 갖추고 있으면, LCD는 리모콘이 작동을 하지 않을 때 현재 시각을 표시한다. MCU 가 시각을 측정하고 표시한다.

▲프로그래밍
MCU는 어떻게 프로그래밍이 되었는가에 따라 따라 다양하게 활용될 수 있다. 이는 프로그래밍 되어 있지 않는 MCU는 아무짝에도 쓸모 없다는 뜻이기도 하다. 일반적으로 윈도 PC를 통해 MCU와 관련된 프로그램을 짠다. 특정한 MCU 프로그래밍이 필요한 애플리케이션은 인터넷에서 다운로드 받을 수 있다. 일부 애플리케이션은 무료로 사용 가능하지만, 어떤 애플리케이션은 프로그램 사이즈가 제한적이거나 정해진 기간 동안만 무료로 사용할 수 있는 것도 있다.

프로그래밍이 완료되면 실행을 위해 MCU에 프로그램을 써넣어야 하는데, 이 작업을 위해서 디버거 및 프로그래머가 필요하다. 또한 MCU의 종류에 따라 특화된 디버거 및 프로그래머가 필요하다.

▲<그림7 : ST-링크 디버거와 프로그래머 샘플>

<그림7>은 ST마이크로일레트로닉스 제품인 ‘ST-링크’ 디버거와 프로그래머의 샘플을 보여주고 있다. 위 그림에서 PC와 ST-링크는 USB 케이블을 통해 연결되고 ST-링크와 PCB의 MCU는 전용 케이블로 연결된다. 언뜻 PCB와 ST-링크를 연결하고 있는 케이블이 많아 보일 수는 있지만 실제 4개의 라인만이 연결돼 있다(전원 공급 모니터를 위한 2 개 라인, 1개의 리셋 라인과 1개의 통제 신호 라인). 사용자는 반드시 PCB를 제작해야 하는데 이는 실제 MCU를 프로그래밍하고 사용하는데 가장 필요한 것이 PCB이기도 하기 때문이다.

글 : 마사루 스가이(ST마이크로 MMS그룹)

블로그 이미지

Link2Me

,
728x90

Audio Streaming 서버 코드를 구현한 걸 오픈한다.


<?php
$search = isset($_POST['audioPath'])? str_replace("/mp3files","",$_POST['audioPath']) : '';
$dir ='./mp3files'.$search;

echo getCurrentFileList($dir);
function getCurrentFileList($dir){
    $web_url = "http://localhost/_test";
    $valid_formats = array("mp3","wav");
    $handle = opendir($dir); // 디렉토리의 핸들을 얻어옴
    // 지정한 디렉토리에 있는 디렉토리와 파일들의 이름을 배열로 읽어들임
    $R = array(); // 결과 담을 변수 생성
    $cnt = 0;
    while ($entry = readdir($handle)) {
        if($entry == '.' || $entry == '..') continue;
        $getExt = pathinfo($entry, PATHINFO_EXTENSION); // 파일 확장자 구하기
        $curdir = substr($dir,1,strlen($dir)-1); // 현재 폴더 정보
        if(empty($getExt)){
            $subdir = $dir.'/'.$entry;
            $subdir = substr($subdir,1,strlen($subdir)-1);
            array_push($R,array("isFile"=>1,"fileName"=>$entry,"filePath"=>$subdir,"curPath"=>$curdir));
        } else {
            if(in_array($getExt, $valid_formats)){
                $filepath = $dir.'/'.$entry;
                $filepath = substr($filepath,1,strlen($filepath)-1);
                array_push($R,array("isFile"=>2,"fileName"=>$entry,"filePath"=>$filepath,"curPath"=>""));
            }
        }

        // 상위폴더
        $check = str_replace("/mp3files","",$curdir);
        if(strlen($check)>0 && $cnt < 1){ // 상위폴더는 1회만 추가되도록 처리
            $filePath = substr($curdir,0,strripos($curdir, "/")); // 상위폴더
            $updir = substr($filePath,0,strripos($filePath, "/")); // 차상위폴더
            array_push($R,array("isFile"=>0,"fileName"=>"상위폴더","filePath"=>$filePath,"curPath"=>$updir));
            $cnt++;
        }

    }
    closedir($handle);
    sort($R); // 안드로이드에서 가나다순으로 정렬하기 위해
    return json_encode(array("result"=>$R));
}

?>
 


블로그 이미지

Link2Me

,
728x90

음력 달력 예제를 가지고 수정해서 만들어본 코드다.


달력의 모양은 위와 같다.

ㅇ bootstrap 코드로 수정 보완

    - 해상도에 따라 일부 좀 수정해야 할 부분이 있음.

ㅇ jQuery 일정 등록 기능 추가

   - 해당 셀에서 마우스 클릭하면 일정 등록 추가 화면 팝업

   - 등록된 일정에 마우스를 클릭하면 삭제 여부 문의 및 삭제 처리

   - 코드를 좀 더 보완해야 할 듯....

ㅇ 음력 및 간지 지원 (음력 지원 DB 활용)

ㅇ 대체공휴일 코드 추가

    - 어린이날, 설날, 추석 대체공유일 코드

ㅇ 기념일 등록

    - 기념일을 등록하는 코드 파일은 미 구현(DB에 직접 기록하는 방법으로 테스트)

    - 태어난 연도 이전에는 표시되지 않도록 하는 코드는 미구현


음력은 함수 lun2sol.php 파일은 만세력 달력을 찾아보니 데이터가 불일치한다.

그래서 MySQL DB 데이터 기준으로 동작되도록 코드를 수정했다.

검색해보니 고영창 만세력 코드가 있는데 이것으로 테스트는 해봤지만 이 코드에 맞춰서 테스트는 아직 안해봤다.

MySQL DB파일 사이즈가 좀 되다보니 용량이 조금 크다고 볼 수도 있다.


테이블 구조

 CREATE TABLE IF NOT EXISTS `memorials` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `category` int(4) NOT NULL,
  `subject` text NOT NULL,
  `start_year` char(4) DEFAULT NULL,
  `memorial_date` varchar(4) NOT NULL,
  `dateType` tinyint(2) NOT NULL DEFAULT '0',
  `writing_date` date NOT NULL DEFAULT '0000-00-00',
  PRIMARY KEY (`id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=4 ;

--
-- 테이블의 덤프 데이터 `memorials`
--

INSERT INTO `memorials` (`id`, `category`, `subject`, `start_year`, `memorial_date`, `dateType`, `writing_date`) VALUES
(1, 1, '홍길동 생일', '1978', '0827', 1, '2018-10-30'),
(2, 1, '이정민 생일', '1979', '1215', 1, '2018-10-30'),
(3, 1, '홍진경 생일', '1992', '0614', 0, '2018-10-30');

-- --------------------------------------------------------

--
-- 테이블 구조 `memorial_data`
--

CREATE TABLE IF NOT EXISTS `memorial_data` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `relatedid` int(11) NOT NULL,
  `solar_date` date NOT NULL DEFAULT '0000-00-00',
  `lunar_date` date NOT NULL DEFAULT '0000-00-00',
  `yun` tinyint(1) NOT NULL DEFAULT '0',
  `subject` text NOT NULL,
  `category` int(4) NOT NULL,
  PRIMARY KEY (`id`),
  KEY `relatedid` (`relatedid`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;

-- --------------------------------------------------------

--
-- 테이블 구조 `tbl_events`
--

CREATE TABLE IF NOT EXISTS `tbl_events` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `title` varchar(255) NOT NULL,
  `start` date NOT NULL,
  `end` date DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;



<?php
define("PHP_SELF", $_SERVER['PHP_SELF']);
error_reporting(error_reporting() & ~E_NOTICE);
if (!isset($cellh))
    $cellh = 70; // date cell height
if (!isset($tablew))
    $tablew = 650; //table width
$cellw = 130;
//---- 오늘 날짜
$thisyear = date('Y'); // 4자리 연도
$thismonth = date('n'); // 0을 포함하지 않는 월
$today = date('j'); // 0을 포함하지 않는 일

// $year, $month 값이 없으면 현재 날짜
$year = isset($_GET['year']) ? $_GET['year'] : $thisyear;
$month = isset($_GET['month']) ? $_GET['month'] : $thismonth;
$day = isset($_GET['day']) ? $_GET['day'] : $today;

//------ 날짜의 범위 체크
if (($year > 2038) or ($year < 1900))
    ErrorMsg("연도는 1900 ~ 2038년만 가능합니다.");

$last_day = date('t', mktime(0, 0, 0, $month, 1, $year)); // 해당월의 총일수 구하기

$prevmonth = $month - 1;
$nextmonth = $month + 1;
$prevyear = $nextyear = $year;
if ($month == 1) {
    $prevmonth = 12;
    $prevyear = $year - 1;
} elseif ($month == 12) {
    $nextmonth = 1;
    $nextyear = $year + 1;
}
$pre_year = $year - 1;
$next_year = $year + 1;


include_once 'dbconnect.php'; // DB 연결
include_once 'lun2sol.php';  //양력.음력 변환 인클루드

/****************** lunar_date ************************/
$predate = date("Y-m-d", mktime(0, 0, 0, $month - 1, 1, $year));
$nextdate = date("Y-m-d", mktime(0, 0, 0, $month + 1, 1, $year));

$sql = "SELECT solar_date,ganji,lunar_date,yun FROM lunar_data where solar_date between '$predate' and '$nextdate' ";
$result = mysqli_query($dbconn, $sql) or die(mysqli_error($dbconn));
while ($R = mysqli_fetch_array($result)) {
    $lunarData[] = array(0 => date("n-j", strtotime($R['solar_date'])), 1 => $R['ganji'], 2 => date("n.j", strtotime($R['lunar_date'])), 3 => date("j", strtotime($R['lunar_date'])), 4 => $R['yun']);
}
//echo '<pre>';print_r($lunarData);echo '</pre>';
/****************** lunar_date ************************/

/****************** 기념일 데이터 ************************/
// 음력 기념일을 생성하면 시작년도부터 해당 양력일자를 자동으로 생성 처리??
$sql = "SELECT category,subject,memorial_date,dateType FROM memorials";
$result = mysqli_query($dbconn, $sql);
while ($R = mysqli_fetch_array($result)) {
    if($R['dateType'] == 1){ // 음력
        //$tmp = lun2sol($year . $R['memorial_date']); // 정확도가 맞는지 확인 필요
        $lunar_temp = $year ."-".substr($R['memorial_date'],0,2)."-".substr($R['memorial_date'],2,2);
        $rsql = "SELECT solar_date,num,yun,lunar_date FROM lunar_data where lunar_date='".$lunar_temp."'";
        $rs = mysqli_query($dbconn, $rsql);
        $RS = mysqli_fetch_array($rs);
        $tmp = strtotime($RS[0]);
        if(substr($RS[0],0,4) !== $year){ // 음력 기념일이 같은 해가 아니면
            $sql = "SELECT count(relatedid) FROM memorial_data where relatedid=".$RS[1]." and solar_date='".$RS[0]."' and yun=".$RS[2]." and subject='".$R['subject']."' ";
            $rt = mysqli_query($dbconn, $sql);
            $RT = mysqli_fetch_array($rt);
            if($RT[0] == 0){ // 일치하는 데이터가 없으면
                $sql ="INSERT INTO memorial_data (relatedid,solar_date,lunar_date,yun,subject,category) ";
                $sql.="VALUES (".$RS[1].",'".$RS[0]."','".$RS[3]."','".$RS[2]."','".$R['subject']."','".$R['category']."')";
                mysqli_query($dbconn, $sql);
            }
        }
    } else { // 양력
        $tmp = strtotime($year ."-".substr($R['memorial_date'],0,2)."-".substr($R['memorial_date'],2,2));
    }
    $memorialData[] = array(0 => date("n-j",$tmp), 1 => $R['category'], 2 => $R['subject']);
}

// 음력 기념일이 같은 해에 없는 경우 테이블에 생성된 데이터를 조회 및 추가
$sql = "SELECT solar_date,subject,category FROM memorial_data where solar_date between '$predate' and '$nextdate' ";
$result = mysqli_query($dbconn, $sql);
while ($R = mysqli_fetch_array($result)) {
    $tmp = strtotime($R[0]);
    $memorialData[] = array(0 => date("n-j",$tmp), 1 => $R['category'], 2 => $R['subject']);
}

/****************** 휴일 정의 ************************/
$Holidays = Array();
$Holidays[] = array(0 => '1-1', 1 => '신정');
$Holidays[] = array(0 => '3-1', 1 => '삼일절');
$Holidays[] = array(0 => '5-5', 1 => '어린이날');
$Holidays[] = array(0 => '6-6', 1 => '현충일');
$Holidays[] = array(0 => '7-17', 1 => '제헌절');
$Holidays[] = array(0 => '8-15', 1 => '광복절');
$Holidays[] = array(0 => '10-3', 1 => '개천절');
$Holidays[] = array(0 => '10-9', 1 => '한글날');
$Holidays[] = array(0 => '12-25', 1 => '성탄절');

//$tmp = lun2sol($year . "0101");  //설날
$tmp = strtotime(Lun2SolDate($year."-01-01"));
$Holidays[] = array(0 => date("n-j", ($tmp - (3600 * 24))), 1 => '');
$Holidays[] = array(0 => date("n-j", $tmp), 1 => '설날');
$Holidays[] = array(0 => date("n-j", ($tmp + (3600 * 24))), 1 => '');

//$tmp = lun2sol($year . "0408");  //석가탄신일
$tmp = strtotime(Lun2SolDate($year."-04-08"));
$Holidays[] = array(0 => date("n-j", $tmp), 1 => '석탄일');

//$tmp = lun2sol($year . "0815"); //추석
$tmp = strtotime(Lun2SolDate($year."-08-15"));
$Holidays[] = array(0 => date("n-j", ($tmp - (3600 * 24))), 1 => '');
$Holidays[] = array(0 => date("n-j", $tmp), 1 => '추석');
$Holidays[] = array(0 => date("n-j", ($tmp + (3600 * 24))), 1 => '');

// 어린이날 대체공휴일 검사 : 어린이날은 토요일, 일요일인 경우 그 다음 평일을 대체공유일로 지정
$childdayChk = isWeekend($year."-05-05");
if($childdayChk == 0) $Holidays[] = array(0 => date("n-j", strtotime($year."-05-06")), 1 => '대체공휴일');
if($childdayChk == 6) $Holidays[] = array(0 => date("n-j", strtotime($year."-05-07")), 1 => '대체공휴일');

// 설날 대체공휴일 검사
if(isWeekend(Lun2SolDate($year."-01-01")) == 0)
    $Holidays[] = array(0 => date("n-j", strtotime(Lun2SolDate($year."-01-03"))), 1 => '');
if(isWeekend(Lun2SolDate($year."-01-01")) == 1)
    $Holidays[] = array(0 => date("n-j", strtotime(Lun2SolDate($year."-01-03"))), 1 => '');
if(isWeekend(Lun2SolDate($year."-01-02")) == 0)
    $Holidays[] = array(0 => date("n-j", strtotime(Lun2SolDate($year."-01-03"))), 1 => '');


// 추석 대체공휴일 검사
if(isWeekend(Lun2SolDate($year."-08-14")) == 0)
    $Holidays[] = array(0 => date("n-j", strtotime(Lun2SolDate($year."-08-17"))), 1 => '');
if(isWeekend(Lun2SolDate($year."-08-15")) == 0)
    $Holidays[] = array(0 => date("n-j", strtotime(Lun2SolDate($year."-08-17"))), 1 => '');
if(isWeekend(Lun2SolDate($year."-08-16")) ==0)
    $Holidays[] = array(0 => date("n-j", strtotime(Lun2SolDate($year."-08-17"))), 1 => '');

/****************** 휴일 정의 ************************/

/****************** schedule ************************/
$sql = "SELECT * FROM tbl_events where start between '$predate' and '$nextdate' ";
$result = mysqli_query($dbconn, $sql);
while ($R = mysqli_fetch_array($result)) {
    $schedule[] = array(0 => date("n-j", strtotime($R['start'])), 1 =>date("n-j", strtotime($R['end'])) ,2 => $R['title'],3 => $R['id']);
}
//echo '<pre>';print_r($schedule);echo '</pre>';
/****************** schedule ************************/

?>

<!DOCTYPE html>
<html lang="ko">
<head>
<title>PHP Calendar</title>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="http://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css">
<style>
    body{margin-top: 20px; }
    .all {border-width: 1;border-color: #cccccc;border-style: solid;}
    font {font-family: 굴림체;font-size: 12px;color: #505050;    }
    font.title {font-family: 굴림체;font-size: 12px;font-weight: bold;color: #2579CF;    }
    font.week {font-family: 돋움,돋움체;color: #ffffff;font-size: 8pt;    letter-spacing: -1;}
    font.holy {font-family: tahoma;font-size: 22px;color: #FF6C21;}
    font.blue {font-family: tahoma;font-size: 22px;color: #0000FF;}
    font.black {font-family: tahoma;font-size: 22px;color: #000000;}
    font.lunar {font-family: tahoma;font-size: 14px;color: #0000bb;}
    font.gangi {font-family: tahoma;font-size: 14px;color: #424242;}
    font.sblue {font-family: tahoma;font-size: 14px;color: blue;    }
    font.green {font-family: tahoma;font-size: 14px;color: green;    }
    font.red {font-family: tahoma;font-size: 14px;color: red;}
    font.num {font-family: tahoma;font-size: 14px;background-color: #DBA901;}
    font.gray {font-family: tahoma;font-size: 14px;color: #bbbbbb;}
    .main {float: left;width: 70%;border: 5px solid #ccc;background-color: #fff;m }
    .right {float: right;width: 20%;background-color: #fff;border: 5px solid #eee;}
</style>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.2/jquery.min.js"></script>
<script src="http://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/js/bootstrap.min.js"></script>
<script>
$(document).ready(function() {
    $(".calcell").click(function(){
        var val=$(this).attr("id");
        var date = val.split('-');
        var year = date[0];
        var month = date[1];
        var day = date[2];
        var title = prompt('Event Title:');
        $.ajax({
            url : 'add-event.php',
            type : 'POST',
            data :{year:date[0],month:date[1],day:date[2],title:title},
            success : function(data){
                if(data == 1){
                    location.reload();
                } else if(data == 0) {
                    alert('등록에 실패했습니다.');
                }
            },
            error: function(jqXHR, textStatus, errorThrown){
                alert("arjax error : " + textStatus + "\n" + errorThrown);
            }
        });
    });

    $(".num").click(function(e){
        var val=$(this).attr("uid");
        var deleteMsg = confirm("정말 삭제하시겠습니까?");
        if(deleteMsg){
            $.ajax({
                url : 'delete-event.php',
                type : 'POST',
                data :{id:val},
                success: function (data) {
                    if(data == 1){
                        location.reload();
                    } else if(data == 0) {
                        alert('삭제에 실패했습니다.');
                    }
                }
            });
        }
    });
});
</script>
</head>
<body>
<div class="container">
<table class="table table-bordered table-responsive">
  <tr align="center" >
    <td>
        <a href=<?php echo 'calendar.php?year='.$pre_year.'&month='.$month . '&day=1'; ?>>◀◀</a>
    </td>
    <td>
        <a href=<?php echo 'calendar.php?year='.$prevyear.'&month='.$prevmonth . '&day=1'; ?>>◀</a>
    </td>
    <td height="50" bgcolor="#FFFFFF" colspan="3">
        <a href=<?php echo 'calendar.php?year=' . $thisyear . '&month=' . $thismonth . '&day=1'; ?>>
        <?php echo "&nbsp;&nbsp;" . $year . '년 ' . $month . '월 ' . "&nbsp;&nbsp;"; ?></a>
    </td>
    <td>
        <a href=<?php echo 'calendar.php?year='.$nextyear.'&month='.$nextmonth.'&day=1'; ?>>▶</a>
    </td>
    <td>
        <a href=<?php echo 'calendar.php?year='.$next_year.'&month='.$month.'&day=1'; ?>>▶▶</a>
    </td>
  </tr>
  <tr class="info">
    <th style="width:14%;text-align:center;">일</td>
    <th style="width:14%;text-align:center;">월</th>
    <th style="width:14%;text-align:center;">화</th>
    <th style="width:14%;text-align:center;">수</th>
    <th style="width:14%;text-align:center;">목</th>
    <th style="width:14%;text-align:center;">금</th>
    <th style="width:14%;text-align:center;">토</th>
  </tr>
  <tr height=<?php echo $cellh;?>>

<?php
    $date = 1;
    $offset = 0;
    $ck_row = 0;
    //프레임 사이즈 조절을 위한 체크인자
    $R = array();

    while ($date <= $last_day) {
        $mday = $date;

        if ($date == '1') {
            // 시작 요일 구하기 : date("w", strtotime($year."-".$month."-01"));
            $offset = date('w', mktime(0, 0, 0, $month, $date, $year)); // 0: 일요일, 6: 토요일
            SkipOffset($offset, mktime(0, 0, 0, $month, $date, $year));
        }
        if ($offset == 0)
            $style = "holy"; // 일요일 빨간색으로 표기
        else if($offset == 6)
            $style = "holy"; // 토요일 빨간색 또는 파란색
        else
            $style = "black";

        // 법정 공휴일
        for ($i = 0; $i < count($Holidays); $i++) {
            if ($Holidays[$i][0] == "$month-$date") {
                $style = "holy";
                $mday = "$date";
                $holidata = $Holidays[$i][1];
                break;
            }
        }

        // 음력 일자 및 간지 데이터
        for ($i = 0; $i < count($lunarData); $i++) {
            if ($lunarData[$i][0] == "$month-$date") {
                if($lunarData[$i][4] == 1){ // 윤달이면
                    $lunarday = '(閏)'.$lunarData[$i][2];
                } else {
                    $lunarday = $lunarData[$i][2];
                }
                $gaingi_text = $lunarData[$i][1];
            }
        }

        // 기념일 : 결혼, 생일, 제사, 기타 등
        for ($i = 0; $i < count($memorialData); $i++) {
            if ($memorialData[$i][0] == "$month-$date") {
                $memorialdata = $memorialData[$i][2];
                break;
            }
        }

        // 사용자 일정 데이터
        $dType1 = array();
        for ($i = 0; $i < count($schedule); $i++) {
            if ($schedule[$i][0] == "$month-$date") {
                $dType1[] = array(0=>$schedule[$i][2],1=>$schedule[$i][3]);
            }
        }
      
        if ($date == $today && $year == $thisyear && $month == $thismonth) { // 오늘 날짜
            echo "<td valign=top bgcolor=#99FFFF class='calcell' id='".$year."-".$month."-".$mday."'>";
        } else {
            echo "<td valign=top class='calcell' id='".$year."-".$month."-".$mday."'>";
        }
            CalendarPrint($style,$mday,$lunarday,$gaingi_text,$holidata,$memorialdata,$dType1);
            echo "</td>\n";

        // 출력후 값 초기화
        $holidata = "";
        $memorialdata ="";

        $date++; // 날짜 증가
        $offset++;
        if ($offset == 7) {
            echo "</tr>";
            if ($date <= $last_day) {
                echo "<tr height=$cellh>";
                $ck_row++;
            }
            $offset = 0;
        }

    }// end of while

    if ($offset != 0) {
        SkipOffset((7 - $offset), '', mktime(0, 0, 0, $month + 1, 1, $year));
        echo "</tr>\n";
    }
    echo("</td>\n");

    function ErrorMsg($msg) {
        echo " <script>window.alert('$msg');history.go(-1);</script>";
        exit;
    }

    function CalendarPrint($style,$mday,$lunarday,$gaingi,$holidata='',$memorialdata='',$dType1=''){
        echo "<font class=".$style.">$mday</font><br/>";
        echo "<font class=lunar>$lunarday</font><br/>";
        echo "<font class=gangi>$gaingi</font><br/>";
        if(strlen($holidata)>0) echo "<font class=red>$holidata</font><br/>";
        if(strlen($memorialdata)>0) echo "<font class=sblue>$memorialdata</font><br/>";
        if(count($dType1)>0) { // 배열 출력
            for ($i = 0; $i < count($dType1); $i++) {
                echo "<font class=num uid=".$dType1[$i][1].">".$dType1[$i][0]."</font><br/>";
            }
        }
    }

    function SkipOffset($no, $sdate = '', $edate = '') {
        for ($i = 1; $i <= $no; $i++) {
            $ck = $no - $i + 1;
            if ($sdate)
                $num = date('n.j', $sdate - (3600 * 24) * $ck);
            if ($edate)
                $num = date('n.j', $edate + (3600 * 24) * ($i - 1));

            echo "<td valign=top><font class=gray>$num</font></td>";
        }
    }

    function Lun2SolDate($date){
        global $dbconn;
        $sql = "SELECT solar_date FROM lunar_data where lunar_date='".$date."'";
        $result = mysqli_query($dbconn, $sql);
        $R = mysqli_fetch_array($result);
        return $R[0];
    }

    function isWeekend($date){
        // 앙력 날짜의 요일을 리턴
        // 일요일 0 토요일 6
        return date("w", strtotime($date));
    }

?>
    </tr>
</table>
</div>
</body>
</html>



코드 구현 파일

calendar.zip

lunar_data.zip


참조한 사이트

- 참조한 URL을 찾게되면 추가할 예정



본 자료가 도움되었다면 000 해주세요. 좋은 글 작성에 큰 힘이 됩니다.


'Web 프로그램 > PHP 응용 및 활용' 카테고리의 다른 글

PHP 날짜와 시간 차이  (0) 2019.03.26
jQuery Select Box 선택값 제어  (0) 2019.01.05
법정공휴일  (0) 2018.11.03
PHP 달력 만들기 소스  (0) 2018.10.30
날짜 선택  (0) 2018.10.26
블로그 이미지

Link2Me

,
728x90

법정공휴일은 '관공서의 공휴일에 관한 규정'(대통령령)에 의해 공휴일이 된 날을 말한다.
법령에 따르면 법정공휴일은 일요일, 국경일, 1월 1일, 음력 1월 1일(설날)과 전후 이틀, 석가탄신일(음력 4월 8일),
어린이날(5월 5일), 현충일(6월 6일), 음력 8월 15일(추석)과 전후 이틀, 성탄절(12월 25일),
보궐선거를 제외한 각종 선거투표일 등 정부에서 수시로 정하는 날 등이다.
국경일은 ‘국경일에 관한 법률’에 의한 3ㆍ1절, 제헌절, 광복절, 개천절, 한글날을 말한다.

대체공휴일제의 도입 (안 제3조)
– 설날, 추석 연휴가 다른 공휴일과 겹치는 경우 그 날 다음의 첫 번째 비공휴일을 공휴일로 함
– 어린이날이 토요일 또는 다른 공휴일과 겹치는 경우 그 날 다음의 첫 번째 비공휴일을 공휴일로 함
(어린이날 외의 토요일은 대체공휴일에 포함되지 않는다)


음력기준으로 법정공휴일인 설날, 추석과 어린이날은 대체 공휴일을 고려하여 코딩해야 한다.



블로그 이미지

Link2Me

,