NALU Explorer - เครื่องมือแสดงภาพ NAL Unit ของสตรีมวิดีโอ H.264
(nalu.funnify.org)ที่มาของการพัฒนาและแนวคิดการนำไปใช้
- ระหว่างการพัฒนา/ดีบักโคเดกวิดีโอ H.264 ต้องการตรวจสอบโครงสร้าง NAL Unit แบบมองเห็นภาพ
- แม้จะวิเคราะห์ด้วยคำสั่ง FFmpeg ได้ แต่ต้องการคลิกดู NAL Unit แต่ละตัวพร้อมภาพเฟรมจริงไปด้วย
- จึงต้องมี Annex B parser ที่ทำงานได้ทันทีบนเบราว์เซอร์ และเมื่อใช้ FFmpeg แบบ WebAssembly ก็สามารถถอดรหัสเฟรมได้ด้วย
- พัฒนาไลบรารี
h264-parserขึ้นเองเพื่อพาร์สได้ถึง SPS/PPS/Slice Header (เผยแพร่เป็นแพ็กเกจ NPM) - เอาต์พุตอิงตามโครงสร้างไวยากรณ์มาตรฐาน H.264: แสดงฟิลด์เป็นลำดับชั้น (indent) โดยอ้างอิง parsing syntax tree ของสเปก ITU-T H.264 โดยตรง
วิธีการทำงาน
- การพาร์ส Annex B: ตรวจจับ start code
00 00 00 01หรือ00 00 01 - การพาร์สพารามิเตอร์:
- SPS/PPS: ดึงพารามิเตอร์ด้วย parser
- Slice Header:
first_mb_in_slice,slice_type,pic_parameter_set_idเป็นต้น - สอดคล้องกับไวยากรณ์มาตรฐาน: แสดงโครงสร้างตามสเปก H.264 ตรงตัว เช่น
nal_unit()→seq_parameter_set_rbsp()→vui_parameters()
- การถอดรหัสเฟรม:
- คำนวณช่วง GOP ที่ NAL Unit ที่เลือกสังกัดอยู่ (ค้นหา IDR ก่อนหน้า/ถัดไป)
- ประกอบ Annex B ใหม่พร้อมส่วนหัว SPS/PPS
ฟีเจอร์หลัก
การพาร์ส
- แยก NAL Unit โดยอิงจาก Annex B Start Code
- พาร์สตามประเภทของ NAL Unit:
- Type 7 (SPS): profile, level, resolution, frame rate เป็นต้น
- Type 8 (PPS): entropy coding mode, slice groups เป็นต้น
- Type 1/5 (Slice): slice_type, first_mb_in_slice, frame_num เป็นต้น
- Type 6 (SEI): เมตาดาตา (รองรับการพาร์สอย่างจำกัด)
- แสดง syntax tree มาตรฐาน H.264: แสดงการพาร์สแบบมีเงื่อนไข (
ifblock), โครงสร้างลำดับชั้น และลำดับการอ่านบิตสตรีมตามจริง - RBSP Hex dump: ดูข้อมูลดิบได้ในรูปแบบ offset, hex bytes และ ASCII
ตัวอย่างเอาต์พุตการพาร์ส SPS จริง:
nal_unit()
forbidden_zero_bit: 0
nal_ref_idc: 3
nal_unit_type: 7
seq_parameter_set_rbsp()
profile_idc: 100
constraint_set0_flag: 0
constraint_set1_flag: 0
constraint_set2_flag: 0
constraint_set3_flag: 0
constraint_set4_flag: 0
constraint_set5_flag: 0
reserved_zero_2bits: 0
...
การถอดรหัสเฟรม
- คำนวณช่วงอัตโนมัติแบบ GOP (ค้นหา IDR ก่อนหน้า/ถัดไป)
- ค้นหาและแทรกส่วนหัว SPS/PPS ล่วงหน้าให้อัตโนมัติ
- ดึง BMP ด้วย FFmpeg.wasm แล้วเรนเดอร์บน Canvas
การดึงข้อมูลออก
- ดาวน์โหลด NAL Unit แยกเดี่ยว (Annex B Start Code + rawData)
- ดาวน์โหลดแบบหน่วย GOP (SPS/PPS + NAL Units ในช่วง GOP)
- แสดงภาพ NAL Unit เป็นไทม์ไลน์ (ใช้สีแยกตามประเภท, ขนาดตามสัดส่วน)
ข้อจำกัด
- ไม่รองรับ Slice Data: พาร์สได้ถึง Slice Header เท่านั้น ไม่วิเคราะห์ส่วน
slice_dataเช่น ข้อมูลมาโครบล็อก, MVD, residual coefficients เป็นต้น - ยังไม่ตรวจสอบฟอร์แมต AVC: มีการเขียนโค้ดสำหรับพาร์สแบบ length-based แล้ว แต่ยังไม่ได้ทดสอบ
- การโหลดเริ่มต้นของ FFmpeg.wasm: ครั้งแรกจะต้องดาวน์โหลดไลบรารีขนาดประมาณ ~10-20MB
ลิงก์
- เดโมสด: https://nalu.funnify.org
- ไลบรารี NPM: https://www.npmjs.com/package/h264-parser
ยังไม่มีความคิดเห็น