Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Flip Flop Camera #131

Open
aponcanos opened this issue Sep 9, 2024 · 9 comments
Open

Flip Flop Camera #131

aponcanos opened this issue Sep 9, 2024 · 9 comments

Comments

@aponcanos
Copy link

How can I flip flop camera?

@pedroSG94
Copy link
Owner

You can flip the preview or the stream using this methods:

//only affect to preview (stream result no change)
rtmpCamera2.getGlInterface().setIsPreviewHorizontalFlip(true);
rtmpCamera2.getGlInterface().setIsPreviewVerticalFlip(true);
//only affect to stream result (preview no change)
rtmpCamera2.getGlInterface().setIsStreamHorizontalFlip(true);
rtmpCamera2.getGlInterface().setIsStreamVerticalFlip(true);

@aponcanos
Copy link
Author

same works on rtspServerCamera1?

@aponcanos
Copy link
Author

aponcanos commented Sep 9, 2024

I am using surfaceView and RtspServerCamera1. I need to flip and flop on stream side. Thnx for help.

@pedroSG94
Copy link
Owner

Hello,

You can't flip using SurfaceView. You will have to change to OpenGlView and then you can use that methods.

@aponcanos
Copy link
Author

it works on android 7.0 ?

@pedroSG94
Copy link
Owner

It works with Android 5.1+

@aponcanos
Copy link
Author

where can I find rtsp + openGL sample? do you have any sample? Thank you

@pedroSG94
Copy link
Owner

You don't need change any code.
Just replace SurfaceView to OpenGlView in your XML and change the class type in your activity code to OpenGlView

@aponcanos
Copy link
Author

I changed XML but crashes. Where is my mistake? Can you help?

package com.pedro.sample

import android.graphics.SurfaceTexture
import android.os.Build
import android.os.Bundle
import android.view.TextureView
import android.view.WindowManager
import android.widget.ImageView
import android.widget.TextView
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import com.pedro.common.ConnectChecker
import com.pedro.encoder.input.video.CameraHelper
import com.pedro.encoder.input.video.CameraOpenException
import com.pedro.library.base.recording.RecordController
import com.pedro.library.view.AutoFitTextureView
import com.pedro.rtspserver.RtspServerCamera1
import com.pedro.rtspserver.server.ClientListener
import com.pedro.rtspserver.server.ServerClient

import java.io.IOException
import java.text.SimpleDateFormat
import java.util.Date
import java.util.Locale
import android.content.pm.ActivityInfo
import android.graphics.RectF
import android.graphics.Matrix
import com.pedro.library.view.OrientationForced

class CameraDemoActivity : AppCompatActivity(), ConnectChecker, ClientListener,
TextureView.SurfaceTextureListener, OnRequestReceivedListener {

private lateinit var httpServer: MyHTTPServer
private lateinit var textView: TextView

private lateinit var rtspServerCamera1: RtspServerCamera1
private lateinit var bStream: ImageView
private lateinit var bRecord: ImageView
private lateinit var bSwitchCamera: ImageView
private lateinit var surfaceView: AutoFitTextureView
private lateinit var tvUrl: TextView
private var recordPath = ""

override fun onCreate(savedInstanceState: Bundle?) {

super.onCreate(savedInstanceState)

// window.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
setContentView(R.layout.activity_camera_demo)
tvUrl = findViewById(R.id.tv_url)
bStream = findViewById(R.id.b_start_stop)
bRecord = findViewById(R.id.b_record)
bSwitchCamera = findViewById(R.id.switch_camera)
surfaceView = findViewById(R.id.surfaceView)
rtspServerCamera1 = RtspServerCamera1(surfaceView, this, 2888)
rtspServerCamera1.streamClient.setClientListener(this)

surfaceView.surfaceTextureListener = this

textView = findViewById(R.id.rtspTest)  // UI'deki TextView

startHttpServer()

// rtspServerCamera1.prepareVideo(1920, 1080, 25, 1024 * 1200, 0)
// rtspServerCamera1.startStream()
// tvUrl.text = rtspServerCamera1.streamClient.getEndPointConnection()
// ScreenOrientation.lockScreen(this)

bStream.setOnClickListener {
  rtspServerCamera1.prepareVideo(1920, 1080, 25, 1024 * 1200, 270)

  rtspServerCamera1.startStream()
  tvUrl.text = rtspServerCamera1.streamClient.getEndPointConnection()



}

bRecord.setOnClickListener {
  if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
    if (rtspServerCamera1.isRecording) {
      rtspServerCamera1.stopRecord()
      bRecord.setImageResource(R.drawable.record_icon)
      PathUtils.updateGallery(this, recordPath)
      if (!rtspServerCamera1.isStreaming) ScreenOrientation.unlockScreen(this)
    } else if (rtspServerCamera1.isStreaming || prepare()) {
      val folder = PathUtils.getRecordPath()
      if (!folder.exists()) folder.mkdir()
      val sdf = SimpleDateFormat("yyyyMMdd_HHmmss", Locale.getDefault())
      recordPath = "${folder.absolutePath}/${sdf.format(Date())}.mp4"
      bRecord.setImageResource(R.drawable.pause_icon)
      rtspServerCamera1.startRecord(recordPath) { status ->
        if (status == RecordController.Status.RECORDING) {
          bRecord.setImageResource(R.drawable.stop_icon)
        }
      }
      ScreenOrientation.lockScreen(this)
    } else {
      toast("Error preparing stream, This device cant do it")
    }
  } else {
    toast("You need min JELLY_BEAN_MR2(API 18) for do it...")
  }
}

bSwitchCamera.setOnClickListener {
  try {
    rtspServerCamera1.switchCamera()
  } catch (e: CameraOpenException) {
    Toast.makeText(this, e.message, Toast.LENGTH_SHORT).show()
  }
}

}

private fun startHttpServer() {
val port = 8080 // Sunucunun çalışacağı port
httpServer = MyHTTPServer(port, this, this)

try {
  httpServer.start()  // HTTP Sunucusunu başlat
  println("HTTP sunucusu $port numaralı portta çalışıyor.")
} catch (e: IOException) {
  e.printStackTrace()
  println("Sunucu başlatılamadı: ${e.message}")
}

}

override fun onRequestReceived(param1: String, param2: String) {
// Gelen parametreleri UI'de göstermek için UI iş parçacığında çalıştır
runOnUiThread {
Toast.makeText(applicationContext, "YASAK PLAKA", Toast.LENGTH_LONG).show()
}
}

private fun prepare(): Boolean {
val prepared = rtspServerCamera1.prepareAudio() && rtspServerCamera1.prepareVideo()
adaptPreview()
return prepared
}

private fun adaptPreview() {
val isPortrait = CameraHelper.isPortrait(this)
val w = if (isPortrait) rtspServerCamera1.streamHeight else rtspServerCamera1.streamWidth
val h = if (isPortrait) rtspServerCamera1.streamWidth else rtspServerCamera1.streamHeight
surfaceView.setAspectRatio(w, h)
}

override fun onNewBitrate(bitrate: Long) {}

override fun onConnectionSuccess() {
toast("Connected")
}

override fun onConnectionFailed(reason: String) {
toast("Failed: $reason")
rtspServerCamera1.stopStream()
if (!rtspServerCamera1.isRecording) ScreenOrientation.unlockScreen(this)
bStream.setImageResource(R.drawable.stream_icon)
}

override fun onConnectionStarted(url: String) {}

override fun onDisconnect() {
toast("Disconnected")
}

override fun onAuthError() {
toast("Auth error")
rtspServerCamera1.stopStream()
if (!rtspServerCamera1.isRecording) ScreenOrientation.unlockScreen(this)
bStream.setImageResource(R.drawable.stream_icon)
}

override fun onAuthSuccess() {
toast("Auth success")
}

override fun onClientConnected(client: ServerClient) {
toast("Client connected: ${client.clientAddress}")
}

override fun onDestroy() {
super.onDestroy()
httpServer.stop()
}

override fun onClientDisconnected(client: ServerClient) {
toast("Client disconnected: ${client.clientAddress}")
}

override fun onSurfaceTextureAvailable(surface: SurfaceTexture, width: Int, height: Int) {
if (!rtspServerCamera1.isOnPreview) {
rtspServerCamera1.startPreview()
adaptPreview()

// // Ekranı 90 derece döndürme işlemi için Matrix oluştur
// val matrix = Matrix()
//
// // TextureView boyutlarına göre merkezi hesapla
// val centerX = width / 2f
// val centerY = height / 2f
//
// // 90 derece döndür ve merkezi belirle
// matrix.postRotate(180f, centerX, centerY)
//
// matrix.postScale(-1f, 1f, centerX, centerY)
//
// // TextureView'e bu dönüşümü uygula
// surfaceView.setTransform(matrix)
}
}

override fun onSurfaceTextureSizeChanged(surface: SurfaceTexture, width: Int, height: Int) {

}

override fun onSurfaceTextureDestroyed(surface: SurfaceTexture): Boolean {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2 && rtspServerCamera1.isRecording) {
rtspServerCamera1.stopRecord()
bRecord.setBackgroundResource(R.drawable.record_icon)
PathUtils.updateGallery(this, recordPath)
}
if (rtspServerCamera1.isStreaming) {
rtspServerCamera1.stopStream()
bStream.setImageResource(R.drawable.stream_icon)
}
if (rtspServerCamera1.isOnPreview) rtspServerCamera1.stopPreview()
ScreenOrientation.unlockScreen(this)
return true
}

override fun onSurfaceTextureUpdated(surface: SurfaceTexture) {}
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants