Operaciones de Windows (C++/CLI)

Muestra varias tareas Windows específicas de la aplicación mediante el SDK Windows.

En los temas siguientes se muestran Windows operaciones realizadas con el SDK de Windows mediante Visual C++.

Determinar si se ha iniciado el apagado

En el ejemplo de código siguiente se muestra cómo determinar si la aplicación o el .NET Framework está finalizando actualmente. Esto es útil para tener acceso a elementos estáticos en el .NET Framework porque, durante el apagado, el sistema ha finalizado estas construcciones y no se pueden usar de forma confiable. Al comprobar primero la propiedad HasShutdownStarted, puede evitar posibles errores si no tiene acceso a estos elementos.

Ejemplo

// check_shutdown.cpp
// compile with: /clr
using namespace System;
int main()
{
   if (Environment::HasShutdownStarted)
      Console::WriteLine("Shutting down.");
   else
      Console::WriteLine("Not shutting down.");
   return 0;
}

Determinar el estado interactivo del usuario

En el ejemplo de código siguiente se muestra cómo determinar si el código se ejecuta en un contexto interactivo del usuario. Si UserInteractive es false, el código se ejecuta como un proceso de servicio o desde dentro de una aplicación web, en cuyo caso no debe intentar interactuar con el usuario.

Ejemplo

// user_interactive.cpp
// compile with: /clr
using namespace System;

int main()
{
   if ( Environment::UserInteractive )
      Console::WriteLine("User interactive");
   else
      Console::WriteLine("Noninteractive");
   return 0;
}

Leer datos del registro Windows datos

En el ejemplo de código siguiente se usa la clave CurrentUser para leer datos del Windows registro. En primer lugar, las subclaves se enumeran mediante el método GetSubKeyNames y, a continuación, la subclave Identities se abre mediante el método OpenSubKey. Al igual que las claves raíz, cada subclave se representa mediante la clase RegistryKey. Por último, el nuevo objeto RegistryKey se usa para enumerar los pares clave-valor.

Ejemplo

// registry_read.cpp
// compile with: /clr
using namespace System;
using namespace Microsoft::Win32;

int main( )
{
   array<String^>^ key = Registry::CurrentUser->GetSubKeyNames( );

   Console::WriteLine("Subkeys within CurrentUser root key:");
   for (int i=0; i<key->Length; i++)
   {
      Console::WriteLine("   {0}", key[i]);
   }

   Console::WriteLine("Opening subkey 'Identities'...");
   RegistryKey^ rk = nullptr;
   rk = Registry::CurrentUser->OpenSubKey("Identities");
   if (rk==nullptr)
   {
      Console::WriteLine("Registry key not found - aborting");
      return -1;
   }

   Console::WriteLine("Key/value pairs within 'Identities' key:");
   array<String^>^ name = rk->GetValueNames( );
   for (int i=0; i<name->Length; i++)
   {
      String^ value = rk->GetValue(name[i])->ToString();
      Console::WriteLine("   {0} = {1}", name[i], value);
   }

   return 0;
}

Comentarios

La clase Registry es simplemente un contenedor para instancias estáticas de RegistryKey. Cada instancia representa un nodo de Registro raíz. Las instancias son ClassesRoot,CurrentConfig,CurrentUser,LocalMachiney Users.

Además de ser estáticos, los objetos de la clase Registry son de solo lectura. Además, las instancias de la clase RegistryKey que se crean para tener acceso al contenido de los objetos del Registro también son de solo lectura. Para obtener un ejemplo de cómo invalidar este comportamiento, vea Cómo: Escribir datos en Windows Registry (C++/CLI).

Hay dos objetos adicionales en la clase Registry:DynData y PerformanceData. Ambos son instancias de la clase RegistryKey. El objeto DynData contiene información dinámica del Registro, que solo se admite en Windows 98 y Windows Me. El objeto PerformanceData se puede usar para acceder a la información del contador de rendimiento de las aplicaciones que usan el Windows supervisión del rendimiento. El nodo PerformanceData representa información que no se almacena realmente en el Registro y, por tanto, no se puede ver mediante Regedit.exe.

Leer Windows contadores de rendimiento

Algunas aplicaciones y subsistemas Windows rendimiento exponen datos de rendimiento a través del Windows de rendimiento. Se puede acceder a estos contadores mediante las clases PerformanceCounterCategory y PerformanceCounter, que residen en el espacio de nombres System.Diagnostics.

En el ejemplo de código siguiente se usan estas clases para recuperar y mostrar un contador actualizado por Windows para indicar el porcentaje de tiempo que el procesador está ocupado.

Nota

Este ejemplo exige privilegios administrativos para ejecutarse en Windows Vista.

Ejemplo

// processor_timer.cpp
// compile with: /clr
#using <system.dll>

using namespace System;
using namespace System::Threading;
using namespace System::Diagnostics;
using namespace System::Timers;

ref struct TimerObject
{
public:
   static String^ m_instanceName;
   static PerformanceCounter^ m_theCounter;

public:
   static void OnTimer(Object^ source, ElapsedEventArgs^ e)
   {
      try
      {
         Console::WriteLine("CPU time used: {0,6} ",
          m_theCounter->NextValue( ).ToString("f"));
      }
      catch(Exception^ e)
      {
         if (dynamic_cast<InvalidOperationException^>(e))
         {
            Console::WriteLine("Instance '{0}' does not exist",
                  m_instanceName);
            return;
         }
         else
         {
            Console::WriteLine("Unknown exception... ('q' to quit)");
            return;
         }
      }
   }
};

int main()
{
   String^ objectName = "Processor";
   String^ counterName = "% Processor Time";
   String^ instanceName = "_Total";

   try
   {
      if ( !PerformanceCounterCategory::Exists(objectName) )
      {
         Console::WriteLine("Object {0} does not exist", objectName);
         return -1;
      }
   }
   catch (UnauthorizedAccessException ^ex)
   {
      Console::WriteLine("You are not authorized to access this information.");
      Console::Write("If you are using Windows Vista, run the application with ");
      Console::WriteLine("administrative privileges.");
      Console::WriteLine(ex->Message);
      return -1;
   }

   if ( !PerformanceCounterCategory::CounterExists(
          counterName, objectName) )
   {
      Console::WriteLine("Counter {0} does not exist", counterName);
      return -1;
   }

   TimerObject::m_instanceName = instanceName;
   TimerObject::m_theCounter = gcnew PerformanceCounter(
          objectName, counterName, instanceName);

   System::Timers::Timer^ aTimer = gcnew System::Timers::Timer();
   aTimer->Elapsed += gcnew ElapsedEventHandler(&TimerObject::OnTimer);
   aTimer->Interval = 1000;
   aTimer->Enabled = true;
   aTimer->AutoReset = true;

   Console::WriteLine("reporting CPU usage for the next 10 seconds");
   Thread::Sleep(10000);
   return 0;
}

Recuperar texto del Portapapeles

En el ejemplo de código siguiente se usa la función miembro GetDataObject para devolver un puntero a la interfaz IDataObject. A continuación, se puede consultar esta interfaz para obtener el formato de los datos y usarse para recuperar los datos reales.

Ejemplo

// read_clipboard.cpp
// compile with: /clr
#using <system.dll>
#using <system.Drawing.dll>
#using <system.windows.forms.dll>

using namespace System;
using namespace System::Windows::Forms;

[STAThread] int main( )
{
   IDataObject^ data = Clipboard::GetDataObject( );

   if (data)
   {
      if (data->GetDataPresent(DataFormats::Text))
      {
         String^ text = static_cast<String^>
           (data->GetData(DataFormats::Text));
         Console::WriteLine(text);
      }
      else
         Console::WriteLine("Nontext data is in the Clipboard.");
   }
   else
   {
      Console::WriteLine("No data was found in the Clipboard.");
   }

   return 0;
}

Recuperación del nombre de usuario actual

En el ejemplo de código siguiente se muestra la recuperación del nombre de usuario actual (el nombre del usuario que ha iniciado sesión Windows). El nombre se almacena en la cadena UserName, que se define en el espacio de nombres Environment.

Ejemplo

// username.cpp
// compile with: /clr
using namespace System;

int main()
{
   Console::WriteLine("\nCurrent user: {0}", Environment::UserName);
   return 0;
}

Recuperación de .NET Framework versión

En el ejemplo de código siguiente se muestra cómo determinar la versión del .NET Framework instalada actualmente con la propiedad Version, que es un puntero a un objeto Version que contiene la información de versión.

Ejemplo

// dotnet_ver.cpp
// compile with: /clr
using namespace System;
int main()
{
   Version^ version = Environment::Version;
   if (version)
   {
      int build = version->Build;
      int major = version->Major;
      int minor = version->Minor;
      int revision = Environment::Version->Revision;
      Console::Write(".NET Framework version: ");
      Console::WriteLine("{0}.{1}.{2}.{3}",
            build, major, minor, revision);
   }
   return 0;
}

Recuperación del nombre de la máquina local

En el ejemplo de código siguiente se muestra la recuperación del nombre del equipo local (el nombre del equipo tal como aparece en una red). Para ello, puede obtener la cadena MachineName, que se define en el espacio de nombres Environment.

Ejemplo

// machine_name.cpp
// compile with: /clr
using namespace System;

int main()
{
   Console::WriteLine("\nMachineName: {0}", Environment::MachineName);
   return 0;
}

Recuperación de Windows versión

En el ejemplo de código siguiente se muestra cómo recuperar la información de plataforma y versión del sistema operativo actual. Esta información se almacena en la propiedad System.Environment.OSVersion y consta de una enumeración que describe la versión de Windows en términos generales y un objeto Version que contiene la compilación exacta del sistema operativo.

Ejemplo

// os_ver.cpp
// compile with: /clr
using namespace System;

int main()
{
   OperatingSystem^ osv = Environment::OSVersion;
   PlatformID id = osv->Platform;
   Console::Write("Operating system: ");

   if (id == PlatformID::Win32NT)
      Console::WriteLine("Win32NT");
   else if (id == PlatformID::Win32S)
      Console::WriteLine("Win32S");
   else if (id == PlatformID::Win32Windows)
      Console::WriteLine("Win32Windows");
   else
      Console::WriteLine("WinCE");

   Version^ version = osv->Version;
   if (version)
   {
      int build = version->Build;
      int major = version->Major;
      int minor = version->Minor;
      int revision = Environment::Version->Revision;
      Console::Write("OS Version: ");
      Console::WriteLine("{0}.{1}.{2}.{3}",
                   build, major, minor, revision);
   }

   return 0;
}

Recuperar el tiempo transcurrido desde el inicio

En el ejemplo de código siguiente se muestra cómo determinar el recuento de tics o el número de milisegundos que han transcurrido desde Windows se inició. Este valor se almacena en el miembro System.Environment.TickCount y, como es un valor de 32 bits, se restablece a cero aproximadamente cada 24,9 días.

Ejemplo

// startup_time.cpp
// compile with: /clr
using namespace System;

int main( )
{
   Int32 tc = Environment::TickCount;
   Int32 seconds = tc / 1000;
   Int32 minutes = seconds / 60;
   float hours = static_cast<float>(minutes) / 60;
   float days = hours / 24;

   Console::WriteLine("Milliseconds since startup: {0}", tc);
   Console::WriteLine("Seconds since startup: {0}", seconds);
   Console::WriteLine("Minutes since startup: {0}", minutes);
   Console::WriteLine("Hours since startup: {0}", hours);
   Console::WriteLine("Days since startup: {0}", days);

   return 0;
}

Almacenar texto en el Portapapeles

En el ejemplo de código siguiente se usa el objeto Clipboard definido en System.Windows. Espacio de nombres de formularios para almacenar una cadena. Este objeto proporciona dos funciones miembro: SetDataObject y GetDataObject. Los datos se almacenan en el Portapapeles mediante el envío de cualquier objeto derivado de Object a SetDataObject.

Ejemplo

// store_clipboard.cpp
// compile with: /clr
#using <System.dll>
#using <System.Drawing.dll>
#using <System.Windows.Forms.dll>

using namespace System;
using namespace System::Windows::Forms;

[STAThread] int main()
{
   String^ str = "This text is copied into the Clipboard.";

   // Use 'true' as the second argument if
   // the data is to remain in the clipboard
   // after the program terminates.
   Clipboard::SetDataObject(str, true);

   Console::WriteLine("Added text to the Clipboard.");

   return 0;
}

Escribir datos en el registro Windows datos

En el ejemplo de código siguiente se usa la clave CurrentUser para crear una instancia grabable de la clase RegistryKey correspondiente a la clave Software. A continuación, se usa el método CreateSubKey para crear una nueva clave y agregar a pares clave-valor.

Ejemplo

// registry_write.cpp
// compile with: /clr
using namespace System;
using namespace Microsoft::Win32;

int main()
{
   // The second OpenSubKey argument indicates that
   // the subkey should be writable.
   RegistryKey^ rk;
   rk  = Registry::CurrentUser->OpenSubKey("Software", true);
   if (!rk)
   {
      Console::WriteLine("Failed to open CurrentUser/Software key");
      return -1;
   }

   RegistryKey^ nk = rk->CreateSubKey("NewRegKey");
   if (!nk)
   {
      Console::WriteLine("Failed to create 'NewRegKey'");
      return -1;
   }

   String^ newValue = "NewValue";
   try
   {
      nk->SetValue("NewKey", newValue);
      nk->SetValue("NewKey2", 44);
   }
   catch (Exception^)
   {
      Console::WriteLine("Failed to set new values in 'NewRegKey'");
      return -1;
   }

   Console::WriteLine("New key created.");
   Console::Write("Use REGEDIT.EXE to verify ");
   Console::WriteLine("'CURRENTUSER/Software/NewRegKey'\n");
   return 0;
}

Comentarios

Puede usar el .NET Framework para acceder al Registro con las clases Registry y RegistryKey, que se definen en el espacio de nombres Microsoft.Win32. La clase Registry es un contenedor para instancias estáticas de la clase RegistryKey. Cada instancia representa un nodo de Registro raíz. Las instancias son ClassesRoot,CurrentConfig,CurrentUser,LocalMachiney Users.

Entorno

Vea también

Programación de .NET con C++/CLI (Visual C++)