pub const ext = @import("ext.zig");
const gstinsertbin = @This();

const std = @import("std");
const compat = @import("compat");
const gst = @import("gst1");
const gobject = @import("gobject2");
const glib = @import("glib2");
const gmodule = @import("gmodule2");
/// This element is a `gst.Bin` that has a single source and sink pad. It allows
/// the user (the application) to easily add and remove filter-like element
/// (that has a single source and sink pad), to the pipeline while it is running.
/// It features a fully asynchronous API inspired by GLib's GAsyncResult based
/// APIs.
///
/// Each operation (addition or removal) can take a callback, this callback
/// is guaranteed to be called. Unlike GIO, there is no guarantee about where
/// this callback will be called from, it could be called before the action
/// returns or it could be called later from another thread. The signature of
/// this callback `gstinsertbin.InsertBinCallback`.
///
/// Apart from the library API, since 1.24 insertbin can also be found in the
/// registry:
///
/// ``` C
///   GstElement *pipeline, *insertbin, *videoflip;
///
///   gst_init (NULL, NULL);
///   pipeline =
///       gst_parse_launch ("videotestsrc ! insertbin name=i ! autovideosink",
///       NULL);
///
///   ...
///
///   insertbin = gst_bin_get_by_name (GST_BIN (pipeline), "i");
///   videoflip = gst_element_factory_make ("videoflip", NULL);
///
///   ...
///
///   g_object_set (videoflip, "method", 1, NULL);
///   g_signal_emit_by_name (insertbin, "append", videoflip, NULL, NULL);
///
///   ...
/// ```
pub const InsertBin = extern struct {
    pub const Parent = gst.Bin;
    pub const Implements = [_]type{gst.ChildProxy};
    pub const Class = gstinsertbin.InsertBinClass;
    f_parent: gst.Bin,
    f_priv: ?*gstinsertbin.InsertBinPrivate,

    pub const virtual_methods = struct {};

    pub const properties = struct {};

    pub const signals = struct {
        /// This action signal adds the filter like element after any other element
        /// in the bin.
        ///
        /// Same as `gstinsertbin.InsertBin.append`
        pub const append = struct {
            pub const name = "append";

            pub fn connect(p_instance: anytype, comptime P_Data: type, p_callback: *const fn (@TypeOf(p_instance), p_callback: *gst.Element, p_user_data: ?*anyopaque, p_user_data2: ?*anyopaque, P_Data) callconv(.c) void, p_data: P_Data, p_options: gobject.ext.ConnectSignalOptions(P_Data)) c_ulong {
                return gobject.signalConnectClosureById(
                    @ptrCast(@alignCast(gobject.ext.as(InsertBin, p_instance))),
                    gobject.signalLookup("append", InsertBin.getGObjectType()),
                    glib.quarkFromString(p_options.detail orelse null),
                    gobject.CClosure.new(@ptrCast(p_callback), p_data, @ptrCast(p_options.destroyData)),
                    @intFromBool(p_options.after),
                );
            }
        };

        /// This action signal adds the filter like element after the `sibling`
        /// element in the bin.
        /// element in the bin.
        ///
        /// Same as `gstinsertbin.InsertBin.insertAfter`
        pub const insert_after = struct {
            pub const name = "insert-after";

            pub fn connect(p_instance: anytype, comptime P_Data: type, p_callback: *const fn (@TypeOf(p_instance), p_sibling: *gst.Element, p_callback: *gst.Element, p_user_data: ?*anyopaque, p_user_data2: ?*anyopaque, P_Data) callconv(.c) void, p_data: P_Data, p_options: gobject.ext.ConnectSignalOptions(P_Data)) c_ulong {
                return gobject.signalConnectClosureById(
                    @ptrCast(@alignCast(gobject.ext.as(InsertBin, p_instance))),
                    gobject.signalLookup("insert-after", InsertBin.getGObjectType()),
                    glib.quarkFromString(p_options.detail orelse null),
                    gobject.CClosure.new(@ptrCast(p_callback), p_data, @ptrCast(p_options.destroyData)),
                    @intFromBool(p_options.after),
                );
            }
        };

        /// This action signal adds the filter like element before the `sibling`
        /// element in the bin.
        ///
        /// Same as `gstinsertbin.InsertBin.insertBefore`
        pub const insert_before = struct {
            pub const name = "insert-before";

            pub fn connect(p_instance: anytype, comptime P_Data: type, p_callback: *const fn (@TypeOf(p_instance), p_sibling: *gst.Element, p_callback: *gst.Element, p_user_data: ?*anyopaque, p_user_data2: ?*anyopaque, P_Data) callconv(.c) void, p_data: P_Data, p_options: gobject.ext.ConnectSignalOptions(P_Data)) c_ulong {
                return gobject.signalConnectClosureById(
                    @ptrCast(@alignCast(gobject.ext.as(InsertBin, p_instance))),
                    gobject.signalLookup("insert-before", InsertBin.getGObjectType()),
                    glib.quarkFromString(p_options.detail orelse null),
                    gobject.CClosure.new(@ptrCast(p_callback), p_data, @ptrCast(p_options.destroyData)),
                    @intFromBool(p_options.after),
                );
            }
        };

        /// This action signal adds the filter like element before any other element
        /// in the bin.
        ///
        /// Same as `gstinsertbin.InsertBin.prepend`
        pub const prepend = struct {
            pub const name = "prepend";

            pub fn connect(p_instance: anytype, comptime P_Data: type, p_callback: *const fn (@TypeOf(p_instance), p_callback: *gst.Element, p_user_data: ?*anyopaque, p_user_data2: ?*anyopaque, P_Data) callconv(.c) void, p_data: P_Data, p_options: gobject.ext.ConnectSignalOptions(P_Data)) c_ulong {
                return gobject.signalConnectClosureById(
                    @ptrCast(@alignCast(gobject.ext.as(InsertBin, p_instance))),
                    gobject.signalLookup("prepend", InsertBin.getGObjectType()),
                    glib.quarkFromString(p_options.detail orelse null),
                    gobject.CClosure.new(@ptrCast(p_callback), p_data, @ptrCast(p_options.destroyData)),
                    @intFromBool(p_options.after),
                );
            }
        };

        /// This action signal removed the filter like element from the bin.
        ///
        /// Same as `gstinsertbin.InsertBin.remove`
        pub const remove = struct {
            pub const name = "remove";

            pub fn connect(p_instance: anytype, comptime P_Data: type, p_callback: *const fn (@TypeOf(p_instance), p_callback: *gst.Element, p_user_data: ?*anyopaque, p_user_data2: ?*anyopaque, P_Data) callconv(.c) void, p_data: P_Data, p_options: gobject.ext.ConnectSignalOptions(P_Data)) c_ulong {
                return gobject.signalConnectClosureById(
                    @ptrCast(@alignCast(gobject.ext.as(InsertBin, p_instance))),
                    gobject.signalLookup("remove", InsertBin.getGObjectType()),
                    glib.quarkFromString(p_options.detail orelse null),
                    gobject.CClosure.new(@ptrCast(p_callback), p_data, @ptrCast(p_options.destroyData)),
                    @intFromBool(p_options.after),
                );
            }
        };
    };

    /// Creates a new `gstinsertbin.InsertBin`
    extern fn gst_insert_bin_new(p_name: ?[*:0]const u8) *gstinsertbin.InsertBin;
    pub const new = gst_insert_bin_new;

    /// This action signal adds the filter like element after any other element
    /// in the bin.
    ///
    /// Same as the `gstinsertbin.InsertBin.signals.append` signal.
    extern fn gst_insert_bin_append(p_self: *InsertBin, p_element: *gst.Element, p_callback: gstinsertbin.InsertBinCallback, p_user_data: ?*anyopaque) void;
    pub const append = gst_insert_bin_append;

    /// This action signal adds the filter like element after the `sibling`
    /// element in the bin.
    ///
    /// Same as the `gstinsertbin.InsertBin.signals.insert`-after signal.
    extern fn gst_insert_bin_insert_after(p_self: *InsertBin, p_element: *gst.Element, p_sibling: *gst.Element, p_callback: gstinsertbin.InsertBinCallback, p_user_data: ?*anyopaque) void;
    pub const insertAfter = gst_insert_bin_insert_after;

    /// This action signal adds the filter like element before the `sibling`
    /// element in the bin.
    ///
    /// Same as the `gstinsertbin.InsertBin.signals.insert`-before signal.
    extern fn gst_insert_bin_insert_before(p_self: *InsertBin, p_element: *gst.Element, p_sibling: *gst.Element, p_callback: gstinsertbin.InsertBinCallback, p_user_data: ?*anyopaque) void;
    pub const insertBefore = gst_insert_bin_insert_before;

    /// This action signal adds the filter like element before any other element
    /// in the bin.
    ///
    /// Same as the `gstinsertbin.InsertBin.signals.prepend` signal.
    extern fn gst_insert_bin_prepend(p_self: *InsertBin, p_element: *gst.Element, p_callback: gstinsertbin.InsertBinCallback, p_user_data: ?*anyopaque) void;
    pub const prepend = gst_insert_bin_prepend;

    /// This action signal removed the filter like element from the bin.
    ///
    /// Same as the `gstinsertbin.InsertBin.signals.remove` signal.
    extern fn gst_insert_bin_remove(p_self: *InsertBin, p_element: *gst.Element, p_callback: gstinsertbin.InsertBinCallback, p_user_data: ?*anyopaque) void;
    pub const remove = gst_insert_bin_remove;

    extern fn gst_insert_bin_get_type() usize;
    pub const getGObjectType = gst_insert_bin_get_type;

    extern fn g_object_ref(p_self: *gstinsertbin.InsertBin) void;
    pub const ref = g_object_ref;

    extern fn g_object_unref(p_self: *gstinsertbin.InsertBin) void;
    pub const unref = g_object_unref;

    pub fn as(p_instance: *InsertBin, comptime P_T: type) *P_T {
        return gobject.ext.as(P_T, p_instance);
    }

    test {
        @setEvalBranchQuota(100_000);
        std.testing.refAllDecls(@This());
    }
};

/// The object class structure.
pub const InsertBinClass = extern struct {
    pub const Instance = gstinsertbin.InsertBin;

    f_parent_class: gst.BinClass,

    pub fn as(p_instance: *InsertBinClass, comptime P_T: type) *P_T {
        return gobject.ext.as(P_T, p_instance);
    }

    test {
        @setEvalBranchQuota(100_000);
        std.testing.refAllDecls(@This());
    }
};

pub const InsertBinPrivate = opaque {
    test {
        @setEvalBranchQuota(100_000);
        std.testing.refAllDecls(@This());
    }
};

/// This is the prototype of callbacks to be called when the operation completes.
/// It could be called at any time, including as a re-entrant call while the
/// operation is requested.
pub const InsertBinCallback = *const fn (p_insertbin: *gstinsertbin.InsertBin, p_element: *gst.Element, p_success: c_int, p_user_data: ?*anyopaque) callconv(.c) void;

test {
    @setEvalBranchQuota(100_000);
    std.testing.refAllDecls(@This());
    std.testing.refAllDecls(ext);
}
