반응형

잘만 되던 VCPKG가 갑자기 OpenCV, VTK 등등을 빌드 할려니 pkgconf를 빌드하는 과정에서 에러가 났다.

결국 하루 동안 계속 문제점을 찾다가 해결 방법을 찾았다..

 

일단 나는 이런 오류가 떴다. 참고로 vcpkg install pkgconf:x64-windows 해서 나온 에러다.

CMake Error at scripts/cmake/vcpkg_execute_required_process.cmake:127 (message):
    Command failed: "C:/Program Files/Microsoft Visual Studio/2022/Community/Common7/IDE/CommonExtensions/Microsoft/CMake/Ninja/ninja.exe" install -v
    Working Directory: C:/dev/vcpkg/buildtrees/pkgconf/x64-windows-dbg
    Error code: 1
    See logs for more information:
      C:\dev\vcpkg\buildtrees\pkgconf\package-x64-windows-dbg-out.log
      C:\dev\vcpkg\buildtrees\pkgconf\package-x64-windows-dbg-err.log

Call Stack (most recent call first):
  installed/x64-windows/share/vcpkg-tool-meson/vcpkg_install_meson.cmake:33 (vcpkg_execute_required_process)
  ports/pkgconf/portfile.cmake:67 (vcpkg_install_meson)
  scripts/ports.cmake:192 (include)


error: building pkgconf:x64-windows failed with: BUILD_FAILED
See https://learn.microsoft.com/vcpkg/troubleshoot/build-failures?WT.mc_id=vcpkg_inproduct_cli for more information.
Elapsed time to handle pkgconf:x64-windows: 6.1 s
Please ensure you're using the latest port files with `git pull` and `vcpkg update`.
Then check for known issues at:
  https://github.com/microsoft/vcpkg/issues?q=is%3Aissue+is%3Aopen+in%3Atitle+pkgconf
You can submit a new issue at:
  https://github.com/microsoft/vcpkg/issues/new?title=[pkgconf]+Build+error+on+x64-windows&body=Copy+issue+body+from+C%3A%2Fdev%2Fvcpkg%2Finstalled%2Fvcpkg%2Fissue_body.md

 

 

에러난 부분의 문제를 보면 

Command failed: "C:/Program Files/Microsoft Visual Studio/2022/Community/Common7/IDE/CommonExtensions/Microsoft/CMake/Ninja/ninja.exe" install -v
Working Directory: C:/dev/vcpkg/buildtrees/pkgconf/x64-windows-dbg

Working Directory에서 위 커맨드를 실행 중 오류가 났다고 한다.

 

그래서 나는 이걸 저 디렉토리에서 똑같이 실행해봤다.

그러더니 이런 오류가 떴다.

Traceback (most recent call last):
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\meson.py", line 27, in <module>
    sys.exit(mesonmain.main())
             ^^^^^^^^^^^^^^^^
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\mesonmain.py", line 291, in main
    return run(sys.argv[1:], launcher)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\mesonmain.py", line 282, in run
    return CommandLineParser().run(args)
           ^^^^^^^^^^^^^^^^^^^
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\mesonmain.py", line 67, in __init__
    from . import mconf, mdist, minit, minstall, mintro, msetup, mtest, rewriter, msubprojects, munstable_coredata, mcompile, mdevenv, mformat
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\mconf.py", line 20, in <module>
    from . import mintro
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\mintro.py", line 23, in <module>
    from .ast import IntrospectionInterpreter, BUILD_TARGET_FUNCTIONS, AstConditionLevel, AstIDGenerator, AstIndentationGenerator, AstJSONPrinter
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\ast\__init__.py", line 19, in <module>
    from .interpreter import AstInterpreter
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\ast\interpreter.py", line 25, in <module>
    from ..interpreter import (
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\interpreter\__init__.py", line 33, in <module>
    from .interpreter import Interpreter, permitted_dependency_kwargs
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\interpreter\interpreter.py", line 19, in <module>
    from ..wrap import wrap, WrapMode
  File "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\mesonbuild\wrap\wrap.py", line 9, in <module>
    import urllib.request
  File "urllib\request.py", line 88, in <module>
  File "http\client.py", line 71, in <module>
  File "email\parser.py", line 12, in <module>
  File "email\feedparser.py", line 27, in <module>
  File "email\_policybase.py", line 9, in <module>
  File "email\utils.py", line 29, in <module>
  File "socket.py", line 51, in <module>

    ^
ImportError: DLL load failed while importing _socket: 지정된 모듈을 찾을 수 없습니다.
[0/1] "C:\dev\vcpkg\downloads\tools\python\python-3.11.8-x64\python.exe" "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\meson.py" "install" "--no-rebuild"
FAILED: meson-internal__install
"C:\dev\vcpkg\downloads\tools\python\python-3.11.8-x64\python.exe" "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\meson.py" "install" "--no-rebuild"
ninja: build stopped: subcommand failed.

이 오류를 보면 vcpkg에서 다운로드 받는 python-3.11.8에서 meson.py를 실행해서 설치를 하는데 _socket과 관련된 DLL 파일을 찾을 수 없어 발생한 문제이다.

 

일단 뭐 파이썬 홈페이지 가서 3.11.8를 받아서 설치하고 dll 파일을 가져오면 아마도 될 것 같긴 하지만..

혹시 실패할 수도 있고.. 제일 중요한건 그거까지 하기가 귀찮았다.. 내가 기본으로 설치한게 3.12.6이라서.. 저걸 깔면 나중에 또 지워야 하고 해서.. 귀찮았다.

 

그래서 혹시 몰라서 내가 기본으로 깔아둔 3.12.6 버전의 파이썬으로 빌드가 될까 해서 해봤더니..

python "C:\dev\vcpkg\downloads\tools\meson-1.5.2-dd4692\meson.py" "install" "--no-rebuild"
Installing pkgconf-5.dll to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\bin
Installing pkgconf.lib to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\lib
Installing pkgconf-5.pdb to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\bin
Installing pkgconf.exe to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\bin
Installing pkgconf.pdb to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\bin
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\libpkgconf\libpkgconf.h to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\../include\pkgconf/libpkgconf
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\libpkgconf\stdinc.h to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\../include\pkgconf/libpkgconf
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\libpkgconf\iter.h to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\../include\pkgconf/libpkgconf
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\libpkgconf\bsdstubs.h to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\../include\pkgconf/libpkgconf
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\libpkgconf\libpkgconf-api.h to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\../include\pkgconf/libpkgconf
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\man/pkgconf.1 to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\share/man\man1
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\man/pkg.m4.7 to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\share/man\man7
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\man/pc.5 to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\share/man\man5
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\man/pkgconf-personality.5 to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\share/man\man5
Installing C:\dev\vcpkg\buildtrees\pkgconf\x64-windows-dbg\meson-private\libpkgconf.pc to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\lib\pkgconfig
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\pkg.m4 to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\share/aclocal
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\AUTHORS to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\share/doc/pkgconf
Installing C:\dev\vcpkg\buildtrees\pkgconf\src\conf-2.3.0-07e4a066bf.clean\README.md to C:/dev/vcpkg/packages/pkgconf_x64-windows/debug\share/doc/pkgconf

빌드가 엄청 잘된다;;

 

일단 이 문제는 VCPKG에서 기본으로 설치하는 Python 3.11.8 버전의 어떤 라이브러리의 DLL 모듈이 없어서 에러났다니깐.. 그냥 VCPKG에서 빌드할 때 Python을 다른걸로 바꾸면 되는게 아닌가 하고 생각을 했다.

 

그래서 VCPKG에서 어느쪽에서 파이썬이 있는지 찾고 다운로드 하는지 찾아봤더니.. 한 파일이 나왔다.

C:\dev\vcpkg\scripts\cmake\vcpkg_find_acquire_program(PYTHON3).cmake

if(CMAKE_HOST_WIN32)
    set(program_name python)
    set(program_version 3.11.8)
    if(DEFINED ENV{PROCESSOR_ARCHITEW6432})
        set(build_arch $ENV{PROCESSOR_ARCHITEW6432})
    else()
        set(build_arch $ENV{PROCESSOR_ARCHITECTURE})
    endif()
    if(build_arch MATCHES "^(ARM|arm)64$")
        set(tool_subdirectory "python-${program_version}-arm64")
        set(download_urls "https://www.python.org/ftp/python/${program_version}/python-${program_version}-embed-arm64.zip")
        set(download_filename "python-${program_version}-embed-arm64.zip")
        set(download_sha512 42b820e34c4a77fe928e0af395292d804dcbf7e1132cf353ce6ce23435a687ec580f03ccbf3cd94d98c9dc5ac951f8ca64dbd65cded7ef1d675a39d63f8ace8d)
    elseif(build_arch MATCHES "(amd|AMD)64")
        set(tool_subdirectory "python-${program_version}-x64")
        set(download_urls "https://www.python.org/ftp/python/${program_version}/python-${program_version}-embed-amd64.zip")
        set(download_filename "python-${program_version}-embed-amd64.zip")
        set(download_sha512 da5f01e94d3505eebdfd4d2e70d9cf494925199024479cc29ef144567906b2e8ad55a855b199a755318f5fb9a260f21b987a5fc85f31acf631af4b677921251d)
    else()
        set(tool_subdirectory "python-${program_version}-x86")
        set(download_urls "https://www.python.org/ftp/python/${program_version}/python-${program_version}-embed-win32.zip")
        set(download_filename "python-${program_version}-embed-win32.zip")
        set(download_sha512 c88ef02f0860000dbc59361cfe051e3e8dc7d208ed39bb5bc20a3e8b8711b578926e281a11941787ea61b2ef05b945ab3133322dcb85b916f79ac4ada57f6309)
    endif()

    set(paths_to_search "${DOWNLOADS}/tools/python/${tool_subdirectory}")
    vcpkg_list(SET post_install_command "${CMAKE_COMMAND}" -E rm python311._pth)
else()
    set(program_name python3)
    set(brew_package_name "python")
    set(apt_package_name "python3")
endif()

이 파일이다.

 

여기를 보면 26번 줄에 set(paths_to_search "${DOWNLOADS}/tools/python/${tool_subdirectory}") 이런 코드가 있는데

이게 파이썬의 폴더를 검색하는 것 같다.

 

그래서 이걸 set(paths_to_search "C:/Users/cheongpark/AppData/Local/Programs/Python/Python312") 이렇게 바꿨다.

python.exe 파일이 있는 폴더까지를 지정해야하는 것 같다.

if(CMAKE_HOST_WIN32)
    set(program_name python)
    set(program_version 3.11.8)
    if(DEFINED ENV{PROCESSOR_ARCHITEW6432})
        set(build_arch $ENV{PROCESSOR_ARCHITEW6432})
    else()
        set(build_arch $ENV{PROCESSOR_ARCHITECTURE})
    endif()
    if(build_arch MATCHES "^(ARM|arm)64$")
        set(tool_subdirectory "python-${program_version}-arm64")
        set(download_urls "https://www.python.org/ftp/python/${program_version}/python-${program_version}-embed-arm64.zip")
        set(download_filename "python-${program_version}-embed-arm64.zip")
        set(download_sha512 42b820e34c4a77fe928e0af395292d804dcbf7e1132cf353ce6ce23435a687ec580f03ccbf3cd94d98c9dc5ac951f8ca64dbd65cded7ef1d675a39d63f8ace8d)
    elseif(build_arch MATCHES "(amd|AMD)64")
        set(tool_subdirectory "python-${program_version}-x64")
        set(download_urls "https://www.python.org/ftp/python/${program_version}/python-${program_version}-embed-amd64.zip")
        set(download_filename "python-${program_version}-embed-amd64.zip")
        set(download_sha512 da5f01e94d3505eebdfd4d2e70d9cf494925199024479cc29ef144567906b2e8ad55a855b199a755318f5fb9a260f21b987a5fc85f31acf631af4b677921251d)
    else()
        set(tool_subdirectory "python-${program_version}-x86")
        set(download_urls "https://www.python.org/ftp/python/${program_version}/python-${program_version}-embed-win32.zip")
        set(download_filename "python-${program_version}-embed-win32.zip")
        set(download_sha512 c88ef02f0860000dbc59361cfe051e3e8dc7d208ed39bb5bc20a3e8b8711b578926e281a11941787ea61b2ef05b945ab3133322dcb85b916f79ac4ada57f6309)
    endif()

    set(paths_to_search "C:/Users/cheongpark/AppData/Local/Programs/Python/Python312")
    vcpkg_list(SET post_install_command "${CMAKE_COMMAND}" -E rm python311._pth)
else()
    set(program_name python3)
    set(brew_package_name "python")
    set(apt_package_name "python3")
endif()

 

 

이렇게 한 후에 다시 vcpkg install pkgconf:x64-windows를 해보면?!!

Computing installation plan...
The following packages will be built and installed:
    pkgconf:x64-windows@2.3.0
Detecting compiler hash for triplet x64-windows...
Compiler found: C:/Program Files/Microsoft Visual Studio/2022/Community/VC/Tools/MSVC/14.41.34120/bin/Hostx64/x64/cl.exe
Restored 0 package(s) from C:\Users\pkdpm\AppData\Local\vcpkg\archives in 91.2 us. Use --debug to see more details.
Installing 1/1 pkgconf:x64-windows@2.3.0...
Building pkgconf:x64-windows@2.3.0...
-- Found Python version '3.12.6 at C:/Users/cheongpark/AppData/Local/Programs/Python/Python312/python.exe'
-- Using meson: C:/dev/vcpkg/downloads/tools/meson-1.5.2-dd4692/meson.py
-- Using cached pkgconf-pkgconf-pkgconf-2.3.0.tar.gz.
-- Cleaning sources at C:/dev/vcpkg/buildtrees/pkgconf/src/conf-2.3.0-07e4a066bf.clean. Use --editable to skip cleaning for the packages you specify.
-- Extracting source C:/dev/vcpkg/downloads/pkgconf-pkgconf-pkgconf-2.3.0.tar.gz
-- Using source at C:/dev/vcpkg/buildtrees/pkgconf/src/conf-2.3.0-07e4a066bf.clean
-- Found external ninja('1.11.0').
-- Configuring x64-windows-dbg
-- Getting CMake variables for x64-windows
-- Configuring x64-windows-dbg done
-- Configuring x64-windows-rel
-- Configuring x64-windows-rel done
-- Package x64-windows-dbg
-- Package x64-windows-rel
-- Fixing pkgconfig file: C:/dev/vcpkg/packages/pkgconf_x64-windows/lib/pkgconfig/libpkgconf.pc
-- Fixing pkgconfig file: C:/dev/vcpkg/packages/pkgconf_x64-windows/debug/lib/pkgconfig/libpkgconf.pc
-- Installing: C:/dev/vcpkg/packages/pkgconf_x64-windows/share/pkgconf/copyright
-- Performing post-build validation
Stored binaries in 1 destinations in 125 ms.
Elapsed time to handle pkgconf:x64-windows: 16 s
pkgconf:x64-windows package ABI: 2aa878a6cc6bcbd98fbe97e87caf0270763d6f45acecb8cd2d758d0e269baeab
Total install time: 16 s
pkgconf provides pkg-config modules:

  # a library for accessing and manipulating development framework configuration
  libpkgconf

-- Found Python version '3.12.6 at C:/Users/pkdpm/AppData/Local/Programs/Python/Python312/python.exe' 

이런식으로 바뀌면서 정상적으로 빌드가 된다!!!

 

드디어 잘 수 있다..

반응형
반응형

이번엔 21권이다!

 

첫번째 사진은 두 팔 달린 로봇으로 박스 포장하는 것 같은 것에 대한 내용인 것 같고..

두번째 사진은 현재 내 전공과도 관련되어있는 내용인 것 같다..!

두번째 사진에 대한 내용은

https://youtu.be/qsTFlmdO05M?si=N9WGNDJGDhct-4sr

이 유튜브에 잘 나와있는 것 같은데.. 현재도 잘 사용되는 분류 모델에 대해서 말하고 있는 것 같다.. 더 놀라운건 사진 오른쪽 아래에도 있고 영상 뒤에도 있는건데.. 노이즈를 제거하는 기술이다.. 

어떤 원리인지는 모르겠지만 여러가지 센서에는 노이즈 들이 있는데 이것들을 제거할 수 있는 기술에 대한 내용인 것 같다.. 도데체 어떻게 제거한거지라는 생각 밖에 안드는 정도로 놀랍다..

 

아무튼 이제 조립이다! 왜인지 모르겠지만 이번에도 부품을 찍어놓은 사진은 없다.. (뭐 어차피 모터 하나라서 상관은 없지만..)

아무튼 이번 것도 모터에 ID 번호를 저장하면 끝!

 

아무튼 21권도 끝이다!

반응형
반응형

드디어.. 20권이다!! (32권까지 만들고 쓰고 있는데 언제쯤 다 쓸수 있을까..)

 

첫번째 사진은 수동 운행, 자율 운행이 가능한 탈 것에 대한 얘기인 것 같다.

두번째 사진은 이전 권에서 있던 오타마톤 아저씨에 대한 인터뷰 얘기인 것 같다.

세번째 사진은 현재도 사용되고 있는 보컬로이드에 대한 내용인 것 같다. 예전에 음성 합성이 신기해서 보컬로이드에 대한 것도 많이 찾아봤었는데.. 도데체 일본은 어떻게 그 옛날 부터 보컬로이드 같은 신기한 기술을 성능이 별로 좋지 못한 컴퓨터에서도 잘 돌아가도록 만들었는지가 굉장히 궁금하다.. 일본은 진심으로 뭔가 한가지 목표를 가지면 그것에 대해서 어떻게든 만들려는 사람들 밖에 없는 것 같은 느낌이 든다.. 예전에 유튜브 영상을 보다가 피아노를 연주하면 그 피아노 노래에 맞는 보컬로이드를 자동으로 부르는 보컬로이드를 만들었던데.. 속도를 느리게 하든 빠르게 하든 편곡을 하든 다 인식하는게 굉장히 신기했었다.. 도데체 어떻게 그걸 다 인식하는거고 그걸 어떻게 만든걸까..

뭐 보컬로이드는 현재의 TTS 보다는 성능이 떨어지지만 어떻게 그 초창기 부터 노래를 하는 보컬로이드를 만들 수 있었는지..

아 그리고 지금 만들고 있는 Robi 로봇의 SD 카드에 있던 내용을 누가 온라인에 올렸어서 확인해봤었는데.. Robi에는 음성 합성으로 음성을 만들어내는건 아닌 것 같고 미리 녹음된 것을 재생하는 방식인 것 같다. 뭐.. Robi의 성능을 생각하면 당연한거겠지만..

 

아무튼 조립 시작! 그런데.. 한가지 문제는 부품을 찍었던 사진이 없다.. 조립 사진은 있는데..

어깨를 움직일 수 있는 철 부품을 끼우고 선을 빼고 넣고 다른 부품으로 고정하면 끝!

 

아무튼 이번 편도 끝이다!

반응형
반응형

이번엔 19권!

첫번째 사진은 10년 이상의 역사를 가진 로봇에 대한 얘기인데.. 그러면 지금은 20년 이상의 역사를 가졌다는 얘기인데.. 현재의 로봇 청소기를 생각하면 20년 이상이나 지났는데 왜 아직도 로봇 청소기는 장애물을 잘 회피하지 못할까 라는 생각이 든다.. 뭐 인공지능이 최근에야 굉장히 활발해져서 이제야 그나마 회피를 잘하게 되기는 했는데.. 왜 케이블 같은건 완벽하게 회피를 못할까라는 생각이 들었다. 

그리고 한가지 생각난게 예전에 2022년도에 어떤 모르는 할아버지와 내 친구들과 캠핑장을 갔다 왔었는데, 나중에는 그 할아버지의 가족분들과도 캠핑장을 갔었다. 그 때 할아버지의 딸이신 분이 예전에 다른 사람들에게 받은 것들을 자신도 베풀어야 한다면서 뭔가를 나와 내 친구들에게 필요하면 가져가라고 주셨었는데, 그 때 나는 로봇 청소기를 선택한적이 있었다. 아마 아이클레보 아르떼 라는 유진 로봇의 청소기 일텐데, 2022년도에 받았었지만 굉장히 오래된 로봇 청소기이다.. (그 때 지하철을 타고 맥도날드에 들르면서 가지고 다녔던 기억이..) 아무튼 로봇 청소기를 가져왔는데 리모컨이 없어서 주문하고 이랬었는데.. 동작시켜봤을 때 굉장히 신기했다.. 현재의 로봇 청소기들 보다 특이한 위치인 위쪽을 바라보는 카메라와 충돌 센서 같은 것들 만으로도 현재도 뒤쳐지지 않는 청소능력을 갖춘것이.. 굉장히 신기했다. 도데체 어떻게 그 센서 만으로 정확하게 자기 위치를 기억하고 움직이는건지.. 가장 신기한건 어떤 방을 다 치우고 다시 돌아갈 때 정확하게 들어왔던 문으로 빠르게 돌아가는거하고 자기 집을 자동으로 찾아가는게 제일 신기했다.. 

그리고 유진 로봇 하니 생각난 것 중에 하나가.. 실버로봇, PaPeRo 같이 생긴 아이로비 라는 로봇인데.. 굉장히 귀엽다!

 

두번째 사진은 오타마톤을 제작한 분과의 인터뷰 얘기 같은데 내용은 잘 모르겠지만, 오타마톤에 대한 기억이 생각났다.

예전에 어릴 때 형아가 일본에 가니깐 선물을 사올 수 있다고 했어서 그 때 내가 오타마톤을 사다달라고 했었던 기억이 있다. 지금은 아트박스에 가도 팔지만 그 때는 인터넷이나 직구로 밖에 구할 수 없던.. 그래서 사왔을 때 굉장히 좋았었는데 처음에 잘 해보다가 결국 연주가 너무 어려워서 포기하고 방치하다가 현재는 완전히 고장나버린.. 그런 기억이 있다..

 

아무튼 이번 부품은 이거다!

 

그렇기 때문에 ID를 저장하는 것이 끝!

 

아무튼 끝

반응형
반응형

이번엔 18권!

 

7월 19일에 만들었던건데.. 연구 때문에 바쁘다보니 방학이 끝나고 기숙사에 있는 지금에야 쓰고 있다..

 

첫번째 사진에 있는 로봇은 뭔가 굉장히 인간과 비슷하게 만들어진 것 같은데.. 언젠가 발전하면 미래에는 저런 뼈대로 된 로봇이 나올 수도 있을 것 같다는 생각이 든다.. (플라스틱 메모리즈 애니가 생각나는..)

두번째 사진은 로봇의 후각에 대한 얘기인 것 같다. 로봇이 어떻게 냄새를 맡고 분류해내는지에 대한 내용인 것 같은데 이 책이 2013년에 나온 책일텐데.. 그 전부터 저런 연구가 있었다는게 굉장히 신기하다.. 과연 미래의 로봇은 어떻게 될까..

 

아무튼 이번 부품은 이거다!

 

그냥 캡을 씌우고 선을 빼서 파츠를 장착해주면 끝!

 

반응형
반응형

내가 대학교에 입학한 후 1학년인데 학생 연구원을 해볼 생각이 없는지 물어보셨었다.

나는 좋다고 한 후 들어갔는데

교수님이 연구를 위해 Tobii Eye Tracker를 빌려주셔서 그 기회에 이 프로젝트를 해보았다.


눈 제어해보기 전에 이것을 만들기 이전에 어떤 과정이 있었는지 말하면..

 

일단 내가 받은 아이트래커는 

이거인데 Tobii Eye Tracker 5이다. 받고난 후 어떻게 할지 검색해보다가 알게 되었다..

내가 받은건 게임용이고 연구용이 아니기에 연구용 SDK가 없다는 것을..

 

아무리 검색해도 이 기기에서는 아이트래킹 정보를 얻을 수가 없었다.

https://developer.tobii.com/product-integration/stream-engine/

 

Stream Engine - Tobii Developer Zone

The Stream Engine SDK is a low-level SDK intended for advanced users wanting to have tight control over the system resources used by Stream Engine and least amount of signal latency. To get started with the StreamEngine SDK, head over to the getting starte

developer.tobii.com

그러다가 이 것이 나와서 찾아봤는데.. 이건 일단 되는 것이다!

게임용으로 지원하는 SDK이고 이 SDK를 사용해서 아이트래킹이 지원되는 게임을 만드는 것 같다.

 

그래서 이걸 쓰기위해 보니 메일을 보내서 요청하라고 적혀있다.. 그래서 보냈더니..

한국어로 답변이 왔는데.. 아이트래커에 해킹을 시도하거나 다르게 이용을 하는 경우가 있어서 SDK를 못 준다는 말만 왔었다.. 개인적으로 사용할 것이라고 얘기해도 불가능이라고 했다.

 

그래서 그냥 포기할까 하고 한가지 생각이 들었다. 이 회사는 유명하니깐 누군가가 Github에 올려놓지 않았을까 하고..

그래서 찾아보니 진짜로 있었다. 32비트, 64비트 모두 Github에 아이트래커 프로젝트를 올리면서 같이 올려진 것들이 있다.

그래서 나는 이걸 다운받아서 시도했더니 아이트래커에 접근이 됬었던 것!

 

(근데 한가지 슬픈건.. 이 SDK가 C++과 C#만 가능한데.. 연구원에서.. 교수님과 나만 C++이 가능했던 것.. 그래서 이 연구와 관련된 프로그램을 제작하는건 모두 내가 맡아서 했었다.. 파이썬으로 실행할 수 있는 것이 github에 있던데.. 더 별로여 보여서 그냥 C++로 하기로 했다..)

 

https://developer.tobii.com/product-integration/stream-engine/tutorial_cplusplus/

 

Stream Engine Tutorial - C++ - Tobii Developer Zone

This policy applies to solutions that store or transfer Tobii eye tracking data, presence or position data, regardless of the purpose for the storing or transferring. End-users care about their data integrity and privacy. Therefore, as a vendor you must ga

developer.tobii.com

아무튼 예제 코드는 여기에 있다. C++ 프로젝트로 사용하는 방법도 나와있고..

뭐 일단 이제 VRChat과 관련된 얘기를 해보겠다!

일단 VRChat에는 OSC 라는 기능이 있다.

https://docs.vrchat.com/docs/osc-overview

 

OSC Overview

Intro to OSC OSC is a way to get different devices and applications to talk to each other. It's a favorite method of creative coders and people making weird interactive things because it's fast, networked, and very open-ended. What does this have to do wit

docs.vrchat.com

여기에 자세히 나와있는데 OSC를 이용하면 VRChat에서 아바타나 VRChat 기능과 소통하면서 여러가지 기능들을 제어할 수가 있는 것 같다.

예전에는 이걸로 번역기도 만들어보긴 했는데.. 굉장히 간단하게 할수가 있었다.

 

아무튼 저 글에서 보면 

https://docs.vrchat.com/docs/osc-eye-tracking

 

OSC Eye Tracking

VRChat now offers support for receiving eye tracking data (eyelook and eyelid) via OSC. Please note: This is an advanced feature! It is NOT plug-and-play. You must create your own program to transmit this data to VRChat using OSC. Hardware manufacturers ma

docs.vrchat.com

 

 

아이트래킹을 할 수 있는 링크가 설명이 되어있는데 대충 이거다.

/tracking/eye/EyesClosedAmount

/tracking/eye/CenterPitchYaw
/tracking/eye/CenterPitchYawDist
/tracking/eye/CenterVec
/tracking/eye/CenterVecFull
/tracking/eye/LeftRightPitchYaw
/tracking/eye/LeftRightVec

(참고로 여기로 9000 포트와 함께 데이터를 보내면 OSC가 작동한다.)

 

일단 Stream Engine을 살펴보니 잘은 모르겠지만 내가 보고 있는 시선의 위치만 가져올 수 있는 것 같다. 뭐.. 게임 용이라 그런 것 같은데.. 아니면 내가 제대로 안 찾아본 것일 수도 있고..

 

아무튼 내가 보고 있는 위치만 가져올 수 있으니깐.. 사용할 수 있는 OSC는 "/tracking/eye/CenterPitchYaw" 이거다. 이거는 문서에 잘 설명 되어있다.

그리고 눈을 감았는지에 대한건 "/tracking/eye/EyesClosedAmount" 이걸 사용하면 될 것 같다.

 

아무튼 이걸 알았으니 이제 예제 코드를 실행해볼껀데, 그냥 실행하면 이런 오류가 난다. 아마도 내꺼가 Github에서 가져와서 버전이 낮은 것 때문에 그런 것 같은데..

// Connect to the first tracker found
tobii_device_t* device = NULL;
result = tobii_device_create(api, url, TOBII_FIELD_OF_USE_STORE_OR_TRANSFER_FALSE, &device);
assert(result == TOBII_ERROR_NO_ERROR);

여기 코드에서 TOBII_FIELD_OF_USE_STORE_OR_TRANSFER_FALSE 이게 오류가 난다.

 

그냥 해결 방법은 그냥 저거 빼고 

사진에 나온거 2개 중에 아무거나 넣으면 된다.

그리고

이런 오류 나면.. 뭐 다르게 해결하는 방법이 있지만 빠르게 테스트 하기 위해 맨 상단에 이걸 넣는다.

#define _CRT_SECURE_NO_WARNINGS

아무튼 이러면 오류가 사라진다.

 

이제 실행해보면 Tobii Eye Tracker이 정상적으로 연결 되어있는 경우 작동하는데 해보면 내가 보고 있는 시선이 x, y로 나올꺼다. 그런데 내가 눈을 감거나 감지할 수 없는 영역을 쳐다보면 아무것도 출력이 안되는데.. 이걸 알 수 있다는 것은 눈을 깜박이는 것을 알 수 있다는 것이다! 확실히 알기 위해 코드를 수정했다!

void gaze_point_callback(tobii_gaze_point_t const* gaze_point, void* /* user_data */)
{
    // Check that the data is valid before using it
    if (gaze_point->validity == TOBII_VALIDITY_VALID)
        printf("Gaze point: %f, %f\n",
            gaze_point->position_xy[0],
            gaze_point->position_xy[1]);
    else // 추가
        printf("Gaze Error\n"); // 추가
}

// 추가 라고 되어있는 것이 내가 추가한건데 그냥 인식 안되면 출력하라는거다..

이렇게 하면 정상적으로 눈을 깜으면 Gaze Error이 표시되고 감지 영역에서 눈을 움직이면 쳐다보는 곳이 잘 출력된다..!

 

그리고 한가지 알아둘 것이 있는데 출력되고 있는 것을 보면

Gaze point: 0.695525, 0.411705
Gaze point: 0.634280, 0.405759
Gaze point: 0.541244, 0.393794
Gaze point: 0.465725, 0.383487
Gaze point: 0.423483, 0.384978
Gaze point: 0.402698, 0.381798
Gaze point: 0.368750, 0.379669
Gaze point: 1.126799, 0.609565
Gaze point: 1.110942, 0.619803
Gaze point: 1.121417, 0.617664
Gaze point: 1.146164, 0.605248
Gaze point: 1.153657, 0.606785
Gaze point: 1.154399, 0.599591
Gaze point: 1.155324, 0.597877

 

 

이런게 있는데.. 이 숫자에 대한 것이다.

이 숫자는 그냥 x와 y의 시선 값인데 0부터 1 사이 값들은 모니터 안에 있는 것이고

1 이상들은 모니터 밖을 쳐다보고 있다는 것이다.

또한 모니터가 1920 * 1080 이면 각각에 x와 y 값을 곱해보면 내가 보고 있던 픽셀을 알수도 있다는 것이다.

 

이번에는 VRChat OSC에 정보를 보내는 방법에 대한 얘기인데

Python이라면 그냥 python-osc 이거 사용해서 로컬 9000 포트로 보내면 끝난다.

근데 C++이기에 OSC 라이브러리를 사용해야한다.

 

일단 난 그냥 간단하게 이걸 사용했다.

https://github.com/CINPLA/oscpack

 

GitHub - CINPLA/oscpack: Automatically exported from code.google.com/p/oscpack

Automatically exported from code.google.com/p/oscpack - CINPLA/oscpack

github.com

 

아무튼 바로 코드!

#include "tobii/tobii.h"
#include "tobii/tobii_streams.h"
#include <iostream>
#include <stdio.h>
#include <assert.h>
#include <string.h>
#include <conio.h>
#include <Windows.h>
#include <typeinfo>
#include "osc/OscOutboundPacketStream.h"
#include "ip/UdpSocket.h"
#include <opencv2/opencv.hpp>

#pragma comment(lib, "Ws2_32.lib")

#define CanvasW 1920 / 4
#define CanvasH 1080 / 4

const char* ip = "127.0.0.1";
const int port = 9000;

float last_sent_value = -1.0f; // 이전에 보낸 값을 저장할 변수
bool test_mode = true; // 테스트 모드 설정

cv::Point2f current_point(0.0f, 0.0f); // 현재 점의 위치
cv::Point2f target_point(0.0f, 0.0f); // 목표 점의 위치

const float gaze_x_min = -25.0f;
const float gaze_x_max = 25.0f;
const float gaze_y_min = -15.0f;
const float gaze_y_max = 20.0f;

cv::Mat canvas(CanvasH, CanvasW, CV_8UC3, cv::Scalar(255, 255, 255)); // canvas 선언

void send_message(UdpTransmitSocket& transmitSocket, const char* address, float value) {
    if (value == last_sent_value) return; // 이전에 보낸 값과 같다면 보내지 않음

    char buffer[1024];
    osc::OutboundPacketStream p(buffer, 1024);

    p << osc::BeginMessage(address) << value << osc::EndMessage;
    transmitSocket.Send(p.Data(), p.Size());

    last_sent_value = value; // 보낸 값을 저장
}

void send_gaze_message(UdpTransmitSocket& transmitSocket, const char* address, float x, float y) {
    char buffer[1024];
    osc::OutboundPacketStream p(buffer, 1024);

    p << osc::BeginMessage(address) << x << y << osc::EndMessage;
    transmitSocket.Send(p.Data(), p.Size());
}

void gaze_point_callback(tobii_gaze_point_t const* gaze_point, void* user_data)
{
    UdpTransmitSocket* transmitSocket = static_cast<UdpTransmitSocket*>(user_data);
    if (gaze_point->validity == TOBII_VALIDITY_VALID) {
        printf("Gaze point: %f, %f\n",
            gaze_point->position_xy[0],
            gaze_point->position_xy[1]);

        float x = gaze_point->position_xy[0] * (gaze_x_max - gaze_x_min) + gaze_x_min;
        float y = gaze_point->position_xy[1] * (gaze_y_max - gaze_y_min) + gaze_y_min;

        send_gaze_message(*transmitSocket, "/tracking/eye/CenterPitchYaw", y, x);

        send_message(*transmitSocket, "/tracking/eye/EyesClosedAmount", 0.0f);

        if (test_mode) {
            target_point = cv::Point2f(gaze_point->position_xy[0] * CanvasW, gaze_point->position_xy[1] * CanvasH);
            current_point = target_point;
            cv::circle(canvas, current_point, 3, cv::Scalar(255, 0, 0), -1); // 파란색으로 변경
        }
    }
    else {
        std::cout << "Invalid" << std::endl;
        send_message(*transmitSocket, "/tracking/eye/EyesClosedAmount", 1.0f);

        if (test_mode) {
            current_point = target_point;
            cv::circle(canvas, current_point, 3, cv::Scalar(0, 0, 255), -1); // 빨간색으로 변경
        }
    }
}

void url_receiver(char const* url, void* user_data)
{
    char* buffer = (char*)user_data;
    if (*buffer != '\0') return; // only keep first value

    if (strlen(url) < 256)
        strcpy_s(buffer, 256, url); // strcpy_s로 변경
}

int main()
{
    // Create API
    tobii_api_t* api = NULL;
    tobii_error_t result = tobii_api_create(&api, NULL, NULL);
    assert(result == TOBII_ERROR_NO_ERROR);

    // Enumerate devices to find connected eye trackers, keep the first
    char url[256] = { 0 };
    result = tobii_enumerate_local_device_urls(api, url_receiver, url);
    assert(result == TOBII_ERROR_NO_ERROR);
    if (*url == '\0')
    {
        printf("Error: No device found\n");
        //return 1;
    }

    // Connect to the first tracker found
    tobii_device_t* device = NULL;
    result = tobii_device_create(api, url, TOBII_FIELD_OF_USE_ANALYTICAL, &device);
    std::cout << typeid(result).name() << std::endl;
    assert(result == TOBII_ERROR_NO_ERROR);

    // Subscribe to gaze data
    UdpTransmitSocket transmitSocket(IpEndpointName(ip, port));
    result = tobii_gaze_point_subscribe(device, gaze_point_callback, &transmitSocket);
    assert(result == TOBII_ERROR_NO_ERROR);

    // Initialize socket and server address

    while (true) {
        // Optionally block this thread until data is available. Especially useful if running in a separate thread.
        result = tobii_wait_for_callbacks(1, &device);
        assert(result == TOBII_ERROR_NO_ERROR || result == TOBII_ERROR_TIMED_OUT);

        // Process callbacks on this thread if data is available
        result = tobii_device_process_callbacks(device);
        assert(result == TOBII_ERROR_NO_ERROR);

        if (test_mode) {
            cv::imshow("Gaze Point", canvas);
            cv::waitKey(1);
            canvas.setTo(cv::Scalar(255, 255, 255));
        }

        if (_kbhit()) {
            int ch = _getch();
            if (ch == 27) // ESC Key
                break;
        }
    }

    // Cleanup
    result = tobii_gaze_point_unsubscribe(device);
    assert(result == TOBII_ERROR_NO_ERROR);
    result = tobii_device_destroy(device);
    assert(result == TOBII_ERROR_NO_ERROR);
    result = tobii_api_destroy(api);
    assert(result == TOBII_ERROR_NO_ERROR);
    return 0;
}

 

일단 이건 내가 그냥 간단하게 테스트만 해볼려고 만든 코드이다.

그래서 코드가 더러운 것도 있고 굳이 필요 없는 기능이 있기도 하다.

뭐 그래도 대충 이 코드를 실행하면 정상적으로 눈 제어가 가능한 아바타에서는 작동한다!!

 

그리고 코드에 보면 캔버스 설정한게 있는데 그냥 그건 OpenCV로 어디를 보고 있는지 표시하기 위해 놔둔 것이다. test_mode 끄면 나오지 않는다.

 

const float gaze_x_min = -25.0f;
const float gaze_x_max = 25.0f;
const float gaze_y_min = -15.0f;
const float gaze_y_max = 20.0f;

그리고 이런 코드가 있는데.. 이 코드는 VRChat OSC로 데이터를 보낼 때 데이터 범위이다.

각 아바타 마다 데이터의 범위가 정해져있는 것 같다. 일단 내가 사용하는 아바타는 일일이 값을 보내서 테스트 해본 결과 저정도 인 것 같다.

 

아무튼 이렇게 하면 눈 제어와 눈 깜박이는 것을 모두 아이트래커로 가능하다! 심지어 놀라운건 나는 아이트래킹은 VR 유저만 가능한 줄 알았는데 데스크탑에서도 가능하다는 것..

이게 테스트 영상!

 

아무튼 끝!

반응형
반응형

이번엔 17권이다!

 

첫번째 사진 로봇은 나도 처음보는거다.. SAUT 로봇이라는 것 같은데.. 잘 모르겠다!

두번째 사진도 잘은 모르겠다.

 

아무튼 조립 시작!

이번 부품도 역시.. 변색.. 

이걸 보다 보니 생각난게 다른 거와 비교했을 때 흰색 부품만 있거나 흰색 부품들은 저렇게 변색이 되지 않았는데 근처에 검은색 부품이 있거나 검은색 부품들만 색이 저렇게 변하는걸 보면.. 검은색 부품이 있어서 저래 되나보다..

 

이전 조립된 모터와 새로운 부품을 조립해준 후 

 

이렇게 끼워서 고정하면 끝!

 

이렇게 17권도 끝!

반응형
반응형

이번엔 16권!

 

첫번째 사진은 PR2에 대한 로봇을 말하는 것 같은데, 이 로봇은 처음 본다.. ROS로 작동하고 연구 이런걸로 사용되기 위해 만들어졌다는 것 같은데.. 굉장히 신기하다.

예전에 ROS를 검색했던적이 있던 것 같은데.. 어디 때문에 검색해보았는진 기억 안나지만 아마도 휴머노이드 로봇을 제어하기 위한거거나 대회 로봇 때문에 찾아봤던 것 같다. 그냥 찾아보기만 하고 써보진 않았는데 언젠가는 써보고 싶기는 하다. 사용법을 몰라서 안쓸뿐..

 

두번째 사진은 걷는 방법에 대한 이야기 같은데.. 나는 걷는 방법에도 이름이 정해져 있을 꺼라곤 생각하지 못했다.

여기에선 SHIN-Walk라는 방법을 쓰는 것 같은데 이 걷는 방법은 나도 자세히는 모르겠지만 찾아보다가 이곳에 누군가가 적어놓았다.

https://raionnoie.blogspot.com/2013/03/shin-walk.html

 

SHIN-WALKの仕組みをわかりやすく解説してみた

ガジェット系ブログ。 現在はデアゴスティーニのロボット「ロビ」の記事が中心。

raionnoie.blogspot.com

뭔가 이 분도 나와 비슷하게 ROBI에 대해 정리하시는 분 같은데.. 나중에도 좀 봐야할 것 같다.

저분 글을 보다가 한가지 발견한게.. 눈의 필름은 마지막에 떼야하는거라고 나와있는데.. 음.. 나중에 테이프로라도 붙여야겠다..

나중에 한번 제대로 저 걷는 방법에 대해 찾아보고 내가 가지고 있는 다른 휴머노이드 로봇에도 적용시켜봐야 할 것 같다.

 

아무튼 조립!

사실 조립할껀 없다..

부품이 이거 한개라서..

 

그냥 모터에 케이블 끼우고

 

모터 ID를 써주면 끝

 

16권도 끝이 났다!

반응형

+ Recent posts