"use strict";
var __defProp = Object.defineProperty;
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
var __getOwnPropNames = Object.getOwnPropertyNames;
var __hasOwnProp = Object.prototype.hasOwnProperty;
var __export = (target, all) => {
  for (var name in all)
    __defProp(target, name, { get: all[name], enumerable: true });
};
var __copyProps = (to, from, except, desc) => {
  if (from && typeof from === "object" || typeof from === "function") {
    for (let key of __getOwnPropNames(from))
      if (!__hasOwnProp.call(to, key) && key !== except)
        __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
  }
  return to;
};
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
var water_heater_management_exports = {};
__export(water_heater_management_exports, {
  WaterHeaterManagement: () => WaterHeaterManagement,
  WaterHeaterManagementCluster: () => WaterHeaterManagementCluster
});
module.exports = __toCommonJS(water_heater_management_exports);
var import_MutableCluster = require("../cluster/mutation/MutableCluster.js");
var import_Cluster = require("../cluster/Cluster.js");
var import_TlvNumber = require("../tlv/TlvNumber.js");
var import_BitmapSchema = require("../schema/BitmapSchema.js");
var import_TlvObject = require("../tlv/TlvObject.js");
var import_TlvBoolean = require("../tlv/TlvBoolean.js");
var import_model = require("#model");
var import_TlvNoArguments = require("../tlv/TlvNoArguments.js");
var import_Priority = require("../globals/Priority.js");
var import_ClusterRegistry = require("../cluster/ClusterRegistry.js");
/**
 * @license
 * Copyright 2022-2026 Matter.js Authors
 * SPDX-License-Identifier: Apache-2.0
 */
var WaterHeaterManagement;
((WaterHeaterManagement2) => {
  let Feature;
  ((Feature2) => {
    Feature2["EnergyManagement"] = "EnergyManagement";
    Feature2["TankPercent"] = "TankPercent";
  })(Feature = WaterHeaterManagement2.Feature || (WaterHeaterManagement2.Feature = {}));
  WaterHeaterManagement2.WaterHeaterHeatSource = {
    /**
     * Immersion Heating Element 1
     */
    immersionElement1: (0, import_BitmapSchema.BitFlag)(0),
    /**
     * Immersion Heating Element 2
     */
    immersionElement2: (0, import_BitmapSchema.BitFlag)(1),
    /**
     * Heat pump Heating
     */
    heatPump: (0, import_BitmapSchema.BitFlag)(2),
    /**
     * Boiler Heating (e.g. Gas or Oil)
     */
    boiler: (0, import_BitmapSchema.BitFlag)(3),
    /**
     * Other Heating
     */
    other: (0, import_BitmapSchema.BitFlag)(4)
  };
  let BoostState;
  ((BoostState2) => {
    BoostState2[BoostState2["Inactive"] = 0] = "Inactive";
    BoostState2[BoostState2["Active"] = 1] = "Active";
  })(BoostState = WaterHeaterManagement2.BoostState || (WaterHeaterManagement2.BoostState = {}));
  WaterHeaterManagement2.TlvWaterHeaterBoostInfo = (0, import_TlvObject.TlvObject)({
    /**
     * This field shall indicate the time period, in seconds, for which the boost state is activated.
     *
     * @see {@link MatterSpecification.v142.Cluster} § 9.5.6.3.1
     */
    duration: (0, import_TlvObject.TlvField)(0, import_TlvNumber.TlvUInt32.bound({ min: 1 })),
    /**
     * This field shall indicate whether the boost state shall be automatically canceled once the hot water has
     * reached either:
     *
     *   • the set point temperature (from the thermostat cluster)
     *
     *   • the TemporarySetpoint temperature (if specified)
     *
     *   • the TargetPercentage (if specified).
     *
     * @see {@link MatterSpecification.v142.Cluster} § 9.5.6.3.2
     */
    oneShot: (0, import_TlvObject.TlvOptionalField)(1, import_TlvBoolean.TlvBoolean),
    /**
     * This field shall indicate that the consumer wants the water to be heated quickly. This may cause multiple
     * heat sources to be activated (e.g. a heat pump and direct electric immersion heating element).
     *
     * The choice of which heat sources are activated is manufacturer specific.
     *
     * @see {@link MatterSpecification.v142.Cluster} § 9.5.6.3.3
     */
    emergencyBoost: (0, import_TlvObject.TlvOptionalField)(2, import_TlvBoolean.TlvBoolean),
    /**
     * This field shall indicate the target temperature to which the water will be heated.
     *
     * If included, it shall be used instead of the thermostat cluster set point temperature whilst the boost state
     * is activated.
     *
     * The value of this field shall be within the constraints of the MinHeatSetpointLimit and MaxHeatSetpointLimit
     * attributes (inclusive), of the thermostat cluster.
     *
     * @see {@link MatterSpecification.v142.Cluster} § 9.5.6.3.4
     */
    temporarySetpoint: (0, import_TlvObject.TlvOptionalField)(3, import_TlvNumber.TlvInt16),
    /**
     * This field shall indicate the target percentage of hot water in the tank that the TankPercentage attribute
     * must reach before the heating is switched off.
     *
     * @see {@link MatterSpecification.v142.Cluster} § 9.5.6.3.5
     */
    targetPercentage: (0, import_TlvObject.TlvOptionalField)(4, import_TlvNumber.TlvPercent),
    /**
     * This field shall indicate the percentage to which the hot water in the tank shall be allowed to fall before
     * again beginning to reheat it.
     *
     * For example if the TargetPercentage was 80%, and the TargetReheat was 40%, then after initial heating to 80%
     * hot water, the tank may have hot water drawn off until only 40% hot water remains. At this point the heater
     * will begin to heat back up to 80% of hot water. If this field and the OneShot field were both omitted,
     * heating would begin again after any water draw which reduced the TankPercentage below 80%.
     *
     * This field shall be less than or equal to the TargetPercentage field.
     *
     * @see {@link MatterSpecification.v142.Cluster} § 9.5.6.3.6
     */
    targetReheat: (0, import_TlvObject.TlvOptionalField)(5, import_TlvNumber.TlvPercent)
  });
  WaterHeaterManagement2.TlvBoostRequest = (0, import_TlvObject.TlvObject)({ boostInfo: (0, import_TlvObject.TlvField)(0, WaterHeaterManagement2.TlvWaterHeaterBoostInfo) });
  WaterHeaterManagement2.TlvBoostStartedEvent = (0, import_TlvObject.TlvObject)({ boostInfo: (0, import_TlvObject.TlvField)(0, WaterHeaterManagement2.TlvWaterHeaterBoostInfo) });
  WaterHeaterManagement2.EnergyManagementComponent = import_MutableCluster.MutableCluster.Component({
    attributes: {
      /**
       * Indicates the volume of water that the hot water tank can hold (in units of Litres). This allows an
       * energy management system to estimate the required heating energy needed to reach the target temperature.
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.7.3
       */
      tankVolume: (0, import_Cluster.Attribute)(2, import_TlvNumber.TlvUInt16),
      /**
       * Indicates the estimated heat energy needed to raise the water temperature to the target setpoint. This
       * can be computed by taking the specific heat capacity of water (4182 J/kg °C) and by knowing the current
       * temperature of the water, the tank volume and target temperature.
       *
       * For example, if the target temperature was 60°C, the current temperature was 20°C and the tank volume was
       * 100L:
       *
       * ### Mass of water = 1kg per Litre
       *
       * Total Mass = 100 x 1kg = 100kg
       *
       * Δ Temperature = (target temperature - current temperature)
       *
       * = (60°C - 20°C) = 40°C
       *
       * ### Energy required to
       *
       * heat the water to 60°C = 4182 x 40 x 100 = 16,728,000 J
       *
       * Converting Joules in to Wh of heat (divide by 3600):
       *
       * If the TankPercent feature is supported, then this estimate shall also take into account the percentage
       * of the water in the tank which is already hot.
       *
       * > [!NOTE]
       *
       * > The electrical energy required to heat the water depends on the heating system used to heat the water.
       *   For example, a direct electric immersion heating element can be close to 100% efficient, so the
       *   electrical energy needed to heat the hot water is nearly the same as the EstimatedHeatEnergyRequired.
       *   However some forms of heating, such as an air-source heat pump which extracts heat from ambient air,
       *   requires much less electrical energy to heat hot water. Heat pumps can be produce 3kWh of heat output
       *   for 1kWh of electrical energy input. The conversion between heat energy and electrical energy is
       *   outside the scope of this cluster.
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.7.4
       */
      estimatedHeatRequired: (0, import_Cluster.Attribute)(3, import_TlvNumber.TlvInt64.bound({ min: 0 }))
    }
  });
  WaterHeaterManagement2.TankPercentComponent = import_MutableCluster.MutableCluster.Component({
    attributes: {
      /**
       * Indicates an approximate level of hot water stored in the tank, which might help consumers understand the
       * amount of hot water remaining in the tank. The accuracy of this attribute is manufacturer specific.
       *
       * In most hot water tanks, there is a stratification effect where the hot water layer rests above a cooler
       * layer of water below. For this reason cold water is fed in at the bottom of the tank and the hot water is
       * drawn from the top.
       *
       * Some water tanks might use multiple temperature probes to estimate the level of the hot water layer. A
       * water heater with multiple temperature probes is likely to implement an algorithm to estimate the hot
       * water tank percentage by taking into account the temperature values of each probe to determine the height
       * of the hot water.
       *
       * However it might be possible with a single temperature probe to estimate how much hot water is left using
       * a simpler algorithm:
       *
       * For example, if the target temperature was 60°C, the CurrentTemperature was 40°C from a single
       * temperature probe measuring the average water temperature and the temperature of incoming cold water
       * (COLD_WATER_TEMP) was assumed to be 20°C:
       *
       * TankPercentage = int(((current temperature - COLD_WATER_TEMP) / (target temperature - COLD_WATER_TEMP)) *
       * 100)
       *
       * TankPercentage = min( max(TankPercentage,0), 100)
       *
       * ### TankPercentage = 50%
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.7.5
       */
      tankPercentage: (0, import_Cluster.Attribute)(4, import_TlvNumber.TlvPercent)
    }
  });
  WaterHeaterManagement2.Base = import_MutableCluster.MutableCluster.Component({
    id: 148,
    name: "WaterHeaterManagement",
    revision: 2,
    features: {
      /**
       * Allows energy management control of the tank
       */
      energyManagement: (0, import_BitmapSchema.BitFlag)(0),
      /**
       * Supports monitoring the percentage of hot water in the tank
       */
      tankPercent: (0, import_BitmapSchema.BitFlag)(1)
    },
    attributes: {
      /**
       * Indicates the heat sources that the water heater can call on for heating. If a bit is set then the water
       * heater supports the corresponding heat source.
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.7.1
       */
      heaterTypes: (0, import_Cluster.FixedAttribute)(0, (0, import_TlvNumber.TlvBitmap)(import_TlvNumber.TlvUInt8, WaterHeaterManagement2.WaterHeaterHeatSource)),
      /**
       * Indicates if the water heater is heating water. If a bit is set then the corresponding heat source is
       * active.
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.7.2
       */
      heatDemand: (0, import_Cluster.Attribute)(1, (0, import_TlvNumber.TlvBitmap)(import_TlvNumber.TlvUInt8, WaterHeaterManagement2.WaterHeaterHeatSource)),
      /**
       * Indicates whether the Boost, as triggered by a Boost command, is currently Active or Inactive.
       *
       * See Section 9.5.8.1, “Boost Command” and Section 9.5.8.2, “CancelBoost Command” for more details.
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.7.6
       */
      boostState: (0, import_Cluster.Attribute)(5, (0, import_TlvNumber.TlvEnum)())
    },
    commands: {
      /**
       * Allows a client to request that the water heater is put into a Boost state.
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.8.1
       */
      boost: (0, import_Cluster.Command)(0, WaterHeaterManagement2.TlvBoostRequest, 0, import_Cluster.TlvNoResponse, { invokeAcl: import_model.AccessLevel.Manage }),
      /**
       * Allows a client to cancel an ongoing Boost operation. This command has no payload.
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.8.2
       */
      cancelBoost: (0, import_Cluster.Command)(1, import_TlvNoArguments.TlvNoArguments, 1, import_Cluster.TlvNoResponse, { invokeAcl: import_model.AccessLevel.Manage })
    },
    events: {
      /**
       * This event shall be generated whenever a Boost command is accepted.
       *
       * The corresponding structure fields within the WaterHeaterBoostInfoStruct are copied from the Boost
       * command.
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.9.1
       */
      boostStarted: (0, import_Cluster.Event)(0, import_Priority.Priority.Info, WaterHeaterManagement2.TlvBoostStartedEvent),
      /**
       * This event shall be generated whenever the BoostState transitions from Active to Inactive.
       *
       * @see {@link MatterSpecification.v142.Cluster} § 9.5.9.2
       */
      boostEnded: (0, import_Cluster.Event)(1, import_Priority.Priority.Info, import_TlvNoArguments.TlvNoArguments)
    },
    /**
     * This metadata controls which WaterHeaterManagementCluster elements matter.js activates for specific feature
     * combinations.
     */
    extensions: import_MutableCluster.MutableCluster.Extensions(
      { flags: { energyManagement: true }, component: WaterHeaterManagement2.EnergyManagementComponent },
      { flags: { tankPercent: true }, component: WaterHeaterManagement2.TankPercentComponent }
    )
  });
  WaterHeaterManagement2.ClusterInstance = (0, import_MutableCluster.MutableCluster)(WaterHeaterManagement2.Base);
  WaterHeaterManagement2.Cluster = WaterHeaterManagement2.ClusterInstance;
  const EM = { energyManagement: true };
  const TP = { tankPercent: true };
  WaterHeaterManagement2.CompleteInstance = (0, import_MutableCluster.MutableCluster)({
    id: WaterHeaterManagement2.Cluster.id,
    name: WaterHeaterManagement2.Cluster.name,
    revision: WaterHeaterManagement2.Cluster.revision,
    features: WaterHeaterManagement2.Cluster.features,
    attributes: {
      ...WaterHeaterManagement2.Cluster.attributes,
      tankVolume: import_MutableCluster.MutableCluster.AsConditional(
        WaterHeaterManagement2.EnergyManagementComponent.attributes.tankVolume,
        { mandatoryIf: [EM] }
      ),
      estimatedHeatRequired: import_MutableCluster.MutableCluster.AsConditional(
        WaterHeaterManagement2.EnergyManagementComponent.attributes.estimatedHeatRequired,
        { mandatoryIf: [EM] }
      ),
      tankPercentage: import_MutableCluster.MutableCluster.AsConditional(
        WaterHeaterManagement2.TankPercentComponent.attributes.tankPercentage,
        { mandatoryIf: [TP] }
      )
    },
    commands: WaterHeaterManagement2.Cluster.commands,
    events: WaterHeaterManagement2.Cluster.events
  });
  WaterHeaterManagement2.Complete = WaterHeaterManagement2.CompleteInstance;
})(WaterHeaterManagement || (WaterHeaterManagement = {}));
const WaterHeaterManagementCluster = WaterHeaterManagement.Cluster;
import_ClusterRegistry.ClusterRegistry.register(WaterHeaterManagement.Complete);
//# sourceMappingURL=water-heater-management.js.map
