// Code generated by girgen. DO NOT EDIT.

package adw

import (
	"runtime"
	"unsafe"

	"github.com/diamondburned/gotk4/pkg/core/gextras"
	coreglib "github.com/diamondburned/gotk4/pkg/core/glib"
	"github.com/diamondburned/gotk4/pkg/gtk/v4"
)

// #include <stdlib.h>
// #include <adwaita.h>
// #include <glib-object.h>
import "C"

// GType values.
var (
	GTypeBreakpointBin = coreglib.Type(C.adw_breakpoint_bin_get_type())
)

func init() {
	coreglib.RegisterGValueMarshalers([]coreglib.TypeMarshaler{
		coreglib.TypeMarshaler{T: GTypeBreakpointBin, F: marshalBreakpointBin},
	})
}

// BreakpointBinOverrides contains methods that are overridable.
type BreakpointBinOverrides struct {
}

func defaultBreakpointBinOverrides(v *BreakpointBin) BreakpointBinOverrides {
	return BreakpointBinOverrides{}
}

// BreakpointBin: widget that changes layout based on available size.
//
// <picture> <source srcset="breakpoint-bin-dark.png"
// media="(prefers-color-scheme: dark)"> <img src="breakpoint-bin.png"
// alt="breakpoint-bin"> </picture>
//
// AdwBreakpointBin provides a way to use breakpoints without window,
// applicationwindow or dialog. It can be useful for limiting breakpoints to a
// single page and similar purposes. Most applications shouldn't need it.
//
// AdwBreakpointBin is similar to bin. It has one child, set via the
// breakpointbin:child property.
//
// When AdwBreakpointBin is resized, its child widget can rearrange its layout
// at specific thresholds.
//
// The thresholds and layout changes are defined via breakpoint objects.
// They can be added using breakpointbin.AddBreakpoint.
//
// Each breakpoint has a condition, specifying the bin's size and/or aspect
// ratio, and setters that automatically set object properties when that
// happens. The breakpoint::apply and breakpoint::unapply can be used instead
// for more complex scenarios.
//
// Breakpoints are only allowed to modify widgets inside the AdwBreakpointBin,
// but not on the AdwBreakpointBin itself or any other widgets.
//
// If multiple breakpoints can be used for the current size, the last
// one is always picked. The current breakpoint can be tracked using the
// breakpointbin:current-breakpoint property.
//
// If none of the breakpoints can be used, that property will be set to NULL,
// and the original property values will be used instead.
//
// # Minimum Size
//
// Adding a breakpoint to AdwBreakpointBin will result in it having no minimum
// size. The gtk.Widget:width-request and gtk.Widget:height-request properties
// must always be set when using breakpoints, indicating the smallest size you
// want to support.
//
// The minimum size and breakpoint conditions must be carefully selected so
// that the child widget completely fits. If it doesn't, it will overflow and a
// warning message will be printed.
//
// When choosing minimum size, consider translations and text scale factor
// changes. Make sure to leave enough space for text labels, and enable
// ellipsizing or wrapping if they might not fit.
//
// For gtk.Label this can be done via gtk.Label:ellipsize, or via gtk.Label:wrap
// together with gtk.Label:wrap-mode.
//
// For buttons, use gtk.Button:can-shrink, gtk.MenuButton:can-shrink,
// adw.SplitButton:can-shrink, or adw.ButtonContent:can-shrink.
//
// Example
//
//	GtkWidget *bin, *child;
//	AdwBreakpoint *breakpoint;
//
//	bin = adw_breakpoint_bin_new ();
//	gtk_widget_set_size_request (bin, 150, 150);
//
//	child = gtk_label_new ("Wide");
//	gtk_label_set_ellipsize (GTK_LABEL (label), PANGO_ELLIPSIZE_END);
//	gtk_widget_add_css_class (child, "title-1");
//	adw_breakpoint_bin_set_child (ADW_BREAKPOINT_BIN (bin), child);
//
//	breakpoint = adw_breakpoint_new (adw_breakpoint_condition_parse ("max-width: 200px"));
//	adw_breakpoint_add_setters (breakpoint,
//	                            G_OBJECT (child), "label", "Narrow",
//	                            NULL);
//	adw_breakpoint_bin_add_breakpoint (ADW_BREAKPOINT_BIN (bin), breakpoint);
//
// The bin has a single label inside it, displaying "Wide". When the bin's width
// is smaller than or equal to 200px, it changes to "Narrow".
//
// # AdwBreakpointBin as GtkBuildable
//
// AdwBreakpointBin allows adding AdwBreakpoint objects as children.
//
// Example of an AdwBreakpointBin UI definition:
//
//	<object class="AdwBreakpointBin">
//	  <property name="width-request">150</property>
//	  <property name="height-request">150</property>
//	  <property name="child">
//	    <object class="GtkLabel" id="child">
//	      <property name="label">Wide</property>
//	      <property name="ellipsize">end</property>
//	      <style>
//	        <class name="title-1"/>
//	      </style>
//	    </object>
//	  </property>
//	  <child>
//	    <object class="AdwBreakpoint">
//	      <condition>max-width: 200px</condition>
//	      <setter object="child" property="label">Narrow</setter>
//	    </object>
//	  </child>
//	</object>
//
// See breakpoint documentation for details.
type BreakpointBin struct {
	_ [0]func() // equal guard
	gtk.Widget
}

var (
	_ gtk.Widgetter = (*BreakpointBin)(nil)
)

func init() {
	coreglib.RegisterClassInfo[*BreakpointBin, *BreakpointBinClass, BreakpointBinOverrides](
		GTypeBreakpointBin,
		initBreakpointBinClass,
		wrapBreakpointBin,
		defaultBreakpointBinOverrides,
	)
}

func initBreakpointBinClass(gclass unsafe.Pointer, overrides BreakpointBinOverrides, classInitFunc func(*BreakpointBinClass)) {
	if classInitFunc != nil {
		class := (*BreakpointBinClass)(gextras.NewStructNative(gclass))
		classInitFunc(class)
	}
}

func wrapBreakpointBin(obj *coreglib.Object) *BreakpointBin {
	return &BreakpointBin{
		Widget: gtk.Widget{
			InitiallyUnowned: coreglib.InitiallyUnowned{
				Object: obj,
			},
			Object: obj,
			Accessible: gtk.Accessible{
				Object: obj,
			},
			Buildable: gtk.Buildable{
				Object: obj,
			},
			ConstraintTarget: gtk.ConstraintTarget{
				Object: obj,
			},
		},
	}
}

func marshalBreakpointBin(p uintptr) (interface{}, error) {
	return wrapBreakpointBin(coreglib.ValueFromNative(unsafe.Pointer(p)).Object()), nil
}

// NewBreakpointBin creates a new AdwBreakpointBin.
//
// The function returns the following values:
//
//   - breakpointBin: newly created AdwBreakpointBin.
func NewBreakpointBin() *BreakpointBin {
	var _cret *C.GtkWidget // in

	_cret = C.adw_breakpoint_bin_new()

	var _breakpointBin *BreakpointBin // out

	_breakpointBin = wrapBreakpointBin(coreglib.Take(unsafe.Pointer(_cret)))

	return _breakpointBin
}

// AddBreakpoint adds breakpoint to self.
//
// The function takes the following parameters:
//
//   - breakpoint to add.
func (self *BreakpointBin) AddBreakpoint(breakpoint *Breakpoint) {
	var _arg0 *C.AdwBreakpointBin // out
	var _arg1 *C.AdwBreakpoint    // out

	_arg0 = (*C.AdwBreakpointBin)(unsafe.Pointer(coreglib.InternObject(self).Native()))
	_arg1 = (*C.AdwBreakpoint)(unsafe.Pointer(coreglib.InternObject(breakpoint).Native()))
	C.g_object_ref(C.gpointer(coreglib.InternObject(breakpoint).Native()))

	C.adw_breakpoint_bin_add_breakpoint(_arg0, _arg1)
	runtime.KeepAlive(self)
	runtime.KeepAlive(breakpoint)
}

// Child gets the child widget of self.
//
// The function returns the following values:
//
//   - widget (optional): child widget of self.
func (self *BreakpointBin) Child() gtk.Widgetter {
	var _arg0 *C.AdwBreakpointBin // out
	var _cret *C.GtkWidget        // in

	_arg0 = (*C.AdwBreakpointBin)(unsafe.Pointer(coreglib.InternObject(self).Native()))

	_cret = C.adw_breakpoint_bin_get_child(_arg0)
	runtime.KeepAlive(self)

	var _widget gtk.Widgetter // out

	if _cret != nil {
		{
			objptr := unsafe.Pointer(_cret)

			object := coreglib.Take(objptr)
			casted := object.WalkCast(func(obj coreglib.Objector) bool {
				_, ok := obj.(gtk.Widgetter)
				return ok
			})
			rv, ok := casted.(gtk.Widgetter)
			if !ok {
				panic("no marshaler for " + object.TypeFromInstance().String() + " matching gtk.Widgetter")
			}
			_widget = rv
		}
	}

	return _widget
}

// CurrentBreakpoint gets the current breakpoint.
//
// The function returns the following values:
//
//   - breakpoint (optional): current breakpoint.
func (self *BreakpointBin) CurrentBreakpoint() *Breakpoint {
	var _arg0 *C.AdwBreakpointBin // out
	var _cret *C.AdwBreakpoint    // in

	_arg0 = (*C.AdwBreakpointBin)(unsafe.Pointer(coreglib.InternObject(self).Native()))

	_cret = C.adw_breakpoint_bin_get_current_breakpoint(_arg0)
	runtime.KeepAlive(self)

	var _breakpoint *Breakpoint // out

	if _cret != nil {
		_breakpoint = wrapBreakpoint(coreglib.Take(unsafe.Pointer(_cret)))
	}

	return _breakpoint
}

// RemoveBreakpoint removes breakpoint from self.
//
// The function takes the following parameters:
//
//   - breakpoint to remove.
func (self *BreakpointBin) RemoveBreakpoint(breakpoint *Breakpoint) {
	var _arg0 *C.AdwBreakpointBin // out
	var _arg1 *C.AdwBreakpoint    // out

	_arg0 = (*C.AdwBreakpointBin)(unsafe.Pointer(coreglib.InternObject(self).Native()))
	_arg1 = (*C.AdwBreakpoint)(unsafe.Pointer(coreglib.InternObject(breakpoint).Native()))

	C.adw_breakpoint_bin_remove_breakpoint(_arg0, _arg1)
	runtime.KeepAlive(self)
	runtime.KeepAlive(breakpoint)
}

// SetChild sets the child widget of self.
//
// The function takes the following parameters:
//
//   - child (optional) widget.
func (self *BreakpointBin) SetChild(child gtk.Widgetter) {
	var _arg0 *C.AdwBreakpointBin // out
	var _arg1 *C.GtkWidget        // out

	_arg0 = (*C.AdwBreakpointBin)(unsafe.Pointer(coreglib.InternObject(self).Native()))
	if child != nil {
		_arg1 = (*C.GtkWidget)(unsafe.Pointer(coreglib.InternObject(child).Native()))
	}

	C.adw_breakpoint_bin_set_child(_arg0, _arg1)
	runtime.KeepAlive(self)
	runtime.KeepAlive(child)
}
