package action

// Not great, but maybe the best way
var CurrentWindowId int = 1000

type WindowBuilder struct {
	window Window
}

// NewWindowBuilder: Creates a new window builder. The window builder implements a
// builder pattern to create a window with the defined properties and values.
func NewWindowBuilder() *WindowBuilder {
	return &WindowBuilder{
		window: Window{
			Id:      0, // This is set when built
			Number:  1, // Ignored for now, will be used for splits
			Buffer:  nil,
			Cursor:  Position{Line: 0, Col: 0},
			Anchor:  Position{Line: 0, Col: 0},
			ScrollY: 0,
			Height:  0,
			Width:   0,
		},
	}
}

// WindowBuilder.WithNumber: Attaches a window number to the window that is being built.
// Window numbers are position-based and change when windows are rearranged. This is
// ignored for now, but will be used when splits are implemented.
func (w *WindowBuilder) WithNumber(number int) *WindowBuilder {
	w.window.Number = number
	return w
}

// WindowBuilder.WithBuffer: Attaches a buffer to the window that is being built. The
// window will display and edit the content of this buffer.
func (w *WindowBuilder) WithBuffer(buffer *Buffer) *WindowBuilder {
	w.window.Buffer = buffer
	return w
}

// WindowBuilder.WithCursor: Sets the cursor position in the window that is being built.
func (w *WindowBuilder) WithCursor(cursor Position) *WindowBuilder {
	w.window.Cursor = cursor
	return w
}

// WindowBuilder.WithCursorPos: Sets the cursor position in the window that is being built.
// This is an alias for WithCursor that accepts line and column separately.
func (w *WindowBuilder) WithCursorPos(line, col int) *WindowBuilder {
	w.window.Cursor = Position{Line: line, Col: col}
	return w
}

// WindowBuilder.WithAnchor: Sets the anchor position in the window that is being built.
// The anchor is used for visual mode selections.
func (w *WindowBuilder) WithAnchor(anchor Position) *WindowBuilder {
	w.window.Anchor = anchor
	return w
}

// WindowBuilder.WithAnchorPos: Sets the anchor position in the window that is being built.
// This is an alias for WithAnchor that accepts line and column separately.
func (w *WindowBuilder) WithAnchorPos(line, col int) *WindowBuilder {
	w.window.Anchor = Position{Line: line, Col: col}
	return w
}

// WindowBuilder.WithScrollY: Sets the vertical scroll offset of the window that is being built.
func (w *WindowBuilder) WithScrollY(scrollY int) *WindowBuilder {
	w.window.ScrollY = scrollY
	return w
}

// WindowBuilder.WithHeight: Sets the height of the window that is being built.
func (w *WindowBuilder) WithHeight(height int) *WindowBuilder {
	w.window.Height = height
	return w
}

// WindowBuilder.WithWidth: Sets the width of the window that is being built.
func (w *WindowBuilder) WithWidth(width int) *WindowBuilder {
	w.window.Width = width
	return w
}

// WindowBuilder.WithDimensions: Sets both width and height of the window that is being built.
// This is a convenience method for setting dimensions in one call.
func (w *WindowBuilder) WithDimensions(width, height int) *WindowBuilder {
	w.window.Width = width
	w.window.Height = height
	return w
}

// WindowBuilder.Build: Build the final window and return it to the caller. Final
// step in the process. This is where the ID is set, so many windows can be "in-progress"
// but the ID will be set when they are built. Meaning, this is not thread safe.
func (w *WindowBuilder) Build() Window {
	w.window.Id = CurrentWindowId
	CurrentWindowId++

	return w.window
}
