2012. 3. 28. 09:56ㆍ99. 정리전 - IT/12. Javascript
Geolocation 활용
01. 단순 위도 경도 찾아내기
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<script>
// 위도 경도 획득 조건 명시
var options = {
enableHighAccuracy : true, // 위도 경도 provider가 여러게 있을경우 정확도가 높은게 우선순위로
timeout : 10000,
maximumAge : 6000 // provider는 device에서 가지고 있는 최신 위도 경도를 넘김
// 획득한 데이터가 6초가 지났다면 무의미 하므로 다시 획득하기 설정
}
window.onload = function() {
if (navigator.geolocation) {
var gps = navigator.geolocation;
// 위경도 획득
gps.getCurrentPosition(success , error, options);
}
}
function success(position) {
var lat = position.coords.latitude; // 위도
var lon = position.coords.longitude; // 경도
// altitude, speed, heading 등도 제공 된다면 추출 가능
alert(lat + " : " + lon);
}
function error(state) {
switch(state.code) {
case state.TIMEOUT:
alert("TIMEOUT");
break;
case state.POSITION_UNAVAILABLE:
alert("UNABAILABLE");
break;
case state.PERMISSION_DENIED:
alert("DENIED");
break;
case state.UNKNOWN_ERROR:
alert("ERROR");
break;
}
}
</script>
</head>
<body>
<div id="map" style="width:800px; height:600px;">
</div>
</body>
</html>
지도 서비스의 활용 요소
- 특정위치 위경도
- Maker : 지도에 그려야 되는 아이콘 이미지 (Zoom in out 이 안됨)
- geocoder (reverse geocoder) : 주소값과 위경도 맵핑
- overlay : 지도 위의 그림 Layer (Zoom in out 이 가능)
02. 지도위의 위도 경도 찾아내기
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<!-- 구글 open api 에서 제공하는 지도 로드 -->
<script src="http://maps.google.com/maps/api/js?v=3.3&sensor=true"></script>
<script>
// 위도 경도 획득 조건 명시
var options = {
enableHighAccuracy : true, // 위도 경도 provider가 여러게 있을경우 정확도가 높은게 우선순위로
timeout : 10000,
maximumAge : 6000 // provider는 device에서 가지고 있는 최신 위도 경도를 넘김
// 획득한 데이터가 6초가 지났다면 무의미 하므로 다시 획득하기 설정
}
window.onload = function() {
if (navigator.geolocation) {
var gps = navigator.geolocation;
// 위경도 획득
gps.getCurrentPosition(success , error, options);
}
}
function success(position) {
var lat = position.coords.latitude; // 위도
var lon = position.coords.longitude; // 경도
// altitude, speed, heading 등도 제공 된다면 추출 가능
// 지도 띄우기
var latLng = new google.maps.LatLng(lat, lon);
var opts = {
zoom : 16,
center : latLng, // 지도의 center는 현위치
mapTypeId : google.maps.MapTypeId.ROADMAP //or SATELLITE 지도의 종류는 평면지도
};
var map = new google.maps.Map(document.getElementById("map"), opts);
}
function error(state) {
switch(state.code) {
case state.TIMEOUT:
alert("TIMEOUT");
break;
case state.POSITION_UNAVAILABLE:
alert("UNABAILABLE");
break;
case state.PERMISSION_DENIED:
alert("DENIED");
break;
case state.UNKNOWN_ERROR:
alert("ERROR");
break;
}
}
</script>
</head>
<body>
<div id="map" style="width:800px; height:600px;">
</div>
</body>
</html>
03. 지도위의
<!DOCTYPE html>
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<!-- 구글 open api 에서 제공하는 지도 로드 -->
<script src="http://maps.google.com/maps/api/js?v=3.3&sensor=true"></script>
<script>
// 위도 경도 획득 조건 명시
var options = {
enableHighAccuracy : true, // 위도 경도 provider가 여러게 있을경우 정확도가 높은게 우선순위로
timeout : 10000,
maximumAge : 6000 // provider는 device에서 가지고 있는 최신 위도 경도를 넘김
// 획득한 데이터가 6초가 지났다면 무의미 하므로 다시 획득하기 설정
}
window.onload = function() {
if (navigator.geolocation) {
var gps = navigator.geolocation;
// 위경도 획득
gps.getCurrentPosition(success , error, options);
}
}
function success(position) {
var lat = position.coords.latitude; // 위도
var lon = position.coords.longitude; // 경도
// altitude, speed, heading 등도 제공 된다면 추출 가능
alert(lat + " : " + lon);
// 지도 띄우기
var latLng = new google.maps.LatLng(lat, lon);
var opts = {
zoom : 16,
center : latLng, // 지도의 center는 현위치
mapTypeId : google.maps.MapTypeId.ROADMAP //or SATELLITE 지도의 종류는 평면지도
};
var map = new google.maps.Map(document.getElementById("map"), opts);
// 사용자의 위치 Marker
var marker1 = new google.maps.Marker({
position : latLng,
title : 'hello',
map : map,
icon : 'iconb1.png'
});
// 회사의 위치 Marker
var latLng1 = new google.maps.LatLng(37.5, 127.01);
var marker2 = new google.maps.Marker({
position : latLng1,
title : 'company',
map : map,
icon : 'iconr1.png'
});
// reverse geocoding (위도와 경도를 주소값으로 바꿔줌)
var geocoder = new google.maps.Geocoder();
if (geocoder) {
geocoder.geocode({
'latLng' : latLng
}, function (results, status) {
if (status == google.maps.GeocoderStatus.OK) {
if (results[1]) {
alert(results[1].formatted_address);
}
}
})
}
}
function error(state) {
switch(state.code) {
case state.TIMEOUT:
alert("TIMEOUT");
break;
case state.POSITION_UNAVAILABLE:
alert("UNABAILABLE");
break;
case state.PERMISSION_DENIED:
alert("DENIED");
break;
case state.UNKNOWN_ERROR:
alert("ERROR");
break;
}
}
</script>
</head>
<body>
<div id="map" style="width:800px; height:600px;">
</div>
</body>
</html>
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
WEBKIT 기반의 웹브라우져 - SMART TV 가 구동가능
- viewPort 의 meta tag : 화면사이즈를 늘리거나 줄이기 위한 tag
- Media Query : 반응형 web design 에 사용- 서버의 하나의 UI를 엑세스 할 때 각기 다른 device(PC, 각종mobile) 에서는
(CSS3 설정) 필요한 요소만 view에 보여준다 (클라이언트 쪽에서 CSS3를 이용하여 서버에서 내려받은 UI 결정)
01. meta tag 및 viewport 설정 예제
<!DOCTYPE html>
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<!------------------------------------------------------->
<!-- rel 은 본 프로그램이 구동되는 브라우져가 인식되는 명령어 -->
<!------------------------------------------------------->
<!-- iPhone의 바로가기 아이콘 -->
<link rel="apple-touch-icon" href="han_icon.png" />
<!-- android의 바로가기 아이콘 -->
<link rel="shortcut icon" href="han_icon.ico" />
<!-- iPhone의 바로가기 아이콘을 눌러 화면이 뜰때 잠깐 보이는 이미지 -->
<link rel="apple-touch-startup-image" href="han_start.png" />
<!-- iPhone web app 효과적용! url 입력bar가 사라짐 -->
<meta name="apple-mobile-web-app-capable" content="yes" />
<!-- 자동화면 조절(아래의 tag 없이 실행시키면 컴퍼넌트는 상당히 작게 나옴) -->
<meta name="viewport" content="width=480, initial-scale=1.0, user-scalable=no" />
</head>
<body>
<p> viewPort 관련 실습 </p>
<p> <input type="text" /> </p>
<p> <button>button</button> </p>
</body>
</html>
이하와 같이 아이폰 테스트 (MobiOne Test Center 를 이용하여 테스트)
01. 화면이 알맞게 늘려져 나옴을 확인
02.바탕화면에 바로가기 설정
03. 바탕화면에 바로가기 아이콘이 지정한 이미지로 표시됨 04. 페이지 시작시 지정한 이미지가 잠깐 보임
02. Media Query 설정 예제
n-screen.html
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<link rel="stylesheet" type="text/css" href="n-screen.css" />
</head>
<body>
<div id="container">
<!-- 메인 메뉴 -->
<div id="nav">
<ul>
<li>AAA</li>
<li>BBB</li>
<li>CCC</li>
</ul>
</div>
<!-- 메인 본문 -->
<div id="content">
<ul>
<h2>AAA의 콘텐츠</h2>
<p>
<img class="feature-image" src="han_start.png">
AAAAAAAAAA
</p>
</ul>
</div>
<!-- 부가 컨텐츠 영역 -->
<div id="extras">
<ul>
<h2>이외의 소식</h2>
<p>
ZZZZZZZZZ
</p>
</ul>
</div>
</div>
</body>
</html>
n-screen.css
/****************/
/* #은 id 값설정 */
/****************/
#container {
float : left;
width : 1000px;
background : #bbb;
}
#nav {
float : left;
width : 200px;
background : green;
}
#content {
float : left;
width : 550px;
margin : 0 0 0 25px
background : blue;
}
#extras {
float : right;
width : 200px;
background : red;
}
/*********************/
/* .은 클레스 속성 설정 */
/*********************/
.feature-image
{
float : right;
margin : 0 0 10px 10px
}
/* 웹페이지가 width가 999px 이하의 크기에서 뜬다면 상기를 포함한 아래의 내용도 추가하여 보여준다 */
@media screen and (max-width:999px)
{
#container { width:800px; }
#extras
{
clear : left;
float : none;
margin : 0 0 0 255px;
width : 550px;
}
}
/* 웹페이지가 width가 480px 이하의 크기에서 뜬다면 상기를 포함한 아래의 내용도 추가하여 보여준다 */
@media screen and (max-width:480px)
{
#container { width:400px; }
#content
{
float : none;
width : auto;
margin : 0;
}
#nav
{
float : none;
width : auto;
}
#extras
{
float : none;
width : auto;
margin : 0;
}
.feature-image { display:none; }
}
결과 (창의 크기에 따라 Media Query (CSS3 Style에 의해 컨텐츠의 형태가 변함)
--------------------------------------
MOBILE UI FRAMEWORK 현황
--------------------------------------
JAVASCRIPT FRAMEWORK 의 종류별 기술 지원현황
링크 : http://www.markus-falk.com/mobile-frameworks-comparison-chart/
Target
Native app ? (code 작성은 JS로하지만 컴파일을 통하여 해당 기계의 코드로 변환되어 실행되는 형태) Hybrid app ?
Mobile website ?
WebApp ?
지원하는 기능에 의해 여러가지 frame work를 혼재하여 사용가능 (jQuery + phone gap)
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
JQM (jQuery Mobile) - http://jquerymobile.com/
+- HTML +- JQTouch (2010)
| +- JQuery Mobile, 12k (2010.12 alpha) : jQuery 단체의 공식 제품 (plugin 제공)
+- JavaScript + Sencha, 300k (유료)
+ Jo App (OpenSource)
+ zeptoss, 2k - UI (X) , Hybrid 기능 (X)
- 일반적인 모바일영 web page를 만드는데 무거운 lib를 사용하지 않기 위해 초경량
사용법 : jQuery + jQuery Mobile 두개를 다운로드한다. (실장시 스크립트 순서상 로딩순서 중요)
index.html
<!DOCTYPE html>
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<link rel="stylesheet" href="./libs/jquery.mobile-1.0.css" />
<script src="./libs/jquery-1.6.4.js"></script>
<script src="./libs/jquery.mobile-1.0.js"></script>
</head>
<body>
<div data-role="page" id="home" data-add-back-btn="true">
<div data-role="header">
<h1>HOME</h1>
</div>
<div data-role="content">
<p>HOME 화면내용출력</p>
<p><a href="#about" data-role="button">ABOUT</a></p>
<!-- target 페이지를 dialog 로 띄워줌 -->
<p><a href="#pop" data-role="button" data-rel="dialog">POP</a></p>
</div>
</div>
<div data-role="page" id="about" data-add-back-btn="true">
<div data-role="header">
<h1>ABOUT</h1>
</div>
<div data-role="content">
<p>ABOUT 화면내용출력</p>
</div>
</div>
<div data-role="page" id="pop">
<div data-role="header">
<h1>POP</h1>
</div>
<div data-role="content">
<p>POP 화면내용출력</p>
<P><a href="#" data-role="button" data-rel="back">close</a></P>
</div>
</div>
</body>
</html>
출력결과
외부링크를 열기
01. some.html 을 ajax를 제거하여 열기
02. jsp 페이지를 mobileinit 하여 링크걸기
index.html
<!DOCTYPE html>
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<link rel="stylesheet" href="./libs/jquery.mobile-1.0.css" />
<script src="./libs/jquery-1.6.4.js"></script>
<!-- 반드시 주의할 것
mobileinit 는 <script src="./libs/jquery.mobile-1.0.js"></script> 에서 이미
mobileinit 라는 동일한 펑션이 로딩되어 있으므로 반드시 상기의 js쿼리 위에 위치하게 한다
-->
<script>
// link1에 tap 이벤트를 걸면 tap 오른쪽의 function이 실행됨
$(document).bind("mobileinit", function() {
$('#link1').live('tap', function() {
$.mobile.changePage("#about", {
transition : 'pop',
reverse : false,
changeHash : false
});
});
$('#link2').live('tap', function() {
$.mobile.changePage("some.jsp", {
transition : 'pop',
type : 'post',
data : $('#form1').serialize()
});
});
});
</script>
<script src="./libs/jquery.mobile-1.0.js"></script>
<!-- 외부링크 페이지를 javascript로 -->
</head>
<body>
<!-- PAGE1 (data-add-back-btn="true"를 추가해도 어차피 시작페이지에서는 안나옴)-->
<div data-role="page" id="home" data-add-back-btn="true">
<div data-role="header">
<h1>HOME</h1>
</div>
<div data-role="content">
<p>HOME 화면내용출력</p>
<p><a href="#about" data-role="button">ABOUT</a></p>
<!-- target 페이지를 dialog 로 띄워줌 -->
<p><a href="#pop" data-role="button" data-rel="dialog">POP</a></p>
<!-- target 페이지를 외부링크로 걸면 ajax의 동작에 의해 some.html의 body 코드만 자동으로 가져옴!!! -->
<p><a href="some.html" data-role="button">some1.html</a></p>
<!-- target 페이지를 외부링크로 걸면 rel="external"에 의해 some.html의 모든 코드를 실행하게됨 -->
<p><a href="some.html" data-role="button" rel="external">some2.html</a></p>
<!-- target 페이지를 외부링크로 걸때 javascript로 -->
<p><a href="#" id="link1" data-role="button">about api</a></p>
</div>
</div>
<!-- PAGE2 -->
<div data-role="page" id="about" data-add-back-btn="true">
<div data-role="header">
<h1>ABOUT</h1>
</div>
<div data-role="content">
<p>ABOUT 화면내용출력</p>
<p>
<form id="form1">
<p><input type="text" name="a1" /></p>
<p><input type="text" name="a2" /></p>
<p><input type="checkbox" name="a3" value="a3 check" /></p>
<p><a href="#" id="link2" data-role="button">submit</a></p>
</form>
</p>
</div>
</div>
<!-- PAGE3 -->
<div data-role="page" id="pop">
<div data-role="header">
<h1>POP</h1>
</div>
<div data-role="content">
<p>POP 화면내용출력</p>
<P><a href="#" data-role="button" data-rel="back">close</a></P>
</div>
</div>
</body>
</html>
some.html
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<script>
window.onload=function() {
alert("some.html start!");
}
</script>
</head>
<body>
<div data-role="page" id="some">
<div data-role="header">
<h1>SOME</h1>
</div>
<div data-role="content">
<p>SOME 화면내용출력</p>
</div>
</div>
</body>
</html>
some.jsp
<!DOCTYPE html>
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
</head>
<body>
<div data-role="page" id="submit">
<div data-role="header">
<h1>SUBMIT</h1>
</div>
<div data-role="content">
${param.a1} - ${param.a2} - ${param.a3}
</div>
</div>
</body>
</html>
출력결과
그 밖의 JQM 기능들 확인하기
01.
list.html
<!-- 외부 링크는 반드시 rel="external" 을 사용하여야 외부링크 페이지에 걸려있는 링크가 작동한다 -->
<!DOCTYPE html>
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<link rel="stylesheet" href="./libs/jquery.mobile-1.0.css" />
<script src="./libs/jquery-1.6.4.js"></script>
<script src="./libs/jquery.mobile-1.0.js"></script>
<!-- 모든 li tag 에다 걸겠다!!! -->
<script>
window.onload=function() {
$("li").live("click", function() {
alert($(this).index() + " : " + $(this).text());
});
}
function addItem() {
if ($('#hello li').size() > 0) {
// list의 마지막 index 의 데이터 삭제
$('#hello li').eq($('#hello li').size() -1).remove();
}
// list 데이터 추가
$('#hello').append("<li>some data</li>");
// 중요!!!! 데이터를 추가 하면 반드시 데이터를 refresh 한다!!!!
$('#hello').listview('refresh');
}
</script>
<title>Insert title here</title>
</head>
<body>
<div data-role="page" id="home">
<div data-role="header">
<h1>LIST</h1>
</div>
<div data-role="content">
<p>
<ul data-role="listview" data-inset="true" data-filter="true">
<li data-role="list-divider">ㄱ</li>
<li>강성윤</li>
<li>김길동</li>
<li>구길동</li>
</ul>
<ul data-role="listview" data-inset="true" data-filter="true">
<li data-role="list-divider">ㄴ</li>
<li>나성윤</li>
<li>남길동</li>
<li>날길동</li>
</ul>
</p>
<p>
<ul data-role="listview" data-split-icon="gear" data-split-theme="a">
<li>
<a href="index.html">
<img src="album-af.jpg" /><h3>카라</h3>
<p>한승연</p>
</a>
<a href="index.html">hello</a>
</li>
<li>
<a href="index.html">
<img src="album-af.jpg" /><h3>카라</h3>
<p>한승연</p>
</a>
<span class="ui-li-count">34</span>
</li>
</ul>
</p>
<p>
<ul id="hello" data-role="listview">
<li>item1</li>
<li>item2</li>
<li>item3</li>
</ul>
</p>
<p>
<a href="javascript:addItem()" data-role="button">add</a>
</p>
</div>
<div data-role="footer">
<h1>fotter</h1>
</div>
</div>
</body>
</html>
출력결과
EVENT API
main.html
<html>
<head>
<meta charset=EUC-KR">
<title>Insert title here</title>
<link rel="stylesheet" href="./libs/jquery.mobile-1.0.css" />
<script src="./libs/jquery-1.6.4.js"></script>
<script src="./libs/jquery.mobile-1.0.js"></script>
<script src="my.js"></script>
<script>
// tag에 있는 data-role=page 속성명으로 페이지가 처음실행될때 한번만 받아온다.
$("[data-role=page]").live("pagecreate", function(event) {
if (this.id == "mainList") {
alert("mainList Page");
getMainListData(); // my.js 에 정의됨
} else if (this.id == "subList") {
alert("subList");
getSubListData();
}
});
</script>
</head>
<body>
<!-- mainList Page -->
<div data-role="page" id="mainList">
<div data-role="header" data-position="fixed">
<h1>MainList</h1>
</div>
<div data-role="content">
<ul data-role="listview" id="mainListView"></ul>
</div>
</div>
<!-- subList Page -->
<div data-role="page" id="subList" data-add-back-btn="true">
<div data-role="header" data-position="fixed">
<h1>SubList</h1>
</div>
<div data-role="content">
<ul data-role="listview" id="subListView"></ul>
</div>
</div>
</body>
</html>
my.js
// mainList를 위해 서버 요청하는 함수
function getMainListData() {
// jQuery 가 손쉽게 ajax를 사용할 수 있게 제공하는 방법으로 코딩
$.ajax({
type : 'GET',
url : "http://localhost:8080/CH7-JQM/serverfile/main.jsp",
success : function(msg) {
handleMainList(msg);
}
});
}
//서버로부터 받은 mainList data로 화면 구성
function handleMainList(msg) {
// 화면구성
var array_data = msg.split("@");
var listview = $('#mainListView');
for (var i=0 ; i<array_data.length ; i++) {
var array_data2 = array_data[i].split("|");
var txt = "<li>"
+ " <a my-data=" + array_data[0] + " href='#'>"
+ " <h3>" + array_data2[1] + "</h3><p>" + array_data2[2] + "</p>"
+ " </a>"
+ "</li>";
listview.append(txt);
}
// listview는 데이터 갱신후 반드시 refresh로 화면 갱신 필요!!!
listview.listview('refresh');
// mainList의 각 항목을 눌렀을때 개발자 임의 이벤트 발생시켜 데이터를 sub로 전달하고자
// subList에 aaa(임의의 이벤트)라는 이벤트를 달아라
// 화면과 화면간이 아닌 한 하나의 html내에서 page전환을 할때 주로 사용하는 방식임
$('#subList').bind("aaa", function(e, args) {
alert("selected option : " + args.sel);
});
// mainList 라는 아이디 값을 가진 ul li 테그에 a 테그로 클릭 이벤트가 발생하면 function 을 실행하라
$("#mainList ul li").delegate("a", "click", function() {
var attr = $(this).attr("my-data");
myChangePage("#subList", {"sel":attr});
});
}
//javascript 에서 동적으로 페이지 로딩하는 함수
//지정된 url로 페이지 이동 및 페이지 이동시 남길 데이터 전달을 위한 이벤트 발생
function myChangePage(page, args) {
// 화면전환
$.mobile.changePage(page, {
transition : 'slide'
});
// 화면 전환시 이 순간 서버 요청이 들어가는건 아님
// 클라이언트 사이드에서 준비한 page가 단순히 화면에 보이는 것 뿐이다
// 페이지간의 데이터 전달이 기존의 서버연동에 의한 방법과는 상이하게 고민
// 개발자 임의의 데이터 발생으로 데이터 전달
$(page).trigger("aaa", args);
}
function getSubListData(msg) {
$.ajax({
type : 'GET',
url : "http://localhost:8080/CH7-JQM/serverfile/sub.jsp",
success : function(msg) {
handleSubList(msg);
}
});
}
function handleSubList(msg) {
// 화면구성
var array_data = msg.split("@");
var listview = $('#subListView');
for (var i=0 ; i<array_data.length ; i++) {
var array_data2 = array_data[i].split("|");
var txt = "<li>"
+ " <a href='#'>"
+ " <h3>" + array_data2[0] + "</h3>"
+ " </a>"
+ "</li>";
listview.append(txt);
}
// listview는 데이터 갱신후 반드시 refresh로 화면 갱신 필요!!!
listview.listview('refresh');
}
main.jsp
sub.jsp
곤지암리조트|127.290676|37.3368986|031-760-3939|가평군 외서면 하판리 산1-1@베어스타운|127.2512501|37.79719408|031-532-2534|포천시 내촌면 소학리 291-1@서울스키리조트|127.257897|37.64679918|031-591-1230|남양주시 호평동 산37-18@스타힐리조트|127.2670143|37.66200039|031-594-1211|남양주시 화도읍 묵현리 548@지산리조트|127.3434584|37.20999234|031-330-1541|이천시 마장면 해월리 산28-1@파인리조트|127.2984029|37.21099965|031-388-2001|용인시 처인구 양지면 남곡리 34-1@호명산|127.4118882|37.92062648|031-234-7525|광주시 도척면 도웅리 산 40-1