Pregunta

Cuando creo un winrt componente mediante WRL, el problema es que solo puedo utilizar ABI::Windows::xxx espacio de nombres, y no puedo usar Windows::UI::Xaml::Media::Imaging espacio de nombres en WRL.

Entonces, ¿cómo crear una acumulación en winrt componente como un retorno de valor?

// idl
import "inspectable.idl";
import "Windows.Foundation.idl";
import "Windows.UI.Xaml.Media.Imaging.idl";

namespace Decoder
{
    interface IPhotoDecoder;
    runtimeclass PhotoDecoder;

    interface IPhotoDecoder : IInspectable
    {
        HRESULT Decode([in] int width, [in] int height, [out, retval] Windows.UI.Xaml.Media.Imaging.BitmapImage **ppBitmapImage);
    }

    [version(COMPONENT_VERSION), activatable(COMPONENT_VERSION)]
    runtimeclass PhotoDecoder
    {
         [default] interface IPhotoDecoder;
    }
}

// cpp
using namespace Microsoft::WRL;
using namespace Windows::Foundation;
using namespace ABI::Windows::UI::Xaml::Media::Imaging;
namespace ABI
{
    namespace Decoder
    {
        class PhotoDecoder: public RuntimeClass<IPhotoDecoder>
        {
            InspectableClass(L"Decoder.PhotoDecoder", BaseTrust)

            public:
            PhotoDecoder()
            {
            }

            HRESULT __stdcall Decode(_In_ int width, _In_ int height, _Out_ IBitmapImage **ppBitmapImage)
            {
                // How to create Windows.UI.Xaml.Media.Imaging.BitmapImage without using Windows::UI::Xaml::Media::Imaging
            }

        };

        ActivatableClass(PhotoDecoder);
    }
}
¿Fue útil?

Solución

Hay dos conjuntos de espacios de nombres:

  • aquellas enraizadas en el espacio de nombres global (por ejemplo, Windows::Foundation)
  • los fundamentados en la ABI espacio de nombres (por ejemplo, ABI::Windows::Foundation)

El contenido de cada uno de ellos son "el mismo". Por ejemplo, Windows::Foundation::IUriRuntimeClass los nombres de la misma interfaz ABI::Windows::Foundation::IUriRuntimeClass.

Así que, ¿por qué hay dos conjuntos de espacios de nombres?los espacios de nombres arraigada en el espacio de nombres global se reserva el uso de C++/CX:genera a sus proyecciones de clases en tiempo de ejecución en los espacios de nombres.Cuando usted está utilizando WRL, siempre vas a trabajar con los espacios de nombres arraigada en la ABI espacio de nombres (que son los "no proyectados" nombres, es decir, son exactamente lo que existe en la capa ABI).

Clases en tiempo de ejecución se crea una instancia ("activado") en una de dos maneras.Si el tipo predeterminado es edificable, puede ser predeterminado construido llamando RoActivateInstance.Si un tipo se declara otros constructores, los constructores pueden ser llamados por conseguir la activación de la fábrica para el tipo en tiempo de ejecución llamando RoGetActivationFactory.Como un ejemplo, usted puede construir un defecto BitmapImage así:

using namespace Microsoft::WRL;
using namespace Microsoft::WRL::Wrappers;

using namespace ABI::Windows::UI::Xaml::Media::Imaging;

HStringReference classId(RuntimeClass_Windows_UI_Xaml_Media_Imaging_BitmapImage);

ComPtr<IInspectable> inspectable;
if (FAILED(RoActivateInstance(classId.Get(), inspectable.GetAddressOf())))
{
    // Handle failure
}

ComPtr<IBitmapImage> bitmapImage;
if (FAILED(inspectable.As(&bitmapImage)))
{
    // Handle failure
}

WRL también tiene una útil función de la plantilla, Windows::Foundation::ActivateInstance, que tanto las llamadas RoActivateInstance y realiza la QueryInterface a la meta deseada de la interfaz:

using namespace Windows::Foundation;

ComPtr<IBitmapImage> bitmapImage;
if (FAILED(ActivateInstance(classId.Get(), bitmapImage.GetAddressOf())))
{
    // Handle failure
}
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top