Click here to Skip to main content
15,881,248 members
Articles / Mobile Apps / Windows Mobile

Audio Book Player

Rate me:
Please Sign up or sign in to vote.
4.86/5 (36 votes)
11 Jun 2009CPOL6 min read 197.3K   3.5K   84  
Audio player designed specifically for listening to audio books
using System;
using System.Runtime.InteropServices;
using System.Collections.Generic;
using System.IO;
using Microsoft.Win32;
using System.Text;

// this helper class encapsulates various API calls and methods
// that work fine (after numerous trial-and-error) on my device
// (ASUS MyPal 639) but may not perform on other devices and may
// need device adaptation
public enum ePlaySoundFlags
{
    SND_ALIAS = 0x10000,
    SND_FILENAME = 0x20000,
    SND_RESOURCE = 0x40004,
    SND_SYNC = 0x0,
    SND_ASYNC = 0x1,
    SND_NODEFAULT = 0x2,
    SND_MEMORY = 0x4,
    SND_LOOP = 0x8,
    SND_NOSTOP = 0x10,
    SND_NOWAIT = 0x2000,
    SND_VALIDFLAGS = 0x17201F,
    SND_TYPE_MASK = 0x170007
};

public class cASUS639DeviceSpecifics : cBaseDeviceSpecifics
{
    // System power status structure
    [StructLayout(LayoutKind.Sequential)]
    internal struct SYSTEM_POWER_STATUS_EX
    {
        public byte ACLineStatus;
        public byte BatteryFlag;
        public byte BatteryLifePercent;
        public byte Reserved1;
        public uint BatteryLifeTime;
        public uint BatteryFullLifeTime;
        public byte Reserved2;
        public byte BackupBatteryFlag;
        public byte BackupBatteryLifePercent;
        public byte Reserved3;
        public uint BackupBatteryLifeTime;
        public uint BackupBatteryFullLifeTime;
    }

    [DllImport("coredll.dll")]
    public extern static int SetSystemPowerState(IntPtr psState, int StateFlags,
        int Options);
    [DllImport("coredll.dll")]
    public extern static int PlaySound(string szSound, IntPtr hMod, int flags);
    [DllImport("coredll")]
    public static extern int waveOutSetVolume(IntPtr hMod, int lVolume);
    [DllImport("coredll")]
    public static extern int waveOutGetVolume(IntPtr hMod, ref int lVolume);
    [DllImport("Coredll.dll")]
    internal static extern bool GetSystemPowerStatusEx(ref SYSTEM_POWER_STATUS_EX pstatus, bool fUpdate);
    [DllImport("coredll.dll")]
    public static extern void SystemIdleTimerReset();
    [DllImport("Aygshell.dll")]
    public static extern void SHIdleTimerReset();
    [DllImport("coredll.dll")]
    public static extern int SystemParametersInfo(uint uiAction,
        uint uiParam, ref uint pvParam, uint fWinIni);

    // constants
    private const int POWER_STATE_OFF = (int)(0x00020000);
    private const int POWER_FORCE = (int)(0x00001000);
    private const uint SPI_GETSCREENSAVETIMEOUT = 14;
    private const uint SPI_SETSCREENSAVEACTIVE = 17;
    // Backlight registry constants
    private const String BACKLIGHT_ROOT_KEY = "ControlPanel";
    private const String BACKLIGHT_SUB_KEY = "BackLight";
    private const String BACKLIGHT_ENTRY = "BatteryTimeout";
    private const int BACKLIGHT_DEFAULT_VALUE = 30;
    // sound related vars
    private string PLAYLIST_READY_FILE = "";
    private const String BEEP_ROOT_KEY = "ControlPanel\\Notifications\\Default";
    private const String BEEP_VALUE = "Wave";
    private const String BEEP_PATH = "\\Windows\\";
    private const String BEEP_DEFAULT_FILE = "Notify";

    // play notification beep
    public override void Beep()
    {
        string str = "";
        if (PLAYLIST_READY_FILE == "")
        {
            RegistryKey RK = null;
            try
            {
                RK = Registry.CurrentUser.OpenSubKey(BEEP_ROOT_KEY, true);
                str = (String)RK.GetValue(BEEP_VALUE,
                    BEEP_DEFAULT_FILE);
                PLAYLIST_READY_FILE = (File.Exists(BEEP_PATH + str + ".wav"))?
                    BEEP_PATH + str + ".wav": "-";

            }
            catch
            {
                PLAYLIST_READY_FILE = "-";
            }
            finally
            {
                if (RK != null) RK.Close();
            }
        }

        str = (PLAYLIST_READY_FILE == "-") ? "" : PLAYLIST_READY_FILE;
        ePlaySoundFlags flag = (str == "")? 
            ePlaySoundFlags.SND_ALIAS: ePlaySoundFlags.SND_FILENAME;
        PlaySound(str, IntPtr.Zero, (int)(ePlaySoundFlags.SND_ASYNC | flag));
    }
    // get/set the wave master volume
    // the master volume is a 2-word value representing the left and right
    // value in each word. value is between 0 and maxvalue of a word - 64k
    // we use pecentage values and convert from and to with the help of
    // functions later in this class
    // we set both the left and right parts to the same level
    public override int Volume
    {
        get
        {
            // get volume into v
            int v = 0;
            waveOutGetVolume(IntPtr.Zero, ref v);
            // convert to percentage
            return NativeVolToPercent(v);
        }
        set
        {
            // set after converting from percentage to native values
            waveOutSetVolume(IntPtr.Zero, PercentToNativeVol(value));
        }
    }
    // convert percentage to device volume values
    private int PercentToNativeVol(int percent)
    {
        int i = (int)(((0xFFFF * 1.0) * percent) / 100.0);
        return i + i * 0x10000;
    }
    // convert device volume values to percentage
    private int NativeVolToPercent(int vol)
    {
        int i = (vol & 0xFFFF);
        return (int)(i * 100.0 / (0xFFFF * 1.0));
    }
    // power and backlight functions
    public override long PowerOffThreshold
    {
        get
        {
            // get device screensave timeout 
            uint timeout = uint.MaxValue;
            SystemParametersInfo(SPI_GETSCREENSAVETIMEOUT, 0, ref timeout, 0);
            // set desired threshold
            return (timeout < 30) ? 20 : timeout - 20;
        }
    }
    // keep system runnung
    public override void PreventAutoPowerOff()
    {
        SystemIdleTimerReset();
        SHIdleTimerReset();
    }
    // get power state
    public override PowerState PowerAndBatteryState
    {
        get
        {
            SYSTEM_POWER_STATUS_EX system_power_status_ex = new SYSTEM_POWER_STATUS_EX();
            GetSystemPowerStatusEx(ref system_power_status_ex, true);
            return new PowerState((system_power_status_ex.ACLineStatus == 1),
                system_power_status_ex.BatteryLifePercent);
        }
    }
    // power off device
    public override void PowerOff()
    {
        SetSystemPowerState((IntPtr)null, POWER_STATE_OFF, POWER_FORCE);
    }
    // get/set backlight timeout
    public override int BacklightTimeout
    {
        get
        {
            int blto = 0;
            RegistryKey RK = null;
            RegistryKey SRK = null;
            try
            {
                RK = Registry.CurrentUser.OpenSubKey(BACKLIGHT_ROOT_KEY, true);
                SRK = RK.OpenSubKey(BACKLIGHT_SUB_KEY, true);
                blto = (int)SRK.GetValue(BACKLIGHT_ENTRY,
                    BACKLIGHT_DEFAULT_VALUE);
            }
            catch
            {
            }
            finally
            {
                if (SRK != null) SRK.Close();
                if (RK != null) RK.Close();
            }
            return blto;
        }
        set
        {
            RegistryKey RK = null;
            RegistryKey SRK = null;
            try
            {
                RK = Registry.CurrentUser.OpenSubKey(BACKLIGHT_ROOT_KEY, true);
                SRK = RK.OpenSubKey(BACKLIGHT_SUB_KEY, true);
                SRK.SetValue(BACKLIGHT_ENTRY, value, RegistryValueKind.DWord);
            }
            catch
            {
            }
            finally
            {
                if (SRK != null) SRK.Close();
                if (RK != null) RK.Close();
            }
        }
    }
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Israel Israel
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions