// Example: Batch writing to Analog Value objects
//
// This example demonstrates how to use the WritePropertyMultiple service
// to efficiently write multiple properties to multiple Analog Value objects
// in a single BACnet request.

use bacnet_emb::{
    application_protocol::primitives::data_value::ApplicationDataValueWrite,
    application_protocol::services::write_property_multiple::{
        WritePropertyMultiple, WritePropertyMultipleObject, WritePropertyRequest,
    },
    common::object_id::{ObjectId, ObjectType},
    common::property_id::PropertyId,
};

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
    // Initialize your network IO implementation
    // let io = YourNetworkIo::new();
    // let bacnet = Bacnet::new(io);

    // Example 1: Write multiple properties to a single Analog Value object
    // This is useful when configuring a new analog output point
    let av_object_0 = vec![
        WritePropertyRequest::new(
            PropertyId::PropPresentValue,
            None,
            ApplicationDataValueWrite::Real(72.5), // Set temperature to 72.5°F
            None,
        ),
        WritePropertyRequest::new(
            PropertyId::PropDeadband,
            None,
            ApplicationDataValueWrite::Real(1.0), // Set deadband to 1.0
            None,
        ),
        WritePropertyRequest::new(
            PropertyId::PropResolution,
            None,
            ApplicationDataValueWrite::Real(0.1), // Set resolution to 0.1
            None,
        ),
    ];

    let object1 = WritePropertyMultipleObject::new(
        ObjectId::new(ObjectType::ObjectAnalogValue, 0),
        av_object_0,
    );

    // Example 2: Configure another Analog Value object with different properties
    let av_object_1 = vec![
        WritePropertyRequest::new(
            PropertyId::PropPresentValue,
            None,
            ApplicationDataValueWrite::Real(45.0), // Set humidity to 45%
            None,
        ),
        WritePropertyRequest::new(
            PropertyId::PropMinPresValue,
            None,
            ApplicationDataValueWrite::Real(0.0), // Minimum value: 0%
            None,
        ),
        WritePropertyRequest::new(
            PropertyId::PropMaxPresValue,
            None,
            ApplicationDataValueWrite::Real(100.0), // Maximum value: 100%
            None,
        ),
    ];

    let object2 = WritePropertyMultipleObject::new(
        ObjectId::new(ObjectType::ObjectAnalogValue, 1),
        av_object_1,
    );

    // Example 3: Batch update multiple Analog Value objects simultaneously
    // This is useful for initializing a set of setpoints
    let av_object_2 = vec![WritePropertyRequest::new(
        PropertyId::PropPresentValue,
        None,
        ApplicationDataValueWrite::Real(68.0), // Heating setpoint
        None,
    )];

    let av_object_3 = vec![WritePropertyRequest::new(
        PropertyId::PropPresentValue,
        None,
        ApplicationDataValueWrite::Real(74.0), // Cooling setpoint
        None,
    )];

    let object3 = WritePropertyMultipleObject::new(
        ObjectId::new(ObjectType::ObjectAnalogValue, 2),
        av_object_2,
    );

    let object4 = WritePropertyMultipleObject::new(
        ObjectId::new(ObjectType::ObjectAnalogValue, 3),
        av_object_3,
    );

    // Combine all Analog Value objects into a single WritePropertyMultiple request
    let _request = WritePropertyMultiple::new(vec![object1, object2, object3, object4]);

    // Send the request
    // let mut buffer = [0u8; 1500];
    // bacnet
    //     .write_property_multiple(&mut buffer, request, None)
    //     .await?;

    println!("Analog Value batch write example completed successfully!");
    println!("Wrote to 4 Analog Value objects in a single request");
    Ok(())
}

// Common Analog Value properties you might want to write:
//
// - PresentValue: The current value of the analog value
// - Description: Text description of the point
// - Units: Engineering units (e.g., degrees Fahrenheit, percent)
// - MinPresValue: Minimum allowed present value
// - MaxPresValue: Maximum allowed present value
// - Resolution: Smallest change in value that can be detected
// - Deadband: Range around the setpoint where no action is taken
// - PriorityArray: Command priority array
// - RelinquishDefault: Default value when all priorities are relinquished
//
// Use cases for Analog Value batch writes:
//
// 1. **Setpoint Management**: Update multiple temperature/humidity setpoints at once
// 2. **System Initialization**: Configure default values for all analog outputs
// 3. **Mode Changes**: Switch between day/night or seasonal operating modes
// 4. **Alarm Thresholds**: Update multiple alarm limits simultaneously
// 5. **Tuning**: Adjust PID parameters or control settings across multiple loops
//
// Example scenarios:
//
// - Building automation: Update all zone temperature setpoints for occupied mode
// - HVAC control: Change heating and cooling setpoints together
// - Process control: Initialize multiple process variables at startup
// - Energy management: Shift all setpoints for demand response events
