성태의 닷넷 이야기
홈 주인
모아 놓은 자료
프로그래밍
질문/답변
사용자 관리
사용자
메뉴
아티클
외부 아티클
유용한 코드
온라인 기능
MathJax 입력기
최근 덧글
[정성태] Working with Rust Libraries from C#...
[정성태] Detecting blocking calls using asyn...
[정성태] 아쉽게도, 커뮤니티는 아니고 개인 블로그입니다. ^^
[정성태] 질문이 잘 이해가 안 됩니다. 우선, 해당 소스코드에서 ILis...
[양승조
] var대신 dinamic으로 선언해서 해결은 했습니다. 맞는 해...
[양승조
] 또 막혔습니다. ㅠㅠ var list = props[i].Ge...
[양승조
] 아. 감사합니다. 어제는 안됐던것 같은데....정신을 차려야겠네...
[정성태] "props[i].GetValue(props[i])" 코드에서 ...
[정성태] 저렇게 조각 코드 말고, 실제로 재현이 되는 예제 프로젝트를 압...
[정성태] Modules 창(Ctrl+Shift+U)을 띄워서, 해당 Op...
글쓰기
제목
이름
암호
전자우편
HTML
홈페이지
유형
제니퍼 .NET
닷넷
COM 개체 관련
스크립트
VC++
VS.NET IDE
Windows
Team Foundation Server
디버깅 기술
오류 유형
개발 환경 구성
웹
기타
Linux
Java
DDK
Math
Phone
Graphics
사물인터넷
부모글 보이기/감추기
내용
<div style='display: inline'> <h1 style='font-family: Malgun Gothic, Consolas; font-size: 20pt; color: #006699; text-align: center; font-weight: bold'>Xamarin - 기존 리모컨 기능을 핸드폰의 적외선 송신으로 구현</h1> <p> 집에 있는 리모컨의 기능을 핸드폰으로 복사하는 것이 가능합니다. 이를 위해서는 우선 기존 리모컨들의 신호 값을 알아야 하는데, 다음의 글에 따라 아두이노를 이용하면 가능합니다.<br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > 아두이노에서 적외선 수신기 기본 사용법 ; <a target='tab' href='http://www.sysnet.pe.kr/2/0/11670'>http://www.sysnet.pe.kr/2/0/11670</a> </pre> <br /> 사실 송신 기능도 핸드폰 대신 아두이노를 이용한 송신기로 구현할 수는 있습니다.<br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > 아두이노에서 적외선 송신기 기본 사용법 ; <a target='tab' href='http://www.sysnet.pe.kr/2/0/11671'>http://www.sysnet.pe.kr/2/0/11671</a> </pre> <br /> 문제는 저런 식으로 아두이노로 구현하는 것은 불편한 면이 많습니다. 가령, 현실적으로 쓰기 위해선 기능에 따른 버튼도 더 늘려야 하고 브레드보드가 아닌 만능 기판에, ... 케이스까지 만들기 위해 3D 프린터라든가 기타 여러 도구들까지 장만을 해야 합니다. (사실, 언젠가는 저도 ^^ 그렇게까지 해보고 싶습니다.) 그런데, 생각해 보면 마감 잘 된 도구가 하나 있습니다. 바로 휴대폰입니다. 검색해 보면 마침 API 19(KitKat)부터 적외선 송신 기능도 제공한다고 합니다.<br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > Using Infrared port ; <a target='tab' href='https://forums.xamarin.com/discussion/12205/using-infrared-port'>https://forums.xamarin.com/discussion/12205/using-infrared-port</a> </pre> <br /> Xamarin의 경우 ConsumerIrManager 타입을 이용해,<br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > Android.Hardware.ConsumerIrManager Class ; <a target='tab' href='https://developer.xamarin.com/api/type/Android.Hardware.ConsumerIrManager/'>https://developer.xamarin.com/api/type/Android.Hardware.ConsumerIrManager/</a> </pre> <br /> 쉽게 접근할 수 있습니다. 그럼 뭐, 다 준비된 거죠. ^^ Visual Studio에서 Xamarin 프로젝트를 생성하고 해당 App에서 적외선 송신 기능을 사용하겠다는 요구를 manifest에 기록하고,<br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > <?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android" android:versionCode="1" android:versionName="1.0" package="IRController.IRController"> <uses-sdk android:minSdkVersion="21" android:targetSdkVersion="27" /> <span style='color: blue; font-weight: bold'><uses-permission android:name="android.permission.TRANSMIT_IR"></uses-permission></span> <application android:allowBackup="true" android:icon="@mipmap/ic_launcher" android:label="@string/app_name" android:roundIcon="@mipmap/ic_launcher_round" android:supportsRtl="true" android:theme="@style/AppTheme"> </application> </manifest> </pre> <br /> 다음과 같이 리모컨 기능을 대신할 버튼을 만든 다음,<br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > <?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent"> <span style='color: blue; font-weight: bold'><Button android:text="Button" android:layout_width="wrap_content" android:layout_height="wrap_content" android:minWidth="25px" android:minHeight="25px" android:id="@+id/btnTurnLightOnOff" /></span> </RelativeLayout> </pre> <br /> 이것을 누르면 그에 해당하는 적외선 송신을 하면 됩니다. <br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > using Android.App; using Android.OS; using Android.Support.V7.App; using Android.Runtime; using Android.Widget; using Android.Content; namespace IRController { [Activity(Label = "@string/app_name", Theme = "@style/AppTheme", MainLauncher = true)] public class MainActivity : AppCompatActivity { Android.Hardware.ConsumerIrManager _ir; protected override void OnCreate(Bundle savedInstanceState) { base.OnCreate(savedInstanceState); SetContentView(Resource.Layout.activity_main); <span style='color: blue; font-weight: bold'>Button button = FindViewById<Button>(Resource.Id.btnTurnLightOnOff); button.Click += btnTurnLightOnOff_Click;</span> } <span style='color: blue; font-weight: bold'>private void btnTurnLightOnOff_Click(object sender, System.EventArgs e) { _ir = ApplicationContext.GetSystemService(Context.ConsumerIrService) as Android.Hardware.ConsumerIrManager; int [] light_onoff_signal_buf = { 3550, 1750, 600, 400, 600, 1800, 550, 450, 600, 450, 600, 1800, 550, 450, 600, 450, 600, 500, 600, 450, 600, 400, 650, 400, 550 }; _ir.Transmit(38, light_onoff_signal_buf); }</span> } } </pre> <br /> 위의 코드에서 Transmit 메서드를 보면,<br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > Android.Hardware.ConsumerIrManager.Transmit Method ; <a target='tab' href='https://developer.xamarin.com/api/member/Android.Hardware.ConsumerIrManager.Transmit/p/System.Int32/System.Int32[]/'>https://developer.xamarin.com/api/member/Android.Hardware.ConsumerIrManager.Transmit/p/System.Int32/System.Int32[]/</a> </pre> <br /> 지난번 "<a target='tab' href='http://www.sysnet.pe.kr/2/0/11671'>아두이노에서 적외선 송신기 기본 사용법</a>"의 코드와 거의 똑같다는 것을 알 수 있습니다. 즉, Raw Data와 함께 주파수만 지정하면 되는 것입니다.<br /> <br /> 제가 가지고 있는 핸드폰이 LG V20인데 다행히 적외선 송신 기능이 있는 제품입니다. 위의 앱을 설치해서 실행해 보면, 와~~~ ^^ 정말 핸드폰으로 형광등을 On/Off 하는 것이 가능해졌습니다. 그런데, 여기서 문제가 있습니다. V20 핸드폰의 적외선 송신기가 원래의 형광등을 제어하던 리모컨의 출력보다 약한 것 같습니다. 재미있는 것은 동일 높이의 정면에서 하면 핸드폰으로 잘 동작을 하는데 높이가 달라지거나 사잇각이 커지면 핸드폰으로는 대상 수신기에서 잘 잡아내지 못합니다.<br /> <br /> 종합해 보면, 어떤 적외선 수신 제품을 (현실적으로) 제어하고 싶은 경우라면 직접 핸드폰에서 신호를 보내는 것보다는 네트워크 기능이 있는 아두이노를 상시 켜 놓고 그 아두이노의 적외선 송신기를 (잘 수신이 되도록 위치를 잡아 놓고) 사용하는 것이 좋을 것 같습니다. 암튼, 좀 아쉽군요. ^^ 핸드폰 하나로 다 될 것 같아서 기대에 부풀었는데.<br /> <br /> (<a target='tab' href='http://www.sysnet.pe.kr/bbs/DownloadAttachment.aspx?fid=1360&boardid=331301885'>첨부 파일은 이 글의 Android/Xamarin 프로젝트</a>입니다.)<br /> <br /> <hr style='width: 50%' /><br /> <br /> 적외선 통신을 다루면서 왜 38Khz를 고정 상수로 전달할까... 하는 의문이 있었는데요, 다음의 글에서 이를 설명하고 있습니다.<br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > 적외선 통신을 알아보자. ; <a target='tab' href='http://dokkodai.tistory.com/106'>http://dokkodai.tistory.com/106</a> </pre> <br /> 즉, 적외선 통신은 37 ~ 42 Khz로 변조를 한다는데, 리모컨의 경우 38Khz로 하는 것이 일반적이라고 합니다.<br /> <br /> <hr style='width: 50%' /><br /> <br /> 참고로, 다음과 같은 식의 오류가 발생한다면?<br /> <br /> <pre style='margin: 10px 0px 10px 10px; padding: 10px 0px 10px 10px; background-color: #fbedbb; overflow: auto; font-family: Consolas, Verdana;' > Unhandled Exception: Java.Lang.SecurityException: <Timeout exceeded getting exception details> occurred </pre> <br /> "Timeout"이긴 하지만 예외의 종류가 SecurityException인 것이 더 중요합니다. 즉, IR 기능 사용에 대한 사용자 허락을 받을 수 있도록 manifest에 "android.permission.TRANSMIT_IR" 권한 요구를 명시하지 않아서 그런 것입니다.<br /> </p><br /> <br /><hr /><span style='color: Maroon'>[이 글에 대해서 여러분들과 의견을 공유하고 싶습니다. 틀리거나 미흡한 부분 또는 의문 사항이 있으시면 언제든 댓글 남겨주십시오.]</span> </div>
첨부파일
스팸 방지용 인증 번호
1645
(왼쪽의 숫자를 입력해야 합니다.)