2016-07-10 3 views
1

SDL을 사용하는 작은 Vala 게임 프로젝트를 계획 중이며 SDL을 GLib 메인 루프에 올바르게 통합하는 방법을 알고 싶습니다. 마지막으로 Vala와 SDL로 작업 한 마지막 순간에 표준 SDL 이벤트 루프를 사용했지만 정직하게 말하자면,이 모듈은 멋진 Vala 또는 GLib 신호 시스템 전체를 손상시킵니다.SDL을 GLib 메인 루프에 통합

나는 an integration for Cogl을 발견했으며 SDL만으로도 똑같은 것을 찾고 있습니다.

+0

당신이하려는 일이 불분명합니다.그리기를 원하면 윈도우에 다시 그리기 콜백을 추가하면 충분합니다 (그리고 어떤 일이 발생하면 표시되는 이미지를 변경해야 함). 더 일반적인 것들을 위해 타이머와 유휴 기능이 있습니다. – keltar

답변

3

입심 소스는 세 가지 콜백 구성되어있다 :

  • 하나는 소스가 폴링하기 전에 준비가되어 있는지 확인 (그리고 poll 전화를 피하기) 소스가 여전히 폴링
  • 후 준비가되었는지
  • 하나 확인하기
  • 하나는 소스 확인하고 매우 간단하게 이벤트를 파견을 가질 수 첨부 된 콜백

를 파견합니다. 이것은 매우 기본적인

var source = new SDLSource(); 

source.add_callback ((event) => { 
    // handle event here 
    return Source.CONTINUE; 
}); 

source.attach ([email protected]()); 

:

public delegate bool SDLSourceFunc (SDL.Event event); 

public class SDLSource : Source 
{ 
    public SDL.Event event; 

    public bool prepare (out uint timeout) 
    { 
     timeout = 0; 
     return true; 
    } 

    public bool check() 
    { 
     return SDL.Event.poll (out event) > 0; 
    } 

    public bool dispatch (SourceFunc callback) 
    { 
     return ((SDLSourceFunc) callback) (event); 
    } 

    public void add_callback (SDLSourceFunc callback) 
    { 
     base.add_callback ((SourceFunc) callback); 
    } 
} 

그런 다음 Source.CONTINUE와 루프 것입니다 소스는 SDL.EventMaskSDL.peep A를 특정 이벤트를 필터링 할 수 있습니다. 단일 소스에 대해 여러 이벤트를 전달하고 관련 파일 설명자를 첨부하는 것이 더 효율적입니다. 당신은 몇 가지 비동기 코드를 사용하는 경우

, 당신은 Source 파견에서 직접 코 루틴 웨이크 업 할 수 있습니다

public async void next_event_async() 
{ 
    var source = new SDLSource(); 
    source.attach ([email protected]()); 
    source.add_callback (handle_event_async.callback); 
    yield; 
    return source.event; 
} 
1

안타깝게도 SDL이 매우 어렵게한다. 이상적으로 SDL API는 이벤트를 사용할 수있을 때마다 신호를 보낼 수있는 파일 디스크립터를 제공하여 glib 메인 루프에 추가 할 수 있지만 이것이 필요하지는 않습니다.

이상적이지 않지만, 가장 간단하고 휴대 가능한 방법은 타이머를 설치하여 정기적으로 SDL 이벤트를 확인하는 것입니다. g_timeout_add을 사용하면 주기적으로 주 루프를 깨우고 콜백에서 SDL_PollEvent를 호출 할 수 있습니다.

이것은 주어진 접근 방식이 실제로 대기 시간을 발생시킬 수 있다는 점을 제외하고는 (과 비슷합니다. 이벤트가 사용 가능하지 않은 경우 준비 기능은 0 시간 제한을 반환합니다) 따라서 항상 100 % CPU를 사용하게됩니다.

클러 터를 사용하여 Git 기록에서 계속 볼 수있는 SDL backend이 필요합니다. 기본적으로 g_timeout_add를 사용하는 대신 커스텀 소스를 생성한다는 점을 제외하면 규칙적인 간격으로 메인 루프를 깨우는 방법을 취합니다.

게임을 작성할 때 계속해서 다시 그리기를하고 SDL_GL_SwapWindow에서 프로세스를 정기적으로 차단하려는 경우에는 g_idle_add과 함께 유휴 처리기를 설치 한 다음 모든 SDL 작업을 수행하는 것이 좋습니다 콜백에. 유휴 콜백이 시작될 때 이벤트를 확인한 다음 SDL_GL_SwapWindow를 호출하면 마지막에 다시 그리기가 100 % CPU를 차지하지 않는다는 의미로 완료 될 때까지 대기합니다.

관련 문제