From 30678653058f62beda7ac3f3ac94bc830b6db85e Mon Sep 17 00:00:00 2001
From: Dana <Dana_Lee1016@126.com>
Date: 星期三, 03 十二月 2025 10:49:35 +0800
Subject: [PATCH] 1.新开进程camera2 2.未测试验证 H264EncodeService2

---
 app/src/main/java/com/anyun/h264/H264EncodeService.java |  176 ++++++++++++++++++++++++++++++++++++++++++++++++++++++----
 1 files changed, 163 insertions(+), 13 deletions(-)

diff --git a/app/src/main/java/com/anyun/h264/H264EncodeService.java b/app/src/main/java/com/anyun/h264/H264EncodeService.java
index 67ce31f..a798418 100644
--- a/app/src/main/java/com/anyun/h264/H264EncodeService.java
+++ b/app/src/main/java/com/anyun/h264/H264EncodeService.java
@@ -1,7 +1,10 @@
 package com.anyun.h264;
 
 import android.app.Service;
+import android.content.ComponentName;
+import android.content.Context;
 import android.content.Intent;
+import android.content.ServiceConnection;
 import android.os.IBinder;
 import android.os.RemoteException;
 import timber.log.Timber;
@@ -19,6 +22,8 @@
 import java.util.Date;
 import java.util.List;
 import java.util.Locale;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
 
 /**
  * H264缂栫爜鏈嶅姟
@@ -31,6 +36,11 @@
     private H264FileTransmitter h264FileTransmitter; // H264鏂囦欢浼犺緭鍣�
     private String outputFileDirectory; // H264鏂囦欢杈撳嚭鐩綍
     private WatermarkInfo currentWatermarkInfo; // 褰撳墠姘村嵃淇℃伅
+    
+    // 澶氳繘绋嬫敮鎸侊細绗簩涓憚鍍忓ご鐨勬湇鍔¤繛鎺�
+    private IH264EncodeService camera2Service;
+    private ServiceConnection camera2Connection;
+    private boolean isCamera2Bound = false;
     
     // 榛樿缂栫爜鍙傛暟
     private static final int DEFAULT_WIDTH = 640;
@@ -91,6 +101,18 @@
         // 鍋滄骞堕噴鏀剧紪鐮佸櫒鍜屾枃浠朵紶杈撳櫒
         stopEncoder();
         stopFileTransmitter();
+        
+        // 瑙g粦绗簩涓繘绋嬬殑鏈嶅姟
+        if (isCamera2Bound && camera2Connection != null) {
+            try {
+                unbindService(camera2Connection);
+            } catch (Exception e) {
+                Timber.e(e, "Error unbinding camera2 service");
+            }
+            isCamera2Bound = false;
+            camera2Service = null;
+            camera2Connection = null;
+        }
     }
     
     /**
@@ -103,6 +125,7 @@
         int height;
         int framerate;
         String simPhone;
+        Integer cameraId; // 鎽勫儚澶碔D锛�1鎴�2锛岀敤浜庡杩涚▼鏂规锛�
         
         // 浠嶫SON瑙f瀽閰嶇疆
         static EncodeConfig fromJson(String jsonConfig) throws JSONException {
@@ -115,6 +138,7 @@
                 config.ip = null;
                 config.port = 0;
                 config.simPhone = null;
+                config.cameraId = 1; // 榛樿浣跨敤绗竴涓憚鍍忓ご
                 return config;
             }
             
@@ -125,6 +149,13 @@
             config.ip = json.optString("ip", null);
             config.port = json.optInt("port", 0);
             config.simPhone = json.optString("simPhone", null);
+            
+            // 瑙f瀽cameraId锛堝鏋滄湭鎸囧畾锛岄粯璁や负1锛�
+            if (json.has("cameraId")) {
+                config.cameraId = json.optInt("cameraId", 1);
+            } else {
+                config.cameraId = 1; // 榛樿浣跨敤绗竴涓憚鍍忓ご
+            }
             
             return config;
         }
@@ -171,15 +202,34 @@
      *               4-寮�濮嬩紶杈揌264鏂囦欢锛堜粠鏂囦欢璇诲彇骞剁綉缁滄帹閫侊級锛�
      *               5-鍋滄H264鏂囦欢浼犺緭
      * @param jsonConfig JSON鏍煎紡鐨勯厤缃弬鏁�
-     *                   action 0/2: 鍖呭惈锛歩p銆乸ort銆亀idth銆乭eight銆乫ramerate銆乻imPhone
+     *                   action 0/2: 鍖呭惈锛歩p銆乸ort銆亀idth銆乭eight銆乫ramerate銆乻imPhone銆乧ameraId锛堝彲閫夛紝1鎴�2锛岄粯璁�1锛�
      *                   action 4: 鍖呭惈锛歩p銆乸ort銆乫ramerate銆乻imPhone銆乫ilePath銆乸rotocolType锛堝彲閫夛紝1-UDP锛�2-TCP锛岄粯璁CP锛�
-     *                   action 1/3/5: 姝ゅ弬鏁板彲涓虹┖鎴杗ull
+     *                   action 1/3/5: 姝ゅ弬鏁板彲涓虹┖鎴杗ull锛屾垨鍖呭惈cameraId鏉ユ寚瀹氳鍋滄鐨勬憚鍍忓ご
      * @return 0-鎴愬姛锛�1-澶辫触
      */
     private synchronized int controlEncode(int action, String jsonConfig) {
         Timber.d("controlEncode called with action: %d, jsonConfig: %s", action, jsonConfig);
         
         try {
+            // 瑙f瀽cameraId锛堝鏋滈厤缃腑鏈夛級
+            Integer cameraId = null;
+            if (jsonConfig != null && !jsonConfig.trim().isEmpty()) {
+                try {
+                    JSONObject json = new JSONObject(jsonConfig);
+                    if (json.has("cameraId")) {
+                        cameraId = json.optInt("cameraId", 1);
+                    }
+                } catch (JSONException e) {
+                    // 蹇界暐瑙f瀽閿欒锛岀户缁娇鐢ㄥ綋鍓嶈繘绋�
+                }
+            }
+            
+            // 濡傛灉鎸囧畾浜哻ameraId=2锛岃矾鐢卞埌绗簩涓繘绋�
+            if (cameraId != null && cameraId == 2) {
+                return controlEncodeInProcess2(action, jsonConfig);
+            }
+            
+            // 鍚﹀垯鍦ㄥ綋鍓嶈繘绋嬶紙cameraId=1锛夊鐞�
             switch (action) {
                 case 0: // 寮�鍚痟264鏂囦欢鍐欏叆
                     try {
@@ -191,6 +241,10 @@
                     }
                     
                 case 1: // 鍋滄h264缂栫爜骞跺仠姝㈠啓鍏ユ枃浠�
+                    // 妫�鏌ユ槸鍚︽寚瀹氫簡cameraId=2
+                    if (cameraId != null && cameraId == 2) {
+                        return controlEncodeInProcess2(action, jsonConfig);
+                    }
                     return stopEncoder();
                     
                 case 2: // 寮�鍚綉缁滄帹閫乭264锛堜笉鍐欏叆鏂囦欢锛�
@@ -203,6 +257,10 @@
                     }
                     
                 case 3: // 鍋滄h264缂栫爜骞跺仠姝㈢綉缁滄帹閫�
+                    // 妫�鏌ユ槸鍚︽寚瀹氫簡cameraId=2
+                    if (cameraId != null && cameraId == 2) {
+                        return controlEncodeInProcess2(action, jsonConfig);
+                    }
                     return stopEncoder();
                     
                 case 4: // 寮�濮嬩紶杈揌264鏂囦欢
@@ -216,6 +274,10 @@
                     
                 case 5: // 鍋滄H264鏂囦欢浼犺緭
                     Timber.i("瀹㈡埛绔姹傚仠姝㈣棰戞枃浠朵笂浼�");
+                    // 妫�鏌ユ槸鍚︽寚瀹氫簡cameraId=2
+                    if (cameraId != null && cameraId == 2) {
+                        return controlEncodeInProcess2(action, jsonConfig);
+                    }
                     return stopFileTransmitter();
                     
                 default:
@@ -226,6 +288,85 @@
             Timber.e(e, "Error in controlEncode");
             return 1; // 澶辫触
         }
+    }
+    
+    /**
+     * 鍦ㄧ浜屼釜杩涚▼锛坈amera2锛変腑鎵ц缂栫爜鎺у埗
+     */
+    private int controlEncodeInProcess2(int action, String jsonConfig) {
+        Timber.d("Routing to process 2 (camera2) for action: %d", action);
+        
+        try {
+            // 纭繚绗簩涓繘绋嬬殑鏈嶅姟宸茬粦瀹�
+            if (!ensureCamera2ServiceBound()) {
+                Timber.e("Failed to bind camera2 service");
+                return 1;
+            }
+            
+            // 璋冪敤绗簩涓繘绋嬬殑鏈嶅姟
+            if (camera2Service != null) {
+                return camera2Service.controlEncode(action, jsonConfig);
+            } else {
+                Timber.e("Camera2 service is null");
+                return 1;
+            }
+        } catch (RemoteException e) {
+            Timber.e(e, "Error calling camera2 service");
+            return 1;
+        }
+    }
+    
+    /**
+     * 纭繚绗簩涓繘绋嬬殑鏈嶅姟宸茬粦瀹�
+     */
+    private synchronized boolean ensureCamera2ServiceBound() {
+        if (isCamera2Bound && camera2Service != null) {
+            return true;
+        }
+        
+        Timber.d("Binding to camera2 service...");
+        
+        final CountDownLatch latch = new CountDownLatch(1);
+        final boolean[] success = {false};
+        
+        camera2Connection = new ServiceConnection() {
+            @Override
+            public void onServiceConnected(ComponentName name, IBinder service) {
+                Timber.d("Camera2 service connected");
+                camera2Service = IH264EncodeService.Stub.asInterface(service);
+                isCamera2Bound = true;
+                success[0] = true;
+                latch.countDown();
+            }
+            
+            @Override
+            public void onServiceDisconnected(ComponentName name) {
+                Timber.w("Camera2 service disconnected");
+                camera2Service = null;
+                isCamera2Bound = false;
+            }
+        };
+        
+        Intent intent = new Intent(this, H264EncodeService2.class);
+        boolean bound = bindService(intent, camera2Connection, Context.BIND_AUTO_CREATE);
+        
+        if (!bound) {
+            Timber.e("Failed to bind camera2 service");
+            return false;
+        }
+        
+        // 绛夊緟鏈嶅姟杩炴帴锛堟渶澶�5绉掞級
+        try {
+            if (!latch.await(5, TimeUnit.SECONDS)) {
+                Timber.e("Timeout waiting for camera2 service connection");
+                return false;
+            }
+        } catch (InterruptedException e) {
+            Timber.e(e, "Interrupted while waiting for camera2 service");
+            return false;
+        }
+        
+        return success[0];
     }
     
     /**
@@ -245,9 +386,9 @@
             h264Encoder = new H264Encoder();
             
             // 璁剧疆缂栫爜鍙傛暟锛堜娇鐢ㄩ厤缃腑鐨勫弬鏁帮級
-            int width = config != null ? config.width : DEFAULT_WIDTH;
-            int height = config != null ? config.height : DEFAULT_HEIGHT;
-            int framerate = config != null ? config.framerate : DEFAULT_FRAME_RATE;
+            int width = config != null && config.width > 0 ? config.width : DEFAULT_WIDTH;
+            int height = config != null && config.height > 0 ? config.height : DEFAULT_HEIGHT;
+            int framerate = config != null && config.framerate > 0 ? config.framerate : DEFAULT_FRAME_RATE;
             h264Encoder.setEncoderParams(width, height, framerate, DEFAULT_BITRATE);
 
             long timeFile = System.currentTimeMillis()/1000*1000;//Date鏄锛屾墍浠ヤ负浜嗚窡涓嬪彂鐨凞ate starttime涓�鑷达紝姝ゅ闄や互1000 绉�
@@ -264,8 +405,14 @@
             h264Encoder.setEnableNetworkTransmission(false);
             
             // 鍒濆鍖栧苟鍚姩锛堜娇鐢ㄩ厤缃腑鐨勫垎杈ㄧ巼锛�
+            // 鏍规嵁cameraId閫夋嫨鎽勫儚澶磋寖鍥�
+            int[] cameraIdRange = DEFAULT_CAMERA_ID_RANGE;
+            if (config != null && config.cameraId != null) {
+                // 濡傛灉鎸囧畾浜哻ameraId锛屼娇鐢ㄥ搴旂殑鎽勫儚澶�
+                cameraIdRange = new int[]{config.cameraId, config.cameraId};
+            }
             int[] resolution = {width, height};
-            if (h264Encoder.initialize(DEFAULT_CAMERA_ID_RANGE, null, resolution, false)) {
+            if (h264Encoder.initialize(cameraIdRange, null, resolution, false)) {
                 // 搴旂敤宸蹭繚瀛樼殑姘村嵃淇℃伅锛堝鏋滄湁锛�
                 if (currentWatermarkInfo != null) {
                     h264Encoder.setWatermarkInfo(currentWatermarkInfo);
@@ -310,12 +457,9 @@
             h264Encoder = new H264Encoder();
             
             // 璁剧疆缂栫爜鍙傛暟锛堜娇鐢ㄩ厤缃腑鐨勫弬鏁帮級
-
-
-            // 璁剧疆缂栫爜鍙傛暟锛堜娇鐢ㄩ厤缃腑鐨勫弬鏁帮級
-            int width =  DEFAULT_WIDTH;
-            int height =  DEFAULT_HEIGHT;
-            int framerate = DEFAULT_FRAME_RATE;
+            int width = config != null && config.width > 0 ? config.width : DEFAULT_WIDTH;
+            int height = config != null && config.height > 0 ? config.height : DEFAULT_HEIGHT;
+            int framerate = config != null && config.framerate > 0 ? config.framerate : DEFAULT_FRAME_RATE;
             h264Encoder.setEncoderParams(width, height, framerate, DEFAULT_BITRATE);
 
             long timeFile = System.currentTimeMillis()/1000*1000;
@@ -339,8 +483,14 @@
             h264Encoder.setProtocolParams(simPhone, (byte)1);
             
             // 鍒濆鍖栧苟鍚姩锛堜娇鐢ㄩ厤缃腑鐨勫垎杈ㄧ巼锛�
+            // 鏍规嵁cameraId閫夋嫨鎽勫儚澶磋寖鍥�
+            int[] cameraIdRange = DEFAULT_CAMERA_ID_RANGE;
+            if (config != null && config.cameraId != null) {
+                // 濡傛灉鎸囧畾浜哻ameraId锛屼娇鐢ㄥ搴旂殑鎽勫儚澶�
+                cameraIdRange = new int[]{config.cameraId, config.cameraId};
+            }
             int[] resolution = {width, height};
-            if (h264Encoder.initialize(DEFAULT_CAMERA_ID_RANGE, null, resolution, false)) {
+            if (h264Encoder.initialize(cameraIdRange, null, resolution, false)) {
                 // 搴旂敤宸蹭繚瀛樼殑姘村嵃淇℃伅锛堝鏋滄湁锛�
                 if (currentWatermarkInfo != null) {
                     h264Encoder.setWatermarkInfo(currentWatermarkInfo);

--
Gitblit v1.8.0