본문 바로가기
Android

아고라 플랫폼을 이용한 안드로이드 라이브스트리밍(RTSP) - 4

by 일용직 코딩노동자 2022. 5. 12.
728x90
반응형

이전 게시글에서 채팅관련 클래스 셋팅까지 끝냈습니다.

 

이제 영상처리부분을 보도록 하겠습니다.

 

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout 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"
    tools:context=".Activity.RoleActivity">

    <Button
        android:id="@+id/broadcaster"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="100dp"
        android:text="방송인"
        app:layout_constraintEnd_toStartOf="@+id/audience"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent"></Button>

    <Button
        android:id="@+id/audience"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginStart="117dp"
        android:layout_marginTop="100dp"
        android:text="시청자"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toEndOf="@+id/broadcaster"
        app:layout_constraintTop_toTopOf="parent"></Button>

</androidx.constraintlayout.widget.ConstraintLayout>

입장시 방송하는 BJ로 접속할것인지 시청자로 접속할것인지 구분해주는 화면을 만들어줍니다.

 

public class RoleActivity extends BaseActivity {

    Button broadcaster;
    Button audience;
    private RtmClient mRtmClient;
    private String requestNickName = "";

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_role);

        broadcaster = findViewById(R.id.broadcaster);
        audience = findViewById(R.id.audience);

        ChatManager mChatManager = AgoraApplication.the().getChatManager();
        mRtmClient = mChatManager.getRtmClient();
        try {
            requestNickName = URLEncoder.encode(config().getNicklName(),"UTF-8");
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        }
        broadcaster.setOnClickListener(new View.OnClickListener() { //방송인
            @Override
            public void onClick(View v) {
                chattingLogin(getRtmToken(requestNickName), requestNickName, 1);
            }
        });

        audience.setOnClickListener(new View.OnClickListener() { //시청자
            @Override
            public void onClick(View v) {
                chattingLogin(getRtmToken(requestNickName),requestNickName,2);
            }
        });
    }

    public String rtmTokenCreate(String uId) throws Exception {
        //채팅 토큰을 발급합니다.
        RtmTokenBuilder token = new RtmTokenBuilder();
        String result = token.buildToken("앱 아이디", "appCertificate", uId, RtmTokenBuilder.Role.Rtm_User, 0);
        return result;
    }

    private String getRtmToken(String userId){
        //채팅 토큰 발급
        try {
            String result =  rtmTokenCreate(userId);
            Log.d("로그 ","채팅토큰 : "+ result);
            return result;
        }
        catch (Exception e) {
            return "";
        }
    }

    private void chattingLogin(String rtmToken, String user, int flag){
        //채팅서버에 로그인
        mRtmClient.login(rtmToken, user, new ResultCallback<Void>() {
            @Override
            public void onSuccess(Void responseInfo) {
                Log.d("로그 ","채팅 로그인 성공");
                runOnUiThread(() -> {

                    if(flag == 1){
                        Intent intent = new Intent(getApplicationContext(),LiveActivity.class);
                        intent.putExtra(Constants.KEY_CLIENT_ROLE, 1);
                        startActivity(intent);
                    }
                    else{
                        Intent intent = new Intent(getApplicationContext(),LiveActivity.class);
                        intent.putExtra(Constants.KEY_CLIENT_ROLE, 2);
                        startActivity(intent);
                    }
                });
            }

            @Override
            public void onFailure(ErrorInfo errorInfo) {
                Log.d("로그 ","채팅 로그인 실패 : "+errorInfo);
            }
        });
    }

    @Override
    protected void onDestroy() {
        mRtmClient.logout(null);
        MessageUtil.cleanMessageListBeanList();
        super.onDestroy();
    }
}

해당 소스에서는 시청자와 방송자를 구분하고 라이브 화면으로 이동할때 구분값을 방송자는 1 시청자는 2로 해서 보내줍니다.

 

그리고 채팅서버에 로그인을 하는데 이과정에서 전 게시글에서 같이 만들어둔 클래스를 통해서

 

채팅에 필요한 채팅토큰을 발급합니다. (해당 토큰이없으면 로그인이 오류나요!!)

 

그리고 상속된 부분이 BaseActivity인데요

 

자 이제 만들어볼게요

 

public abstract class BaseActivity extends AppCompatActivity implements EventHandler {
    protected DisplayMetrics mDisplayMetrics = new DisplayMetrics();
    protected int mStatusBarHeight;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        WindowUtil.hideWindowStatusBar(getWindow());
        setGlobalLayoutListener();
        getDisplayMetrics();
        initStatusBarHeight();
    }

    private void setGlobalLayoutListener() {
        final View layout = findViewById(Window.ID_ANDROID_CONTENT);
        ViewTreeObserver observer = layout.getViewTreeObserver();
        observer.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
            @Override
            public void onGlobalLayout() {
                layout.getViewTreeObserver().removeOnGlobalLayoutListener(this);
                onGlobalLayoutCompleted();
            }
        });
    }
    protected void onGlobalLayoutCompleted() {

    }

    private void getDisplayMetrics() {
        getWindowManager().getDefaultDisplay().getMetrics(mDisplayMetrics);
    }

    private void initStatusBarHeight() {
        mStatusBarHeight = WindowUtil.getSystemStatusBarHeight(this);
    }

    protected AgoraApplication application() {
        return (AgoraApplication) getApplication();
    }

    protected RtcEngine rtcEngine() {
        return application().rtcEngine();
    }

    protected EngineConfig config() {
        return application().engineConfig();
    }

    protected StatsManager statsManager() { return application().statsManager(); }

    protected void registerRtcEventHandler(EventHandler handler) {
        application().registerEventHandler(handler);
    }

    protected void removeRtcEventHandler(EventHandler handler) {
        application().removeEventHandler(handler);
    }
    @Override
    public void onFirstRemoteVideoDecoded(int uid, int width, int height, int elapsed) {

    }
    @Override
    public void onJoinChannelSuccess(String channel, int uid, int elapsed) {

    }
    @Override
    public void onLeaveChannel(IRtcEngineEventHandler.RtcStats stats) {

    }
    @Override
    public void onUserOffline(int uid, int reason) {

    }
    @Override
    public void onUserJoined(int uid, int elapsed) {

    }
    @Override
    public void onLastmileQuality(final int quality) {

    }
    @Override
    public void onLastmileProbeResult(final IRtcEngineEventHandler.LastmileProbeResult result) {

    }
    @Override
    public void onLocalVideoStats(IRtcEngineEventHandler.LocalVideoStats stats) {

    }
    @Override
    public void onRtcStats(IRtcEngineEventHandler.RtcStats stats) {

    }
    @Override
    public void onNetworkQuality(int uid, int txQuality, int rxQuality) {

    }
    @Override
    public void onRemoteVideoStats(IRtcEngineEventHandler.RemoteVideoStats stats) {

    }
    @Override
    public void onRemoteAudioStats(IRtcEngineEventHandler.RemoteAudioStats stats) {

    }
}

이렇게 셋팅해주시면 됩니다.

 

아고라 문서의 샘플소스를 참고하여 만들었습니다.

 

다음 게시글에서 실시간 방송 커스텀 Ui와 클래스를 제작해볼게요.

 

ㄱ ㅏ   ㄱ  푸시

ㅗ o    ㅗ  푸시 :D

728x90
반응형

댓글