/*
 * Copyright 2021 Gijs Vermeulen
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */

#ifdef __WIDL__
#pragma winrt ns_prefix
#endif

import "inspectable.idl";
import "asyncinfo.idl";
import "eventtoken.idl";
import "windowscontracts.idl";
import "windows.storage.streams.idl";
import "windows.foundation.idl";

namespace Windows.Devices.Enumeration {
    typedef enum DeviceClass DeviceClass;
    typedef enum DeviceInformationKind DeviceInformationKind;
    typedef enum DeviceWatcherStatus DeviceWatcherStatus;
    typedef enum Panel Panel;
    typedef enum DeviceAccessStatus DeviceAccessStatus;

    interface IDeviceInformation;
    interface IDeviceInformationStatics;
    interface IDeviceInformationStatics2;
    interface IDeviceInformationUpdate;
    interface IEnclosureLocation;

    runtimeclass DeviceInformation;
    runtimeclass DeviceInformationCollection;
    runtimeclass DeviceInformationUpdate;
    runtimeclass DeviceThumbnail;
    runtimeclass DeviceWatcher;
    runtimeclass EnclosureLocation;
    runtimeclass DeviceAccessChangedEventArgs;
    runtimeclass DeviceAccessInformation;

    declare
    {
        interface Windows.Foundation.Collections.IVectorView<Windows.Devices.Enumeration.DeviceInformation *>;
        interface Windows.Foundation.Collections.IIterable<Windows.Devices.Enumeration.DeviceInformation *>;
        interface Windows.Foundation.Collections.IIterator<Windows.Devices.Enumeration.DeviceInformation *>;
        interface Windows.Foundation.AsyncOperationCompletedHandler<Windows.Devices.Enumeration.DeviceInformation *>;
        interface Windows.Foundation.AsyncOperationCompletedHandler<Windows.Devices.Enumeration.DeviceInformationCollection *>;
        interface Windows.Foundation.AsyncOperationCompletedHandler<Windows.Devices.Enumeration.DeviceThumbnail *>;
        interface Windows.Foundation.Collections.IMapView<HSTRING, IInspectable *>;
        interface Windows.Foundation.IAsyncOperation<Windows.Devices.Enumeration.DeviceInformation *>;
        interface Windows.Foundation.IAsyncOperation<Windows.Devices.Enumeration.DeviceInformationCollection *>;
        interface Windows.Foundation.IAsyncOperation<Windows.Devices.Enumeration.DeviceThumbnail *>;
        interface Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceWatcher *, IInspectable *>;
        interface Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceWatcher *, Windows.Devices.Enumeration.DeviceInformation *>;
        interface Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceWatcher *, Windows.Devices.Enumeration.DeviceInformationUpdate *>;
        interface Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceAccessInformation *, Windows.Devices.Enumeration.DeviceAccessChangedEventArgs *>;
    }
}

namespace Windows.Devices.Enumeration {
    [contract(Windows.Foundation.UniversalApiContract, 1.0)]
    enum DeviceClass
    {
        All                   = 0,
        AudioCapture          = 1,
        AudioRender           = 2,
        PortableStorageDevice = 3,
        VideoCapture          = 4,
        [contract(Windows.Foundation.UniversalApiContract, 1.0)]
        ImageScanner          = 5,
        [contract(Windows.Foundation.UniversalApiContract, 1.0)]
        Location              = 6,
    };

    [contract(Windows.Foundation.UniversalApiContract, 1.0)]
    enum DeviceInformationKind
    {
        Unknown                      = 0,
        DeviceInterface              = 1,
        DeviceContainer              = 2,
        Device                       = 3,
        DeviceInterfaceClass         = 4,
        AssociationEndpoint          = 5,
        AssociationEndpointContainer = 6,
        AssociationEndpointService   = 7,
        [contract(Windows.Foundation.UniversalApiContract, 7.0)]
        DevicePanel                  = 8,
    };

    enum DeviceWatcherStatus
    {
        Created              = 0,
        Started              = 1,
        EnumerationCompleted = 2,
        Stopping             = 3,
        Stopped              = 4,
        Aborted              = 5,
    };

    enum Panel
    {
        Unknown = 0,
        Front   = 1,
        Back    = 2,
        Top     = 3,
        Bottom  = 4,
        Left    = 5,
        Right   = 6,
    };

    [contract(Windows.Foundation.UniversalApiContract, 1.0)]
    enum DeviceAccessStatus
    {
        Unspecified    = 0,
        Allowed        = 1,
        DeniedByUser   = 2,
        DeniedBySystem = 3,
    };

    [
        exclusiveto(Windows.Devices.Enumeration.DeviceInformation),
        uuid(aba0fb95-4398-489d-8e44-e6130927011f)
    ]
    interface IDeviceInformation : IInspectable
    {
        [propget] HRESULT Id([out, retval] HSTRING *value);
        [propget] HRESULT Name([out, retval] HSTRING *value);
        [propget] HRESULT IsEnabled([out, retval] boolean *value);
        [propget] HRESULT IsDefault([out, retval] boolean *value);
        [propget] HRESULT EnclosureLocation([out, retval] Windows.Devices.Enumeration.EnclosureLocation **value);
        [propget] HRESULT Properties([out, retval] Windows.Foundation.Collections.IMapView<HSTRING, IInspectable *> **value);
        HRESULT Update([in] Windows.Devices.Enumeration.DeviceInformationUpdate *info);
        HRESULT GetThumbnailAsync([out, retval] Windows.Foundation.IAsyncOperation<Windows.Devices.Enumeration.DeviceThumbnail *> **operation);
        HRESULT GetGlyphThumbnailAsync([out, retval] Windows.Foundation.IAsyncOperation<Windows.Devices.Enumeration.DeviceThumbnail *> **operation);
    }

    [
        exclusiveto(Windows.Devices.Enumeration.DeviceInformationUpdate),
        uuid(8f315305-d972-44b7-a37e-9e822c78213b)
    ]
    interface IDeviceInformationUpdate : IInspectable
    {
        [propget] HRESULT Id([out, retval] HSTRING *value);
        [propget] HRESULT Properties([out, retval] Windows.Foundation.Collections.IMapView<HSTRING, IInspectable *> **value);
    }

    [
        exclusiveto(Windows.Devices.Enumeration.DeviceWatcher),
        uuid(c9eab97d-8f6b-4f96-a9f4-abc814e22271),
    ]
    interface IDeviceWatcher : IInspectable
    {
        [eventadd] HRESULT Added([in] Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceWatcher *,
                Windows.Devices.Enumeration.DeviceInformation *> *handler, [out, retval] EventRegistrationToken *token);
        [eventremove] HRESULT Added([in] EventRegistrationToken token);
        [eventadd] HRESULT Updated([in] Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceWatcher *,
                Windows.Devices.Enumeration.DeviceInformationUpdate *> *handler, [out, retval] EventRegistrationToken *token);
        [eventremove] HRESULT Updated([in] EventRegistrationToken token);
        [eventadd] HRESULT Removed([in] Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceWatcher *,
                Windows.Devices.Enumeration.DeviceInformationUpdate *> *handler, [out, retval] EventRegistrationToken *token);
        [eventremove] HRESULT Removed([in] EventRegistrationToken token);
        [eventadd] HRESULT EnumerationCompleted([in] Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceWatcher *,
                IInspectable *> *handler, [out, retval] EventRegistrationToken *token);
        [eventremove] HRESULT EnumerationCompleted([in] EventRegistrationToken token);
        [eventadd] HRESULT Stopped([in] Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceWatcher *,
                IInspectable *> *handler, [out, retval] EventRegistrationToken *token);
        [eventremove] HRESULT Stopped([in] EventRegistrationToken token);
        [propget] HRESULT Status([out, retval] Windows.Devices.Enumeration.DeviceWatcherStatus *status);
        HRESULT Start();
        HRESULT Stop();
    }

    [
        exclusiveto(Windows.Devices.Enumeration.EnclosureLocation),
        uuid(42340a27-5810-459c-aabb-c65e1f813ecf)
    ]
    interface IEnclosureLocation : IInspectable
    {
        [propget] HRESULT InDock([out, retval] boolean *value);
        [propget] HRESULT InLid([out, retval] boolean *value);
        [propget] HRESULT Panel([out, retval] Windows.Devices.Enumeration.Panel *value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.Devices.Enumeration.DeviceInformation),
        uuid(493b4f34-a84f-45fd-9167-15d1cb1bd1f9)
    ]
    interface IDeviceInformationStatics2 : IInspectable
    {
        HRESULT GetAqsFilterFromDeviceClass([in] Windows.Devices.Enumeration.DeviceClass device_class, [out, retval] HSTRING *filter);
        [overload("CreateFromIdAsync")]
        HRESULT CreateFromIdAsyncWithKindAndAdditionalProperties([in] HSTRING device_id,
                [in] Windows.Foundation.Collections.IIterable<HSTRING> *additional_properties,
                [in] Windows.Devices.Enumeration.DeviceInformationKind kind,
                [out, retval] Windows.Foundation.IAsyncOperation<Windows.Devices.Enumeration.DeviceInformation *> **async_operation);
        [overload("FindAllAsync")]
        HRESULT FindAllAsyncWithKindAqsFilterAndAdditionalProperties([in] HSTRING filter,
                [in] Windows.Foundation.Collections.IIterable<HSTRING> *additional_properties,
                [in] Windows.Devices.Enumeration.DeviceInformationKind kind,
                [out, retval] Windows.Foundation.IAsyncOperation<Windows.Devices.Enumeration.DeviceInformationCollection *> **async_operation);
        [overload("CreateWatcher")]
        HRESULT CreateWatcherWithKindAqsFilterAndAdditionalProperties([in] HSTRING filter,
                [in] Windows.Foundation.Collections.IIterable<HSTRING> *additional_properties,
                [in] Windows.Devices.Enumeration.DeviceInformationKind kind,
                [out, retval] Windows.Devices.Enumeration.DeviceWatcher **watcher);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.Devices.Enumeration.DeviceAccessChangedEventArgs),
        uuid(deda0bcc-4f9d-4f58-9dba-a9bc800408d5)
    ]
    interface IDeviceAccessChangedEventArgs : IInspectable
    {
        [propget] HRESULT Status([out, retval] Windows.Devices.Enumeration.DeviceAccessStatus *value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 3.0),
        exclusiveto(Windows.Devices.Enumeration.DeviceAccessChangedEventArgs),
        uuid(82523262-934b-4b30-a178-adc39f2f2be3)
    ]
    interface IDeviceAccessChangedEventArgs2 : IInspectable
        requires Windows.Devices.Enumeration.IDeviceAccessChangedEventArgs
    {
        [propget] HRESULT Id([out, retval] HSTRING *value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.Devices.Enumeration.DeviceAccessInformation),
        uuid(0baa9a73-6de5-4915-8ddd-9a0554a6f545)
    ]
    interface IDeviceAccessInformation : IInspectable
    {
        [eventadd] HRESULT AccessChanged([in] Windows.Foundation.TypedEventHandler<Windows.Devices.Enumeration.DeviceAccessInformation *, Windows.Devices.Enumeration.DeviceAccessChangedEventArgs *> *handler, [out, retval] EventRegistrationToken *cookie);
        [eventremove] HRESULT AccessChanged([in] EventRegistrationToken cookie);
        [propget] HRESULT CurrentStatus([out, retval] Windows.Devices.Enumeration.DeviceAccessStatus *status);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.Devices.Enumeration.DeviceAccessInformation),
        uuid(574bd3d3-5f30-45cd-8a94-724fe5973084),
    ]
    interface IDeviceAccessInformationStatics : IInspectable
    {
        HRESULT CreateFromId([in] HSTRING device_id, [out, retval] Windows.Devices.Enumeration.DeviceAccessInformation **value);
        HRESULT CreateFromDeviceClassId([in] GUID device_class_id, [out, retval] Windows.Devices.Enumeration.DeviceAccessInformation **value);
        HRESULT CreateFromDeviceClass([in] Windows.Devices.Enumeration.DeviceClass device_class, [out, retval] Windows.Devices.Enumeration.DeviceAccessInformation **value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile),
        static(Windows.Devices.Enumeration.IDeviceInformationStatics, Windows.Foundation.UniversalApiContract, 1.0),
        static(Windows.Devices.Enumeration.IDeviceInformationStatics2, Windows.Foundation.UniversalApiContract, 1.0),
        threading(both)
    ]
    runtimeclass DeviceInformation
    {
        [default] interface Windows.Devices.Enumeration.IDeviceInformation;
        [contract(Windows.Foundation.UniversalApiContract, 1.0)] interface Windows.Devices.Enumeration.IDeviceInformation2;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile),
    ]
    runtimeclass DeviceInformationCollection
    {
        [default] interface Windows.Foundation.Collections.IVectorView<Windows.Devices.Enumeration.DeviceInformation *>;
        interface Windows.Foundation.Collections.IIterable<Windows.Devices.Enumeration.DeviceInformation *>;
    }

    [
        marshaling_behavior(agile),
    ]
    runtimeclass DeviceInformationUpdate
    {
        [default] interface Windows.Devices.Enumeration.IDeviceInformationUpdate;
        interface Windows.Devices.Enumeration.IDeviceInformationUpdate2;
    }

    [
        marshaling_behavior(agile),
    ]
    runtimeclass DeviceThumbnail
    {
        [default] interface Windows.Storage.Streams.IRandomAccessStreamWithContentType;
        interface Windows.Storage.Streams.IContentTypeProvider;
        interface Windows.Storage.Streams.IRandomAccessStream;
        interface Windows.Storage.Streams.IOutputStream;
        interface Windows.Foundation.IClosable;
        interface Windows.Storage.Streams.IInputStream;
    }

    [
        marshaling_behavior(agile),
    ]
    runtimeclass DeviceWatcher
    {
        [default] interface Windows.Devices.Enumeration.IDeviceWatcher;
        interface Windows.Devices.Enumeration.IDeviceWatcher2;
    }

    [
        marshaling_behavior(agile)
    ]
    runtimeclass EnclosureLocation
    {
        [default] interface Windows.Devices.Enumeration.IEnclosureLocation;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile)
    ]
    runtimeclass DeviceAccessChangedEventArgs
    {
        [default] interface Windows.Devices.Enumeration.IDeviceAccessChangedEventArgs;
        [contract(Windows.Foundation.UniversalApiContract, 3.0)] interface Windows.Devices.Enumeration.IDeviceAccessChangedEventArgs2;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile),
        static(Windows.Devices.Enumeration.IDeviceAccessInformationStatics, Windows.Foundation.UniversalApiContract, 1.0),
        threading(both)
    ]
    runtimeclass DeviceAccessInformation
    {
        [default] interface Windows.Devices.Enumeration.IDeviceAccessInformation;
    }

}
