/*
 * Copyright 2023 Hans Leidekker for CodeWeavers
 *
 * 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

#ifndef DO_NO_IMPORTS
import "windows.foundation.idl";
import "windows.storage.idl";
import "windows.system.idl";
import "windows.applicationmodel.activation.idl";
import "windows.applicationmodel.core.idl";
#endif

namespace Windows.ApplicationModel.Core {
    runtimeclass AppListEntry;
}

namespace Windows.ApplicationModel {
    typedef struct PackageVersion PackageVersion;

    interface IAppDisplayInfo;
    interface IDesignModeStatics;
    interface IDesignModeStatics2;
    interface IEnteredBackgroundEventArgs;
    interface ILeavingBackgroundEventArgs;
    interface IPackage;
    interface IPackage2;
    interface IPackage3;
    interface IPackageStatus;
    interface IPackageId;
    interface IPackageIdWithMetadata;
    interface IPackageStatics;
    interface ISuspendingDeferral;
    interface ISuspendingEventArgs;
    interface ISuspendingOperation;

    runtimeclass AppDisplayInfo;
    runtimeclass DesignMode;
    runtimeclass EnteredBackgroundEventArgs;
    runtimeclass LeavingBackgroundEventArgs;
    runtimeclass Package;
    runtimeclass PackageId;
    runtimeclass PackageStatus;
    runtimeclass SuspendingDeferral;
    runtimeclass SuspendingEventArgs;
    runtimeclass SuspendingOperation;

    declare {
        interface Windows.Foundation.Collections.IIterable<Windows.ApplicationModel.Package *>;
        interface Windows.Foundation.Collections.IIterator<Windows.ApplicationModel.Package *>;
        interface Windows.Foundation.Collections.IVectorView<Windows.ApplicationModel.Package *>;
        interface Windows.Foundation.Collections.IVectorView<Windows.ApplicationModel.Core.AppListEntry *>;
        interface Windows.Foundation.EventHandler<Windows.ApplicationModel.EnteredBackgroundEventArgs *>;
        interface Windows.Foundation.EventHandler<Windows.ApplicationModel.LeavingBackgroundEventArgs *>;
        interface Windows.Foundation.EventHandler<Windows.ApplicationModel.SuspendingEventArgs *>;
        interface Windows.Foundation.IAsyncOperation<Windows.Foundation.Collections.IVectorView<Windows.ApplicationModel.Core.AppListEntry *> *>;
        interface Windows.Foundation.AsyncOperationCompletedHandler<Windows.Foundation.Collections.IVectorView<Windows.ApplicationModel.Core.AppListEntry *> *>;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0)
    ]
    struct PackageVersion
    {
        UINT16 Major;
        UINT16 Minor;
        UINT16 Build;
        UINT16 Revision;
    };

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.ApplicationModel.AppDisplayInfo),
        uuid(1aeb1103-e4d4-41aa-a4f6-c4a276e79eac)
    ]
    interface IAppDisplayInfo : IInspectable
    {
        [propget] HRESULT DisplayName([out, retval] HSTRING *value);
        [propget] HRESULT Description([out, retval] HSTRING *value);
        HRESULT GetLogo([in] Windows.Foundation.Size size, [out, retval] Windows.Storage.Streams.RandomAccessStreamReference **value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.ApplicationModel.DesignMode),
        uuid(2c3893cc-f81a-4e7a-b857-76a80887e185)
    ]
    interface IDesignModeStatics : IInspectable
    {
        [propget] HRESULT DesignModeEnabled([out, retval] boolean *value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 5.0),
        exclusiveto(Windows.ApplicationModel.DesignMode),
        uuid(80cf8137-b064-4858-bec8-3eba22357535)
    ]
    interface IDesignModeStatics2 : IInspectable
    {
        [propget] HRESULT DesignMode2Enabled([out, retval] boolean *value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 3.0),
        uuid(f722dcc2-9827-403d-aaed-ecca9ac17398)
    ]
    interface IEnteredBackgroundEventArgs : IInspectable
    {
        HRESULT GetDeferral([out] [retval] Windows.Foundation.Deferral **value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 3.0),
        uuid(39c6ec9a-ae6e-46f9-a07a-cfc23f88733e)
    ]
    interface ILeavingBackgroundEventArgs : IInspectable
    {
        HRESULT GetDeferral([out] [retval] Windows.Foundation.Deferral **value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.ApplicationModel.Package),
        uuid(163c792f-bd75-413c-bf23-b1fe7b95d825)
    ]
    interface IPackage : IInspectable
    {
        [propget] HRESULT Id([out, retval] Windows.ApplicationModel.PackageId **value);
        [propget] HRESULT InstalledLocation([out, retval] Windows.Storage.StorageFolder **value);
        [propget] HRESULT IsFramework([out, retval] boolean *value);
        [propget] HRESULT Dependencies([out, retval] Windows.Foundation.Collections.IVectorView<Windows.ApplicationModel.Package *> **value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.ApplicationModel.Package),
        uuid(a6612fb6-7688-4ace-95fb-359538e7aa01)
    ]
    interface IPackage2 : IInspectable
    {
        [propget] HRESULT DisplayName([out, retval] HSTRING *value);
        [propget] HRESULT PublisherDisplayName([out, retval] HSTRING *value);
        [propget] HRESULT Description([out, retval] HSTRING *value);
        [propget] HRESULT Logo([out, retval] Windows.Foundation.Uri **value);
        [propget] HRESULT IsResourcePackage([out, retval] boolean *value);
        [propget] HRESULT IsBundle([out, retval] boolean *value);
        [propget] HRESULT IsDevelopmentMode([out, retval] boolean *value);
    }

    [
        exclusiveto(Windows.ApplicationModel.Package),
        uuid(5f738b61-f86a-4917-93d1-f1ee9d3b35d9),
        version(0x0a000000)
    ]
    interface IPackage3 : IInspectable
    {
        [propget] HRESULT Status([out, retval] Windows.ApplicationModel.PackageStatus **value);
        [propget] HRESULT InstalledDate([out, retval] Windows.Foundation.DateTime *value);
        HRESULT GetAppListEntriesAsync([out, retval] Windows.Foundation.IAsyncOperation<Windows.Foundation.Collections.IVectorView<Windows.ApplicationModel.Core.AppListEntry *> *> **operation);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.ApplicationModel.PackageStatus),
        uuid(5fe74f71-a365-4c09-a02d-046d525ea1da)
    ]
    interface IPackageStatus : IInspectable
    {
        HRESULT VerifyIsOK([out, retval] boolean *value);
        [propget] HRESULT NotAvailable([out, retval] boolean *value);
        [propget] HRESULT PackageOffline([out, retval] boolean *value);
        [propget] HRESULT DataOffline([out, retval] boolean *value);
        [propget] HRESULT Disabled([out, retval] boolean *value);
        [propget] HRESULT NeedsRemediation([out, retval] boolean *value);
        [propget] HRESULT LicenseIssue([out, retval] boolean *value);
        [propget] HRESULT Modified([out, retval] boolean *value);
        [propget] HRESULT Tampered([out, retval] boolean *value);
        [propget] HRESULT DependencyIssue([out, retval] boolean *value);
        [propget] HRESULT Servicing([out, retval] boolean *value);
        [propget] HRESULT DeploymentInProgress([out, retval] boolean *value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.ApplicationModel.PackageId),
        uuid(1adb665e-37c7-4790-9980-dd7ae74e8bb2)
    ]
    interface IPackageId : IInspectable
    {
        [propget] HRESULT Name([out, retval] HSTRING *value);
        [propget] HRESULT Version([out, retval] Windows.ApplicationModel.PackageVersion *value);
        [propget] HRESULT Architecture([out, retval] Windows.System.ProcessorArchitecture *value);
        [propget] HRESULT ResourceId([out, retval] HSTRING *value);
        [propget] HRESULT Publisher([out, retval] HSTRING *value);
        [propget] HRESULT PublisherId([out, retval] HSTRING *value);
        [propget] HRESULT FullName([out, retval] HSTRING *value);
        [propget] HRESULT FamilyName([out, retval] HSTRING *value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.ApplicationModel.PackageId),
        uuid(40577a7c-0c9e-443d-9074-855f5ce0a08d)
    ]
    interface IPackageIdWithMetadata : IInspectable
    {
        [propget] HRESULT ProductId([out, retval] HSTRING *value);
        [propget] HRESULT Author([out, retval] HSTRING *value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        exclusiveto(Windows.ApplicationModel.Package),
        uuid(4e534bdf-2960-4878-97a4-9624deb72f2d)
    ]
    interface IPackageStatics : IInspectable
    {
        [propget] HRESULT Current([out, retval] Windows.ApplicationModel.Package **value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        uuid(59140509-8bc9-4eb4-b636-dabdc4f46f66)
    ]
    interface ISuspendingDeferral : IInspectable
    {
        HRESULT Complete();
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        uuid(96061c05-2dba-4d08-b0bd-2b30a131c6aa)
    ]
    interface ISuspendingEventArgs : IInspectable
    {
        [propget] HRESULT SuspendingOperation([out, retval] Windows.ApplicationModel.SuspendingOperation **value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        uuid(9da4ca41-20e1-4e9b-9f65-a9f435340c3a)
    ]
    interface ISuspendingOperation : IInspectable
    {
        HRESULT GetDeferral([out, retval] Windows.ApplicationModel.SuspendingDeferral **deferral);
        [propget] HRESULT Deadline([out, retval] Windows.Foundation.DateTime *value);
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile),
        threading(both)
    ]
    runtimeclass AppDisplayInfo
    {
        [default] interface Windows.ApplicationModel.IAppDisplayInfo;
    }


    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile),
        static(Windows.ApplicationModel.IDesignModeStatics, Windows.Foundation.UniversalApiContract, 1.0),
        static(Windows.ApplicationModel.IDesignModeStatics2, Windows.Foundation.UniversalApiContract, 5.0),
        threading(both)
    ]
    runtimeclass DesignMode
    {
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 3.0),
        marshaling_behavior(agile)
    ]
    runtimeclass EnteredBackgroundEventArgs
    {
        [default] interface Windows.ApplicationModel.IEnteredBackgroundEventArgs;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 3.0),
        marshaling_behavior(agile)
    ]
    runtimeclass LeavingBackgroundEventArgs
    {
        [default] interface Windows.ApplicationModel.ILeavingBackgroundEventArgs;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile),
        static(Windows.ApplicationModel.IPackageStatics, Windows.Foundation.UniversalApiContract, 1.0),
        threading(both)
    ]
    runtimeclass Package
    {
        [default] interface Windows.ApplicationModel.IPackage;
        [contract(Windows.Foundation.UniversalApiContract, 1.0)] interface Windows.ApplicationModel.IPackage2;
        [contract(Windows.Foundation.UniversalApiContract, 1.0)] interface Windows.ApplicationModel.IPackage3;
        [contract(Windows.Foundation.UniversalApiContract, 1.0)] interface Windows.ApplicationModel.IPackageWithMetadata;
        [contract(Windows.Foundation.UniversalApiContract, 3.0)] interface Windows.ApplicationModel.IPackage4;
        [contract(Windows.Foundation.UniversalApiContract, 4.0)] interface Windows.ApplicationModel.IPackage5;
        [contract(Windows.Foundation.UniversalApiContract, 7.0)] interface Windows.ApplicationModel.IPackage6;
        [contract(Windows.Foundation.UniversalApiContract, 8.0)] interface Windows.ApplicationModel.IPackage7;
        [contract(Windows.Foundation.UniversalApiContract, 10.0)] interface Windows.ApplicationModel.IPackage8;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile)
    ]
    runtimeclass PackageStatus
    {
        [default] interface Windows.ApplicationModel.IPackageStatus;
        [contract(Windows.Foundation.UniversalApiContract, 4.0)] interface Windows.ApplicationModel.IPackageStatus2;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile)
    ]
    runtimeclass PackageId
    {
        [default] interface Windows.ApplicationModel.IPackageId;
        [contract(Windows.Foundation.UniversalApiContract, 1.0)] interface Windows.ApplicationModel.IPackageIdWithMetadata;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile)
    ]
    runtimeclass SuspendingDeferral
    {
        [default] interface Windows.ApplicationModel.ISuspendingDeferral;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile)
    ]
    runtimeclass SuspendingEventArgs
    {
        [default] interface Windows.ApplicationModel.ISuspendingEventArgs;
    }

    [
        contract(Windows.Foundation.UniversalApiContract, 1.0),
        marshaling_behavior(agile)
    ]
    runtimeclass SuspendingOperation
    {
        [default] interface Windows.ApplicationModel.ISuspendingOperation;
    }
}
