| 1528 | export const aacChannelMap = [-1, 1, 2, 3, 4, 5, 6, 8]; |
| 1529 | |
| 1530 | export const parseAacAudioSpecificConfig = (bytes: Uint8Array | null): AacAudioSpecificConfig => { |
| 1531 | if (!bytes || bytes.byteLength < 2) { |
| 1532 | throw new TypeError('AAC description must be at least 2 bytes long.'); |
| 1533 | } |
| 1534 | |
| 1535 | const bitstream = new Bitstream(bytes); |
| 1536 | |
| 1537 | let objectType = bitstream.readBits(5); |
| 1538 | if (objectType === 31) { |
| 1539 | objectType = 32 + bitstream.readBits(6); |
| 1540 | } |
| 1541 | |
| 1542 | const frequencyIndex = bitstream.readBits(4); |
| 1543 | let sampleRate: number | null = null; |
| 1544 | if (frequencyIndex === 15) { |
| 1545 | sampleRate = bitstream.readBits(24); |
| 1546 | } else { |
| 1547 | if (frequencyIndex < aacFrequencyTable.length) { |
| 1548 | sampleRate = aacFrequencyTable[frequencyIndex]!; |
| 1549 | } |
| 1550 | } |
| 1551 | |
| 1552 | const channelConfiguration = bitstream.readBits(4); |
| 1553 | let numberOfChannels: number | null = null; |
| 1554 | if (channelConfiguration >= 1 && channelConfiguration <= 7) { |
| 1555 | numberOfChannels = aacChannelMap[channelConfiguration]!; |
| 1556 | } |
| 1557 | |
| 1558 | return { |
| 1559 | objectType, |
| 1560 | frequencyIndex, |
| 1561 | sampleRate, |
| 1562 | channelConfiguration, |
| 1563 | numberOfChannels, |
| 1564 | }; |
| 1565 | }; |
| 1566 | |
| 1567 | export const aacToAdts = (data: Uint8Array, audioSpecificConfig: AacAudioSpecificConfig) => { |
| 1568 | const { objectType, frequencyIndex, channelConfiguration } = audioSpecificConfig; |