dacrab 99e31a7bba chore: Refactor build and installation scripts; update configuration and release process
- Enhanced build scripts for improved parallel execution and optimization flags.
- Updated installation scripts for better user experience and error handling.
- Modified .gitignore to include new build artifacts and IDE configurations.
- Updated .goreleaser.yml for better release management and platform support.
- Removed deprecated main.go file and adjusted README for clarity on installation and usage.
- Added support for multiple architectures in build process, including 32-bit and 64-bit for Windows, macOS, and Linux.

These changes streamline the development workflow and enhance the overall usability of the Cursor ID Modifier tool.
2024-12-27 02:05:35 +02:00

111 lines
1.9 KiB
Go

package ui
import (
"fmt"
"sync"
"time"
"github.com/fatih/color"
)
// SpinnerConfig defines spinner configuration
type SpinnerConfig struct {
Frames []string
Delay time.Duration
}
// DefaultSpinnerConfig returns the default spinner configuration
func DefaultSpinnerConfig() *SpinnerConfig {
return &SpinnerConfig{
Frames: []string{"⠋", "⠙", "⠹", "⠸", "⠼", "⠴", "⠦", "⠧", "⠇", "⠏"},
Delay: 100 * time.Millisecond,
}
}
// Spinner represents a progress spinner
type Spinner struct {
config *SpinnerConfig
message string
current int
active bool
stopCh chan struct{}
mu sync.RWMutex
}
// NewSpinner creates a new spinner with the given configuration
func NewSpinner(config *SpinnerConfig) *Spinner {
if config == nil {
config = DefaultSpinnerConfig()
}
return &Spinner{
config: config,
stopCh: make(chan struct{}),
}
}
// SetMessage sets the spinner message
func (s *Spinner) SetMessage(message string) {
s.mu.Lock()
defer s.mu.Unlock()
s.message = message
}
// Start starts the spinner animation
func (s *Spinner) Start() {
s.mu.Lock()
if s.active {
s.mu.Unlock()
return
}
s.active = true
s.mu.Unlock()
go s.run()
}
// Stop stops the spinner animation
func (s *Spinner) Stop() {
s.mu.Lock()
defer s.mu.Unlock()
if !s.active {
return
}
s.active = false
close(s.stopCh)
s.stopCh = make(chan struct{})
fmt.Println()
}
// IsActive returns whether the spinner is currently active
func (s *Spinner) IsActive() bool {
s.mu.RLock()
defer s.mu.RUnlock()
return s.active
}
func (s *Spinner) run() {
ticker := time.NewTicker(s.config.Delay)
defer ticker.Stop()
for {
select {
case <-s.stopCh:
return
case <-ticker.C:
s.mu.RLock()
if !s.active {
s.mu.RUnlock()
return
}
frame := s.config.Frames[s.current%len(s.config.Frames)]
message := s.message
s.current++
s.mu.RUnlock()
fmt.Printf("\r%s %s", color.CyanString(frame), message)
}
}
}