Trong bài này, tôi đang sử dụng H.264
làm ví dụ, nhưng giải pháp có thể được mở rộng để hỗ trợ các codec khác như MPEG-4
, VC-1
, VP8
v.v. Có 2 giải pháp khả thi để giải quyết vấn đề của bạn, mà tôi đang tranh thủ bên dưới, mỗi giải pháp đều có ưu và khuyết điểm riêng để giúp bạn đưa ra quyết định sáng suốt.
Giải pháp 1: Mở rộng các codec để hỗ trợ chế độ mới
Trong JellyBean
, người ta có thể đăng ký cùng OMX
thành phần với cùng MIME
loại như 2 tên thành phần khác nhau tức, OMX.ABC.XYZ
và OMX.ABC.XYZ.secure
.. Trước đây được sử dụng để phát lại bình thường và là thành phần thường được sử dụng hơn. Dữ liệu sau được sử dụng khi trình phân tích cú pháp tức là MediaExtractor
cho biết sự hiện diện của nội dung an toàn. Trong OMXCodec::Create
, sau khi findMatchingCodecs
trả về danh sách các codec, chúng tôi có thể quan sát lựa chọn để chọn thành phần .secure
là here.
bước để làm theo:
Trong nền tảng của bạn, hãy đăng ký thành phần khác với một số phần mở rộng mới như OMX.H264.DECODER.decrypt
hoặc một cái gì đó tương tự. Thay đổi chỉ được yêu cầu trong media_codecs.xml
. Việc chọn đăng ký một phương thức nhà máy mới hoặc có phương pháp nhà máy chung là sự lựa chọn của bạn.
Từ trình phân tích cú pháp của bạn, khi bạn gặp trường hợp sử dụng cụ thể, hãy đặt cờ mới như kKeyDecryptionRequired
. Đối với điều này, bạn sẽ phải xác định một lá cờ mới trong và một quirk tương ứng trong OMXCodec.h
.
Sửa đổi phương thức OMXCodec::create
để thêm hậu tố .decrypt
tương tự như hậu tố .secure
như được hiển thị ở trên.
Với tất cả những thay đổi về OMXCodec
, Metadata
, MediaExtractor
mô-đun, bạn sẽ phải xây dựng lại chỉ libstagefright.so
và thay thế giống nhau trên nền tảng của bạn.
Thì đấy !! sự tích hợp của bạn phải hoàn tất. Bây giờ đến thử thách chính bên trong thành phần. Là một phần của việc triển khai thành phần, bạn sẽ có thể phân biệt giữa việc tạo thành phần thông thường và tạo thành phần .decrypt
.
Từ góc độ thời gian chạy, giả định rằng thành phần của bạn là nhận thức được thực tế là nó là một thành phần .decrypt
hay không, bạn có thể xử lý các decryption
như một phần của OMX_EmptyThisBuffer
cuộc gọi, nơi bạn có thể giải mã dữ liệu và sau đó vượt qua nó để codec bên dưới.
Ưu điểm: Dễ tích hợp, Thay đổi tối thiểu trong khung công tác Android, Khả năng mở rộng sang các codec khác, Không cần đăng ký loại mới MIME
.
Nhược điểm: Bạn cần phải theo dõi các bản sửa đổi trong tương lai của Android, cụ thể trên các quirks mới, cờ và lựa chọn mở rộng .decrypt
. Nếu Google quyết định sử dụng một cái gì đó tương tự, bạn sẽ phải thích ứng/sửa đổi giải pháp của bạn cho phù hợp.
Giải pháp 2: Đăng ký mới Loại MIME
Từ câu hỏi của bạn, nó không phải là rõ ràng nếu bạn đã có thể xác định loại MIME
hay không và do đó, tôi đang chụp các bước cho rõ ràng.
bước để làm theo:
Đăng ký một MIME
kiểu mới tại MediaDefs
như here. Ví dụ: bạn có thể sử dụng loại MIME
mới làm const char *MEDIA_MIMETYPE_VIDEO_AVC_ENCRYPT = "video/avc-encrypt";
Đăng ký thành phần mới của bạn với số này media_codecs.xml
được cập nhật. Xin lưu ý rằng bạn sẽ phải đảm bảo rằng các thành phần quirks cũng được xử lý cho phù hợp.
Trong thực hiện phương pháp OMXCodec::setVideoOutputFormat
, bạn sẽ phải giới thiệu hỗ trợ xử lý loại MIME
mới như được hiển thị cho H.264
here. Xin lưu ý rằng bạn sẽ phải xử lý các thay đổi tương tự trong OMXCodec
để hỗ trợ loại MIME
mới.
Trong MediaExtractor
, bạn sẽ phải báo hiệu loại MIME
cho theo dõi video
bằng cách sử dụng loại mới được xác định.Với những thay đổi này, thành phần của bạn sẽ được chọn và tạo.
Tuy nhiên, thách thức vẫn còn: Nơi để thực hiện giải mã? Đối với điều này, bạn cũng có thể sử dụng cùng một giải pháp như được mô tả trong phần trước, tức là xử lý giống như một phần của cuộc gọi OMX_EmptyThisBuffer
.
Ưu điểm: Không mà tôi có thể nghĩ ra ..
Nhược điểm: Thứ nhất, giải pháp là không thể mở rộng. Bạn sẽ phải tiếp tục thêm các loại MIME
mới hơn và tiếp tục sửa đổi khung Stagefright
. Tiếp theo, các thay đổi trong OMXCodec
sẽ yêu cầu các thay đổi tương ứng trong MediaExtractor
. Do đó, mặc dù trọng tâm ban đầu của bạn là trên thiết bị giải nén MP4
, nếu bạn muốn mở rộng giải pháp cho các định dạng vùng chứa khác như AVI
, MKV
, bạn sẽ phải bao gồm hỗ trợ cho các loại MIME
mới trong các trình giải nén này.
Cuối cùng, một số ghi chú.
Là giải pháp ưu tiên, tôi khuyên bạn nên sử dụng Giải pháp 1 vì dễ dàng và đơn giản.
Tôi chưa chạm vào việc triển khai ACodec
dựa trên codec. Tuy nhiên, tôi cảm thấy rằng Solution 1 sẽ là một giải pháp dễ dàng hơn nhiều để thực hiện ngay cả khi sự hỗ trợ đó được yêu cầu trong tương lai.
Nếu bạn không sửa đổi lõi OMX
, bạn không cần phải sửa đổi libstagefrighthw.so
. Chỉ FYI, điều này thường được thực hiện bởi các nhà cung cấp như là một phần của mô-đun cụ thể của nhà cung cấp của họ như trong vendor/<xyz>/hardware/...
. Bạn cần phải kiểm tra với nhà cung cấp nền tảng của bạn trên các nguồn cho libstagefrighthw.so
.
Cảm ơn rất nhiều Ganesh, điều này thật tuyệt vời. Chúng tôi đã phải triển khai trình phát phương tiện tùy chỉnh hiện tại vì các ràng buộc về thời gian, nhưng sẽ sớm quay lại Giải pháp 1 của bạn ... Cảm ơn bạn một lần nữa. – Matthew
@Matthew Tôi đang làm việc trên chính xác yêu cầu tương tự với thời hạn chặt chẽ. Phải giải mã các tệp trước khi giải mã. Người chơi nào bạn chọn cho người chơi này ?? Hãy đề nghị tôi một. Cảm ơn – CodeFury
@Sree Cuối cùng tôi đã bỏ qua việc sửa đổi Android ngay bây giờ. Tôi dựa trên một trình phát tùy chỉnh trong ví dụ này: [Cedric Fung] (https://github.com/vecio/MediaCodecDemo). Sau dòng 'int sampleSize = extractor.readSampleData (buffer, 0);' bạn có thể giải mã bộ đệm. (Tôi đã xây dựng một bộ mã hóa đơn giản để mã hóa dữ liệu mẫu và tạo một tệp phim enc - chỉ cần phân tích cú pháp các hộp và mã hóa lại độ dài sau khi mã hóa dữ liệu). Hy vọng rằng sẽ giúp! – Matthew