2024-02-07 23:50:11 +00:00
|
|
|
// Copyright (c) 2023-2024 David Vogel
|
2023-12-23 00:09:23 +00:00
|
|
|
//
|
|
|
|
// This software is released under the MIT License.
|
|
|
|
// https://opensource.org/licenses/MIT
|
|
|
|
|
2023-12-22 09:13:22 +00:00
|
|
|
package main
|
|
|
|
|
|
|
|
import (
|
2023-12-22 10:03:04 +00:00
|
|
|
"fmt"
|
2023-12-23 00:09:23 +00:00
|
|
|
"image"
|
2023-12-22 09:13:22 +00:00
|
|
|
"image/jpeg"
|
|
|
|
"log"
|
|
|
|
"os"
|
2024-02-07 23:50:11 +00:00
|
|
|
"time"
|
|
|
|
|
|
|
|
"github.com/cheggaaa/pb/v3"
|
2023-12-22 09:13:22 +00:00
|
|
|
)
|
|
|
|
|
2024-02-07 23:50:11 +00:00
|
|
|
func exportJPEGStitchedImage(stitchedImage *StitchedImage, outputPath string, bar *pb.ProgressBar) error {
|
2023-12-22 10:03:04 +00:00
|
|
|
log.Printf("Creating output file %q.", outputPath)
|
2023-12-23 00:23:53 +00:00
|
|
|
|
2024-02-07 23:50:11 +00:00
|
|
|
// If there is a progress bar, start a goroutine that regularly updates it.
|
|
|
|
// We will base the progress on the number of pixels read from the stitched image.
|
|
|
|
if bar != nil {
|
|
|
|
_, max := stitchedImage.Progress()
|
|
|
|
bar.SetRefreshRate(250 * time.Millisecond).SetTotal(int64(max)).Start()
|
|
|
|
|
|
|
|
done := make(chan struct{})
|
|
|
|
defer func() {
|
|
|
|
done <- struct{}{}
|
|
|
|
bar.SetCurrent(bar.Total()).Finish()
|
|
|
|
}()
|
|
|
|
|
|
|
|
go func() {
|
|
|
|
ticker := time.NewTicker(250 * time.Millisecond)
|
|
|
|
for {
|
|
|
|
select {
|
|
|
|
case <-done:
|
|
|
|
return
|
|
|
|
case <-ticker.C:
|
|
|
|
value, max := stitchedImage.Progress()
|
|
|
|
bar.SetCurrent(int64(value)).SetTotal(int64(max))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}()
|
|
|
|
}
|
|
|
|
|
|
|
|
return exportJPEG(stitchedImage, outputPath)
|
2023-12-23 00:23:53 +00:00
|
|
|
}
|
|
|
|
|
2024-02-07 23:50:11 +00:00
|
|
|
func exportJPEG(img image.Image, outputPath string) error {
|
2023-12-22 10:03:04 +00:00
|
|
|
f, err := os.Create(outputPath)
|
2023-12-22 09:13:22 +00:00
|
|
|
if err != nil {
|
2023-12-22 10:03:04 +00:00
|
|
|
return fmt.Errorf("failed to create file: %w", err)
|
2023-12-22 09:13:22 +00:00
|
|
|
}
|
|
|
|
defer f.Close()
|
|
|
|
|
|
|
|
options := &jpeg.Options{
|
|
|
|
Quality: 80,
|
|
|
|
}
|
|
|
|
|
2024-02-07 23:50:11 +00:00
|
|
|
if err := jpeg.Encode(f, img, options); err != nil {
|
2023-12-22 10:03:04 +00:00
|
|
|
return fmt.Errorf("failed to encode image %q: %w", outputPath, err)
|
2023-12-22 09:13:22 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|