// Copyright 2020 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
library fuchsia.examples.docs;

using zx;

// [START structs]
type CirclePoint = struct {
    x float32;
    y float32;
};

type Color = struct {
    r float32;
    g float32;
    b float32;
};
// [END structs]

// [START structs-use]
type Circle = struct {
    filled bool;
    center CirclePoint; // CirclePoint will be stored in-line
    radius float32;
    color box<Color>; // Color will be stored out-of-line
    dashed bool;
};
// [END structs-use]

// [START comments]
// this is a comment
/// and this one is too, but it also ends up in the generated code
type MyStruct = struct { // plain comment
    f int32; // as is this one
}; // and this is the last one!
// [END comments]

// [START consts]
const ENABLED_FLAG bool = true;
const OFFSET int8 = -33;
const ANSWER uint16 = 42;
const ANSWER_IN_BINARY uint16 = 0b101010;
const POPULATION_USA_2018 uint32 = 330000000;
const DIAMOND uint64 = 0x183c7effff7e3c18;
const FUCHSIA uint64 = 4054509061583223046;
const USERNAME string = "squeenze";
const MIN_TEMP float32 = -273.15;
const CONVERSION_FACTOR float64 = 1.41421358;
const MY_DRINK Beverage = Beverage.WATER;
// [END consts]

// [START defaults]
type Scene = struct {
    @allow_deprecated_struct_defaults
    background_rgb uint32 = 0xFF77FF; // fuchsia is the default background
    foreground_rgb uint32; // there is no default foreground color
};
// [END defaults]

// [START primitives]
// A record which contains fields of a few primitive types.
type Sprite = struct {
    x float32;
    y float32;
    index uint32;
    color uint32;
    visible bool;
};
// [END primitives]

// [START bits]
type InfoFeatures = strict bits : uint8 {
    /// If present, this device represents WLAN hardware
    WLAN = 0x01;
    /// If present, this device is synthetic (not backed by h/w)
    SYNTH = 0x02;
    /// If present, this device receives all messages it sends
    LOOPBACK = 0x04;
};

// Underlying type is assumed to be uint32.
type AllowableSegments = flexible bits {
    TOLL_ROADS = 0b001;
    HIGHWAYS = 0b010;
    BIKE_PATHS = 0b100;
};

const ROADS AllowableSegments = AllowableSegments.TOLL_ROADS | AllowableSegments.HIGHWAYS;
// [END bits]

// [START enums]
type Beverage = flexible enum : uint8 {
    WATER = 0;
    COFFEE = 1;
    TEA = 2;
    WHISKEY = 3;
};

// Underlying type is assumed to be uint32.
type Vessel = strict enum {
    CUP = 0;
    BOWL = 1;
    TUREEN = 2;
    JUG = 3;
};
// [END enums]

// [START enum-use]
// A record which contains two enum fields.
type Order = struct {
    beverage Beverage;
    vessel Vessel;
};
// [END enum-use]

// [START arrays]
// A record which contains some arrays.
type Arrays = struct {
    // array of exactly 16 floating point numbers
    matrix array<float32, 16>;

    // array of exactly 10 arrays of 4 strings each
    form array<array<string, 4>, 10>;
};
// [END arrays]

// [START strings]
// A record which contains some strings.
type Document = struct {
    // title string, maximum of 40 bytes long
    title string:40;

    // description string, may be null, no upper bound on size
    description string:optional;
};
// [END strings]

// [START vectors]
// A record which contains some vectors.
type Vectors = struct {
    // a vector of up to 10 integers
    params vector<int32>:10;

    // a vector of bytes, no upper bound on size
    blob bytes;

    // a nullable vector of up to 24 strings
    nullable_vector_of_strings vector<string>:<24, optional>;

    // a vector of nullable strings, no upper bound on size
    vector_of_nullable_strings vector<string:optional>;

    // a vector of vectors of 16-element arrays of floating point numbers
    complex vector<vector<array<float32, 16>>>;
};
// [END vectors]

// [START handles]
// A record which contains some handles.
type Handles = resource struct {
    // a handle of unspecified type
    h zx.handle;

    // an optional channel
    c zx.handle:<CHANNEL, optional>;
};
// [END handles]

// [START tables]
type Profile = table {
    1: locales vector<string>;
    2: calendars vector<string>;
    3: time_zones vector<string>;
};
// [END tables]

type Left = struct {};

type Right = struct {};

// [START unions-use]
type Either = strict union {
    1: left Left;
    2: right Right;
};
// [END unions-use]

// [START strict-vs-flexible]
type FlexibleEither = flexible union {
    1: left Left;
    2: right Right;
};
// [END strict-vs-flexible]

protocol RealCalculator {};

// [START endpoints]
// A record which contains protocol-bound channels.
type Record = resource struct {
    // client endpoint of a channel bound to the Calculator protocol
    c client_end:Calculator;

    // server endpoint of a channel bound to the Science protocol
    s server_end:Science;

    // optional client endpoint of a channel bound to the
    // RealCalculator protocol
    r client_end:<RealCalculator, optional>;
};
// [END endpoints]

// [START composition-base]
protocol SceneryController {
    SetBackground(struct {
        color Color;
    });
    SetForeground(struct {
        color Color;
    });
};
// [END composition-base]

// [START composition-inherit]
protocol Drawer {
    compose SceneryController;
    Circle(struct {
        x int32;
        y int32;
        radius int32;
    });
    Square(struct {
        x int32;
        y int32;
        diagonal int32;
    });
};

protocol Writer {
    compose SceneryController;
    Text(struct {
        x int32;
        y int32;
        message string;
    });
};
// [END composition-inherit]

// [START composition-multiple-1]
protocol FontController {
    SetPointSize(struct {
        points int32;
    });
    SetFontName(struct {
        fontname string;
    });
    Italic(struct {
        onoff bool;
    });
    Bold(struct {
        onoff bool;
    });
    Underscore(struct {
        onoff bool;
    });
    Strikethrough(struct {
        onoff bool;
    });
};
// [END composition-multiple-1]

type Time = struct {};

// [START layering-clock]
protocol Clock {
    Now() -> (struct {
        time Time;
    });
    CurrentTimeZone() -> (struct {
        timezone string;
    });
};
// [END layering-clock]

// [START layering-horologist]
protocol Horologist {
    SetTime(struct {
        time Time;
    });
    SetCurrentTimeZone(struct {
        timezone string;
    });
};
// [END layering-horologist]

// [START layering-systemclock]
protocol SystemClock {
    compose Clock;
    compose Horologist;
};
// [END layering-systemclock]

// [START aliasing]
alias StoryID = string:MAX;
alias Chapters = vector<StoryID>:5;
// [END aliasing]

// [START aliasing-usage]
type Message = struct {
    baseline StoryID;
    chapters Chapters;
};
// [END aliasing-usage]

// [START builtin-aliases]
type RawBytes = struct {
    head byte;
    rest bytes;
};
// [END builtin-aliases]

// [START calculator]
type DivisionError = strict enum : uint32 {
    DIVIDE_BY_ZERO = 1;
};

protocol Calculator {
    Add(struct {
        a int32;
        b int32;
    }) -> (struct {
        sum int32;
    });
    Divide(struct {
        dividend int32;
        divisor int32;
    }) -> (struct {
        quotient int32;
        remainder int32;
    }) error DivisionError;
    Clear();
    -> OnError(struct {
        status_code uint32;
    });
};
// [END calculator]

// [START maximum-recursion-depth]
type InlineObject = struct {
    content_a string;
    vector vector<OutOfLineStructAtLevel1>;
    table TableInlineAtLevel0;
};

type OutOfLineStructAtLevel1 = struct {
    content_b string;
};

type TableInlineAtLevel0 = table {
    1: content_c string;
};
// [END maximum-recursion-depth]
