This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] TAD5112:TAD5112 音频未播放/失真

Guru**** 2777545 points

Other Parts Discussed in Thread: TAD5112

请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/audio-group/audio/f/audio-forum/1612177/tad5112-tad5112-audio-not-playing-distorted

器件型号: TAD5112

尊敬的所有人:

我使用 TAD5112 存在问题。 我想用它来播放耳机上的短 WAV 文件。 左右声道交替(eMDR 应用程序)。 问题是我只能在播放 WAV 文件时听到软弹出的声音、没有音频。

我使用 STM32U5 和 SAI 外设来控制 TAD5112、这些外设配置为标准 I2S、32 位字长、44.1kHz 音频。 我使用 DMA 将数据传输到 SAI(存储器到外设,数据大小=字)。

下面是我使用 TAD5112 实现的原理图。 我以伪差分配置连接了耳机。 image.png

我使用 PurePath Console 应用程序生成寄存器内容、但我发现它无法正确地将寄存器输出到应用程序中配置的文件。 应用会跳过一些寄存器、值并不总是正确的、因此我自己配置了寄存器。 以下是 TAD5112 的当前初始化:

bool TAD5112::Init(void) {
    // Check if device is ready
    if (!_i2c.isDeviceReady(_address, 3, I2C_TIMEOUT_MS)) {
        return false;
    }
    _currentPage = 0xFF; // Reset page cache

    // Perform a software reset
    if (!SelectPage(0)) return false;
    if (!WriteRegister(REG_RESET, 0x01)) { // Write 0x01 to Reset register
        return false;
    }
    Utils::DelayMs(10); // Wait for reset to complete (datasheet recommends 10ms)

    if (!WriteRegister(REG_P0_DEV_MISC_CFG, 0x09)) return false; // Disable sleep mode
    Utils::DelayMs(2);
    if (!WriteRegister(REG_P0_PASI_CFG0, 0x70)) return false; //Select I2S communication, 32bit words
    if (!WriteRegister(REG_P0_PASI_RX_CFG0, 0x01)) return false; //Set 1 clock offset in I2S communication (standard I2S)
    if (!WriteRegister(REG_P0_PASI_RX_CH1_CFG, 0x20)) return false; //ASI channel 1 = DAC channel 1, I2S left slot 0
    if (!WriteRegister(REG_P0_PASI_RX_CH2_CFG, 0x30)) return false; //ASI channel 2 = DAC channel 2, I2S right slot 0
    if (!WriteRegister(REG_P0_OUT1x_CFG0, 0x34)) return false; //OUT1 to input from DAC, pseudo differential mode
    if (!WriteRegister(REG_P0_OUT1x_CFG1, 0x60)) return false; //OUT1P headphone mode, 0dB gain
    if (!WriteRegister(REG_P0_OUT1x_CFG2, 0x60)) return false; //OUT1M headphone mode
    if (!WriteRegister(REG_P0_OUT2x_CFG0, 0x30)) return false; // OUT2 to input from DAC, pseudo differential mode
    if (!WriteRegister(REG_P0_OUT2x_CFG1, 0x60)) return false; //OUT2P headphone mode, 0dB gain
    if (!WriteRegister(REG_P0_OUT2x_CFG2, 0x60)) return false; //OUT2M headphone mode
    if (!WriteRegister(REG_P0_CH_EN, 0x0C)) return false; // enable DAC channels 1 & 2
    if (!WriteRegister(REG_P0_DYN_PUPD_CFG, 0x20)) return false; // enable DAC dynamic power up & down
    if (!WriteRegister(REG_P0_PWR_CFG, 0x40)) return false; // power up DAC;

    // --- Configure Page 1 (Power and Analog Outputs) ---
    if (!SelectPage(1)) return false;

    if (!WriteRegister(REG_P1_JACK_DET_CFG1, 0x0E)) return false; // headset detection enabled, 2x current, DC-coupled
    if (!WriteRegister(REG_P1_JACK_DET_CFG2, 0x40)) return false; // debounce connect 3 detections, detection time 16ms, debounce removal 5 detections

    // Set default volume (0-100%)
    _volume = 50;
    SetVolume(_volume);

    _isInitialized = true;
    return true;
}

我的代码具有以下功能、可将 16 位带符号 WAV 音频加载到左声道和/或右声道(伪代码):

int32_t buffer[]
if(playback == leftonly) {
buffer[i] = audiosample16bit << 16;
buffer[i+1] = 0;
} else if(playback == rightonly) {
buffer[i] = 0;
buffer[i+1] = audiosample16bit << 16;
} else {
buffer[i] = audiosample16bit << 16;
buffer[i+1] = audiosample16bit << 16;
}

到目前为止我的调查结果:

  • I2C 通信正常工作
  • 验证 WAV 文件数据。 WAV 文件在 Windows 上播放、采样率为 44.1kHz。 我使用 Python 脚本将 wav 文件转换为 C++数组。 我比较的 WAV 文件 hexedit 与 C++代码,这匹配。 我使用具有 32 位时隙的 I2S、因此我将 16 位 wav 文件数据左移 16 位(例如 0x1234 à 0x1234000)。 我还使用调试器(一直到 DMA 缓冲器到 SAI 外设)进行了验证。
  • 我检查了我的耳机、它在我的笔记本电脑 (L+R) 上播放音频
  • 我按照预期检查了 CLK_DET_STS0 寄存器、PASI_SAMP_RATE_STS = 20
  • CLK_ERR_STS0/CLK_ERR_STS1 寄存器均为 0
  • DEV_STS0 寄存器为 0x0C、因此 DAC CH1 / CH2 上电
  • DEV_STS1 寄存器为 0xF0、因此器件处于工作模式、播放开启
  • 我检查了音频插孔的连接。 如果我直接测量耳机、每通道大约为 80 欧姆。 I 测量 OUT1M / OUT1P 和 OUT2M / OUT2P 之间的相同电阻
  • 我添加了另一个 0.5s WAV 音频文件与简单的 1kHz 正弦波。 现在两个 L+R 通道上都有失真的蜂鸣声、无论选择左声道还是右声道都没有区别。 如果我选择立体声与此文件我只得到一个弹出

希望您能帮助我朝着正确的方向前进。 我有感觉,我是接近的解决方案。

提前感谢、

 

Robin

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    嗨、Robin、

    我了解了您提供的原理图和寄存器、没有发现任何即时问题。 我没有看到任何有关 BCLK 值的信息。

    时隙宽度由 b/w BCLK 和 WCLK 关系决定、 如下所示:

    BCLK =通道数 *通道 /时隙 深度 * FS

    在目标模式下、 当同时提供 BCLK 和 WCLK 时、这些位的除法 将决定时隙宽度。 因此、请验证您的时钟方案和位长度是否一致。

    还请检查 PASI_CFG0 寄存器。

    此外、PASI_RX_CFG0=0x01、您是否也可以尝试 0x00?

    请 向 DAC 发送简单的 1KHz 信号并监控引脚处的输出、以确保模拟输出和 VCOM 在那里、并 按预期消除耳机及其连接的任何问题

    关于建议;

    • 我通常向 I2S 线路添加 22 至 100 欧姆串联电阻器(不过,这不会解决您描述的问题)
    • 我还更喜欢通过一个连接到 GND 的电容器将未使用的模拟输入接地

    如果您无法解决  问题、请在一个窗口中向我发送 I2S 线路的屏幕截图和放大版本、以便我可以看到各种 CLKS WRT LRCLK 的边缘(请参阅图 6-6)  

    此致、

    Arash

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Arash:

    我检查了我的 BCLK,它是~2.82MHz :

    正如预期的那样、2 通道* 32 位* 44100Hz = 2.822MHz。 我确实看到侧面出现了较大的尖峰、因此您建议使用串联电阻来通过 EMC 测试。 下面是我的逻辑分析仪的屏幕截图:



    我的逻辑分析仪似乎正确解释了数据。 我尝试了您的建议、将 PASI_RX_CFG0 设置为 0。 现在我听到了一个很好的 1kHz 蜂鸣声。 在我的逻辑分析仪上、我可以清楚地看到 1 个时钟偏移、因此我想我并不完全理解数据表。 配置 I2S 时、TAD5112 会自动设置 1 时钟偏移吗?  

    因此、我更进一步、但我在左右两侧都听到了 1kHz 的蜂鸣声。 我仅将音频发送到左声道(如上面的逻辑分析仪图所示)。 我尝试使用 PASI_RX_CH2_CFG、但没有成功。 我尝试了设置 0x21、0x30、0x31、但所有这些设置都具有类似的输出

    第二个问题是音频文件末尾的小弹出窗口。 如何抑制它?

    第三个问题是插孔检测无法按预期工作。 我从 JACK_Detect_CFG3 读取 0x70、带和不带耳机。

    谢谢、

    Robin

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    对上述帖子的小幅更新:  
    似乎 DAC 内部音频的内部路由配置错误。 我尝试了以下方法:
    使用立体数据、因此 I2S 上的两个 L+R 通道具有相同的数据。 我尝试通过修改我的 SetVolume 功能将左/右声道静音:  


    bool TAD5112::SetVolume(uint8_t volumePercent, bool muteLeft, bool muteRight) {
        // Datasheet: +27dB to -100.0dB. 0.5dB steps.
    
    	// 1. Input Validation: Clamp the input to the valid 0-100 range
    	if (volumePercent > 100) {
    		volumePercent = 100;
    	}
    
    	uint8_t registerValue = 0;
    
    	if(volumePercent == 0) {
    		//mute
    		registerValue = 0;
    	} else {
    		_volume = volumePercent;
    		// Input range: [1, 100] (span of 99 steps)
    		// Output range: [1, 255] (span of 254 steps)
    
    		// Calculation: 1 + (Percent * 200 / 100)
    		int32_t outputNormalized = (volumePercent * 200) / 100;
    		registerValue = static_cast<uint8_t>(outputNormalized + 1);
    	}
    
        // 3. Select Page 0
        if (!SelectPage(0)) return false;
    
        // 4. Write to the correct register(s)
        bool success = true;
        success &= WriteRegister(REG_P0_DAC_CH1A_CFG0, muteLeft ? 0 : registerValue);
        success &= WriteRegister(REG_P0_DAC_CH2A_CFG0, muteRight ? 0 : registerValue);
    
        return success;
    }

    我现在只在左声道获得音频、右侧只有一个砰砰声。 当我选择其他 WAV 文件之一时、我只能听到一个弹出窗口。 文件之间的区别是我的其他文件更短 (250ms)、1kHz 正弦为 500ms。 我的原始 wav 文件是 32 位、并通过 python 脚本转换成 16 位。 但是、如果我在十六进制编辑器中查看数据并将其与代码中的 wav 文件数组进行比较、它们看起来是类似的。 我附上了一个文件:e2e.ti.com/.../beep_5F00_1.wav

     阿拉什·洛洛伊 对此有什么想法?  

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    嗨、Robin、

    您报告的数据在一个信道上、但您在两个信道上听到数据 的原始问题指向一个配置路由  、该路由告诉设备在两个信道上路由和播放信号。  

     在许多 数据转换器中,流行噪声是一种常见现象, 发生 在上电/断电时或出现时钟问题或 CLKS (I2S ) 变化时。 由于在这种情况下砰砰声不是来自上电/断电活动、因此我认为您不能通过 器件中用于砰砰声抑制的特定寄存器来解决该问题。 相反,你必须修复源文件或在弹出之前将设备静音(如果可能)。

    如果你可以播放持续正弦波,例如 1KHz,没有任何问题,那么 该器件就已设置并准备就绪。 经过验证后、我会认为    音频 文件可能是罪魁祸首。

    此致、

    Arash

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Arash:

    我刚在其中一个 wav 文件的开头添加了 200 毫秒的静音、现在它可以播放。 是否必须等待一段时间、直到设备准备好接收音频? 是否有一个寄存器可以用于检查器件是否就绪? 以及哪些寄存器会影响音频播放的开始。 我尝试禁用动态上电/断电、但这没有任何作用

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Arash:  

    另一个问题。 由于我现在有立体声播放工作正常,使用以下设置:

    if (!WriteRegister(REG_P0_PASI_RX_CH1_CFG, 0x20)) return false; //ASI channel 1 = DAC channel 1, I2S left slot 0
    if (!WriteRegister(REG_P0_PASI_RX_CH2_CFG, 0x30)) return false; //ASI channel 2 = DAC channel 2, I2S right slot 0

    我想通过使左声道或右声道静音来实现左声道/右声道交替。 我按如下方式修改了 SetVolume 函数:
     

    bool TAD5112::SetVolume(uint8_t volumePercent, bool muteLeft, bool muteRight) {
        // Datasheet: +27dB to -100.0dB. 0.5dB steps.
    
    	// 1. Input Validation: Clamp the input to the valid 0-100 range
    	if (volumePercent > 100) {
    		volumePercent = 100;
    	}
    
    	uint8_t registerValue = 0;
    
    	if(volumePercent == 0) {
    		//mute
    		registerValue = 0;
    	} else {
    		_volume = volumePercent;
    		// Input range: [1, 100] (span of 99 steps)
    		// Output range: [1, 255] (span of 254 steps)
    
    		// Calculation: 1 + (Percent * 200 / 100)
    		int32_t outputNormalized = (volumePercent * 200) / 100;
    		registerValue = static_cast<uint8_t>(outputNormalized + 1);
    	}
    
        // 3. Select Page 0
        if (!SelectPage(0)) return false;
    
        // 4. Write to the correct register(s)
        bool success = true;
        success &= WriteRegister(REG_P0_DAC_CH1A_CFG0, muteLeft ? 0 : registerValue);
        success &= WriteRegister(REG_P0_DAC_CH1B_CFG0, muteLeft ? 0 : registerValue);
        success &= WriteRegister(REG_P0_DAC_CH2A_CFG0, muteRight ? 0 : registerValue);
        success &= WriteRegister(REG_P0_DAC_CH2B_CFG0, muteRight ? 0 : registerValue);
    
        return success;
    }

    即使我将一个通道静音、它仍然可以播放立体声。 对此有何看法?  

    谢谢、

    Robin

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    根据您的说明、当您播放音调或 复位周期尚未 完成时、DAC 似乎尚未就绪、因此器件未就绪。 有一个寄存器会对 上电 延迟产生影响:

    寄存器 MISC_CFG0 寄存器 (0x7) 设置上电延迟  、包括位 5 (DAC_DLYD_PWRUP_TIME)   和位 4 DAC_DLYD_PWRUP  (可打开或关闭延迟方案)。  

    如果你播放一个立体声,静音一个频道,但仍然听到它,这意味着你不是真的静音它。所以我的建议是放置一些“阅读“命令,以确保它是静音的,就像你想的一样。 例如、在以下命令中:

    30 09 3C  

    R 30 09 01.

    因此,  我希望寄存器 09 读取 3C ,因为我在其中写了 3C。 因此、 在不同的位置放置一些读取以确认写入、并且写入后不会重新编程。

    此致、

    Arash

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Arash:

    我没有写入 MISC-CFG0、因此我想它已经处于复位状态。 当然、我在 INIT 写入 0x00。

    我还 在 Init 中添加了 DSP_CFG0 和 DSP_CFG1 以禁用音量斜坡。 我仍然需要在 wav 文件的开头保持最少 100 毫秒的静音、因此不幸的是、这不能解决我的问题。  

    我尝试了您的读回建议、因此我按如下方式修改了 WriteRegister 函数(复位寄存器有一个迂回):  

    bool TAD5112::WriteRegister(uint8_t reg, uint8_t value) {
    	uint8_t readback;
        // Use the I2CInterface to write 1 byte (value) to the 8-bit register (reg)
        bool success = _i2c.writeRegister(_address, reg, &value, 1, I2C_TIMEOUT_MS);
        _i2c.readRegister(_address, reg, &readback, 1, I2C_TIMEOUT_MS);
    
        if(reg == 1) return success;
        return success && readback == value;
    }

    初始化仍然可以正常工作、因此我想对寄存器进行编程是按预期工作的。 我也从上面的文章监控了我的 SetVolume 函数、但它返回 TRUE、因此寄存器被正确编程。 我可以设置音频的音量、也可以使用 SetVolume 功能。  

    我会在会话期间使 DAC 保持通电状态。 我的用例:  

    1. 将左声道设为静音、将右设为配置的音量
    2. 播放 WAV 文件(350ms -> 100ms 静音+音频)
    3. 左右静音
    4. 等待 2 秒钟
    5. 将右声道设为静音、将左设为配置的音量
    6. 播放 WAV 文件(350ms -> 100ms 静音+音频)
    7. 左右静音

    除了使通道静音外、我还尝试修改 I2S 数据以使通道静音、但这也会在两个通道上产生音频:

            // Place the 32-bit sample directly into the 32-bit buffer slots
            switch (_currentChannelMode) {
                case AudioChannelMode::LeftOnly:
                    buffer[i * 2] = sample_32bit_slot; // Left Channel
                    buffer[i * 2 + 1] = 0;             // Right Channel (Muted)
                    break;
                case AudioChannelMode::RightOnly:
                    buffer[i * 2] = 0;                 // Left Channel (Muted)
                    buffer[i * 2 + 1] = sample_32bit_slot; // Right Channel
                    break;
                case AudioChannelMode::Stereo:
                default:
                    buffer[i * 2] = sample_32bit_slot; // Left Channel
                    buffer[i * 2 + 1] = sample_32bit_slot; // Right Channel
                    break;
            }
            samples_loaded++;

    这似乎 DAC 的内部音频布线不正确、但如果我查看我的配置、则无法看到失配的位置:  

    bool TAD5112::Init(void) {
        // Check if device is ready
        if (!_i2c.isDeviceReady(_address, 3, I2C_TIMEOUT_MS)) {
            return false;
        }
        _currentPage = 0xFF; // Reset page cache
    
        // Perform a software reset
        if (!SelectPage(0)) return false;
        if (!WriteRegister(REG_RESET, 0x01)) { // Write 0x01 to Reset register
            return false;
        }
        Utils::DelayMs(10); // Wait for reset to complete (datasheet recommends 10ms)
    
        if (!WriteRegister(REG_P0_DEV_MISC_CFG, 0x09)) return false; // Disable sleep mode
        Utils::DelayMs(2);
        if (!WriteRegister(REG_P0_PASI_CFG0, 0x70)) return false; //Select I2S communication, 32bit words
        if (!WriteRegister(REG_P0_PASI_RX_CFG0, 0x00)) return false; //Set 1 clock offset in I2S communication
        if (!WriteRegister(REG_P0_PASI_RX_CH1_CFG, 0x20)) return false; //ASI channel 1 = DAC channel 1, I2S left slot 0
        if (!WriteRegister(REG_P0_PASI_RX_CH2_CFG, 0x30)) return false; //ASI channel 2 = DAC channel 2, I2S right slot 0
        if (!WriteRegister(REG_P0_OUT1x_CFG0, 0x34)) return false; //OUT1 to input from DAC, pseudo differential mode
        if (!WriteRegister(REG_P0_OUT1x_CFG1, 0x60)) return false; //OUT1P headphone mode, 0dB gain
        if (!WriteRegister(REG_P0_OUT1x_CFG2, 0x60)) return false; //OUT1M headphone mode
        if (!WriteRegister(REG_P0_OUT2x_CFG0, 0x30)) return false; // 0b00110010 OUT2 to input from DAC, pseudo differential mode
        if (!WriteRegister(REG_P0_OUT2x_CFG1, 0x60)) return false; //OUT2P headphone mode, 0dB gain
        if (!WriteRegister(REG_P0_OUT2x_CFG2, 0x60)) return false; //OUT2M headphone mode
        if (!WriteRegister(REG_P0_CH_EN, 0x0C)) return false; // enable DAC channels 1 & 2
        if (!WriteRegister(REG_P0_DSP_CFG0, 0x1A)) return false; // disable volume ramping
        if (!WriteRegister(REG_P0_DSP_CFG1, 0x1A)) return false; // disable volume ramping
        if (!WriteRegister(REG_P0_MISC_CFG0, 0x00)) return false; // disable power up delay
        if (!WriteRegister(REG_P0_DYN_PUPD_CFG, 0x20)) return false; // enable DAC dynamic power up & down
        if (!WriteRegister(REG_P0_PWR_CFG, 0x40)) return false; // power up DAC;
    
        // --- Configure Page 1 (Power and Analog Outputs) ---
        if (!SelectPage(1)) return false;
    
        if (!WriteRegister(REG_P1_JACK_DET_CFG1, 0x0E)) return false; // headset detection enabled, 2x current, DC-coupled
        if (!WriteRegister(REG_P1_JACK_DET_CFG2, 0x40)) return false; // debounce connect 3 detections, detection time 16ms, debounce removal 5 detections
    
        // Set default volume (0-100%)
        _volume = 50;
        SetVolume(_volume, true, true);
    
        _isInitialized = true;
        return true;
    }


  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    嗨、Robin、

    我对 该寄存器 的理解是、当 DAC_DLYD_PWRUP 被禁用(默认)时、   DAC 上电 的延迟为 64-120m、激活该位后、您可以 通过写入 DAC_DLYD_PWRUP_TIME 位来选择默认延迟或具有更长的延迟。 因此、如果  MISC_CFG0 中的所有位都处于默认值、则 DAC 上电应该有 64m 至 120m 的延迟、 因此 音频文件中所需的 100ms 延迟是合理的。

    我检查了上述 代码、也没有看到任何问题、除非我们都缺少一些东西。 如果您想向 我发送您拥有的寄存器的完整表(如果有上述内容)、我会检查是否有任何与您的预期配置冲突的内容、但从上面看我没有看到任何问题。

    此致、

    Arash

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Arash:

    如果没有任何寄存器来缩短该延迟、我可以在固件中通过 I2S 推零来解决该延迟。 我刚刚测试了这个概念,并能够消除沉默。 此外,在 wav 文件的结尾的弹出现在已经消失了。 最好的是,左右交替也是有效的。 显然、在启动延迟时间中使通道静音并不能正常工作。  

    谢谢!  

    Robin

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Arash:

    还有一个问题。 我仍然有耳机插孔检测功能的问题。 我有以下功能用于检测耳机:

    bool TAD5112::HeadphoneDetected(void) {
    	// 1. Select Page 1
    	if (!SelectPage(1)) return false;
    
    	uint8_t value;
    	if(!ReadRegister(REG_P1_JACK_DET_CFG3, value)) return false;
    
    	if((value & 0xC0) != 0) { //ignore mic detection
    		return true;
    	}
    
    	return false;
    }

    如果我在函数中设置了断点、则值始终为 0x70、这对于我使用的耳机来说是正确的(没有麦克风的立体声)、但如果我移除耳机、其读数仍为 0x70。 如果 I 停止音频播放(停止 I2S 流式传输)、则该值保持为 0x70、无论是否使用耳机。 用于检测的 init 在这里:

    // --- Configure Page 1 (Power and Analog Outputs) ---
        if (!SelectPage(1)) return false;
    
        if (!WriteRegister(REG_P1_JACK_DET_CFG1, 0x0E)) return false; // headset detection enabled, 2x current, DC-coupled
        if (!WriteRegister(REG_P1_JACK_DET_CFG2, 0x40)) return false; // debounce connect 3 detections, detection time 16ms, debounce removal 5 detections

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    你好罗宾,这是很好的听到!

    我可以查看用于检测的寄存器。  SJ3-350114B 是一个带 尖端开关的音频插孔。 我将检查开关是否在有或没有 HP 的情况下卡在同一位置。 您可以探测针脚、查看插上或拔下针脚时是否有任何区别。  

    此外,请尝试 CFG1 和 CFG2 的默认设置,并查看是否有任何差异。

    此致、

    Arash

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Arash:

    • 我测量了 OUT1M / OUT2M 上的电压。 使用耳机时、可获得 VCOM (0.65V)、没有 0
    • 我尝试了默认寄存器设置。 JACK_DET_CFG3 始终返回 0x00、带或不带耳机(默认情况下,在寄存器 JACK_DET_CFG1 中禁用插孔检测,因此这并不奇怪)
    • 我通过将 0x02 写入 JACK_DET_CFG1 来启用插孔检测、 JACK_DET_CFG3 读取 0x40、无论是否使用耳机  
    • 我尝试按照应用手册 slaaeg7 中的建议将 VCOM 设置为 AVDD/2、但读数仍为 0x40
    • 我尝试将 HPDET_CLOCK_SEL 设置为 4ms、但仍为 0x40
    • 我尝试将 HPDET_Coupling 设置为直流。在这种设置下、我在 CFG3 寄存器中看到了一些变化:
      • 从微控制器启动开始、未插入插孔= 0x50
      • 从微控制器启动时、插入插孔、无耳机= 0x40
      • 从微控制器启动时、插入插孔、耳机= 0x40
    • 我尝试将 HPDET_USE_2x_CURR 设置为 2 倍电流。 在这种设置下、CFG3 寄存器中几乎没有变化:
      • 从微控制器启动开始、插孔未插入= 0x10(先读取,后读取为 0x50)
      • 从微控制器启动时、插入插孔、无耳机= 0x00(第一次读取,第二次读取 0x40)
      • 从微控制器引导、插入插孔、耳机= 0x70

    我在没有播放音频的情况下执行了这些测试。 看起来它确实检测到了某些东西,只有在前两次读取后值不再发生变化,有或没有耳机。

    基于上述结果、我实施了一个解决方案。 我现在有了某种工作方式、但感觉不像是一个合适的解决方案:  

    bool TAD5112::HeadphoneDetected(void) {
    	uint8_t value;
    	// 1. Select Page 1
    	if (!SelectPage(1)) return false;
    
    	WriteRegister(REG_P1_JACK_DET_CFG1, 0x0E);
    	Utils::DelayMs(75);
    
    	if(!ReadRegister(REG_P1_JACK_DET_CFG3, value)) return false;
    
    	if((value & 0x70) == 0x70) { //ignore mic detection
    		WriteRegister(REG_P1_JACK_DET_CFG1, 0x00);
    		return true;
    	}
    
    	WriteRegister(REG_P1_JACK_DET_CFG1, 0x00);
    	return false;
    }

    我   从 INIT 中删除了 JACK_DET_CFG0/JACK_DET_CFG1/JACK_DET_CFG2 的配置、我获得了不带耳机的 0x00 和带耳机的 0x70。 这是正确的,我使用的立体声耳机不带麦克风。 需要延迟、否则始终读为 0x00。 是否有其他方法可以重置检测? 我不喜欢冻结我的线程 75 毫秒

    谢谢、  

    Robin

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    嗨、Robin、  

    通过 读取 0x00 和 0x70、检测机制 正常工作、 我只能想到延迟。 我知道这不是您的最佳解决方案、但我不能想到任何其他问题。

    此致、

    Arash

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    感谢阿拉什的帮助,感谢!

    我可以采用这个延迟解决方案、但我对该功能在内部的工作原理很好奇。 是否是寄存器 JACK_DET_CFG1 中的一次性触发器? 在我的经验中、它肯定是这样的。 数据表可以更清楚地说明这一点。 它表示它连续处于活动状态

    谢谢、

    Robin

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    你最受欢迎的罗宾。

    如果没有内部原理图、我猜是一次性触发器。 我将传达您的建议、以便 在下一次 DS 更新中添加更多解释。

    此致、

    Arash