【问题标题】:Change program's volume on Win 7在 Win 7 上更改程序的音量
【发布时间】:2012-04-23 17:00:58
【问题描述】:

我想更改程序的音量(而不是 音量)。我现在有以下代码:

DllImport("winmm.dll")]
public static extern int waveOutGetVolume(IntPtr hwo, out uint dwVolume);

[DllImport("winmm.dll")]
public static extern int waveOutSetVolume(IntPtr hwo, uint dwVolume);

private void volumeBar_Scroll(object sender, EventArgs e)
{
    // Calculate the volume that's being set
    int NewVolume = ((ushort.MaxValue / 10) * volumeBar.Value);
    // Set the same volume for both the left and the right channels
    uint NewVolumeAllChannels = (((uint)NewVolume & 0x0000ffff) | ((uint)NewVolume << 16));
    // Set the volume
    waveOutSetVolume(IntPtr.Zero, NewVolumeAllChannels);
}

这仅适用于 Win XP,不适用于 Windows 7(可能也适用于 Vista)。我没有找到任何可以在 Win 7 上实现相同功能的脚本,只是为了更改主音量(我不在之后)。

【问题讨论】:

    标签: c# pinvoke winmm


    【解决方案1】:

    您的代码对我来说运行良好(经过一些调整)。这是在 Windows 7 x64 上运行的非常简单的 WPF 测试应用程序的代码:

    Xaml

    <Window x:Class="WpfApplication1.MainWindow"
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
            Title="MainWindow" Height="350" Width="525">
        <Grid>
            <Slider Minimum="0" Maximum="10" ValueChanged="ValueChanged"/>
        </Grid>
    </Window>
    

    C#

    public partial class MainWindow
    {
        public MainWindow()
        {
            InitializeComponent();
        }
    
        private void ValueChanged(object sender, RoutedPropertyChangedEventArgs<double> e)
        {
            // Calculate the volume that's being set
            double newVolume = ushort.MaxValue * e.NewValue / 10.0;
    
            uint v = ((uint) newVolume) & 0xffff;
            uint vAll = v | (v << 16);
    
            // Set the volume
            int retVal = NativeMethods.WaveOutSetVolume(IntPtr.Zero, vAll);
    
            Debug.WriteLine(retVal);
    
            bool playRetVal = NativeMethods.PlaySound("tada.wav", IntPtr.Zero, 0x2001);
    
            Debug.WriteLine(playRetVal);
        }
    }
    
    static class NativeMethods
    {
        [DllImport("winmm.dll", EntryPoint = "waveOutSetVolume")]
        public static extern int WaveOutSetVolume(IntPtr hwo, uint dwVolume);
    
        [DllImport("winmm.dll", SetLastError = true)]
        public static extern bool PlaySound(string pszSound, IntPtr hmod, uint fdwSound);
    }
    

    当我启动应用程序并移动滑块时,“音量混合器”中会出现一个额外的音量控件,它与滑块同步地从最小值移动到最大值。

    您应该检查 waveOutSetVolume 的返回值。如果您的代码仍然无法运行,它可能会为您提供线索。

    【讨论】:

    • 我正在使用这个代码:pastebin.com/RcRjfBu4 但是调试给了我0。音量也没有变化。
    • Retval=0 表示成功,所以没有运气。正如我所说,它对我有用。我假设你有 Win7 SP1。我还安装了 VS11 测试版——它可能已经修复了一些问题。
    • 好的,我可以确认它正在工作(虽然只有一半)。滑动滑块时,我确实看到了音量的变化(仅在视觉上)——看看dl.dropbox.com/u/6166898/slider.png。但是音量没有改变!当我手动滑动 Windows 音量滑块时,它确实发生了变化,但不是来自程序内部。我在这里错过了什么吗?
    • 我尝试播放 Windows .wav。为我工作。音量按预期变化。
    • 嗯。可能是因为我使用的是 WebBrowser 对象吗?它再次在 XP 中运行良好。然而这个奇怪的问题(即滑块下降但声音没有,但手动滑动确实)没有意义。
    【解决方案2】:

    您可以使用音频会话 API IAudioVolume 和 IAudioSessionNotification 来修改当前应用的音量,并使用应用中的音量滑块跟踪您的音量。

    您可以在Larry Osterman's blog article中找到它们的使用示例列表

    最容易使用的是ISimpleVolume 接口。 Larry's blog 也有讨论。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-09-09
      • 2012-06-15
      • 1970-01-01
      • 1970-01-01
      • 2013-01-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多