diff --git a/kadai1/imgconv/.gitignore b/kadai1/imgconv/.gitignore new file mode 100644 index 0000000..723ef36 --- /dev/null +++ b/kadai1/imgconv/.gitignore @@ -0,0 +1 @@ +.idea \ No newline at end of file diff --git a/kadai1/imgconv/Makefile b/kadai1/imgconv/Makefile new file mode 100644 index 0000000..f8aa0c8 --- /dev/null +++ b/kadai1/imgconv/Makefile @@ -0,0 +1,4 @@ +.PHONY: fmt +fmt: ## Format source code + @which goimports > /dev/null || GO111MODULE=off go get -u golang.org/x/tools/cmd/goimports + @goimports -d -w $(shell find . -type f -name '*.go') \ No newline at end of file diff --git a/kadai1/imgconv/cmd/imgconv/main.go b/kadai1/imgconv/cmd/imgconv/main.go new file mode 100644 index 0000000..d341cf2 --- /dev/null +++ b/kadai1/imgconv/cmd/imgconv/main.go @@ -0,0 +1,34 @@ +package main + +import ( + "flag" + "log" + "os" + + "github.com/gopherdojo/dojo7/kadai1/sabe/pkg/imgconv" +) + +func main() { + if err := exec(); err != nil { + log.Println(err) + os.Exit(1) + } + os.Exit(0) +} + +func exec() error { + var ( + dir string + fromExt string + toExt string + ) + flag.StringVar(&dir, "d", ".", "target directory flag") + flag.StringVar(&fromExt, "f", "jpg", "before convert ext flag") + flag.StringVar(&toExt, "t", "png", "after convert ext flag") + flag.Parse() + imageConfList, err := imgconv.NewImageConfList(dir, fromExt, toExt) + if err != nil { + return err + } + return imageConfList.Convert() +} diff --git a/kadai1/imgconv/go.mod b/kadai1/imgconv/go.mod new file mode 100644 index 0000000..e876026 --- /dev/null +++ b/kadai1/imgconv/go.mod @@ -0,0 +1,3 @@ +module github.com/gopherdojo/dojo7/kadai1/sabe + +go 1.12 diff --git a/kadai1/imgconv/go.sum b/kadai1/imgconv/go.sum new file mode 100644 index 0000000..5726ce0 --- /dev/null +++ b/kadai1/imgconv/go.sum @@ -0,0 +1 @@ +github.com/gopherdojo/dojo7 v0.0.0-20190903074013-69385d40c994 h1:UbdhtSFDdFiSYOb/TkEmlRIUFQRrBlKOzVDY3+SXaSw= diff --git a/kadai1/imgconv/imgconv b/kadai1/imgconv/imgconv new file mode 100755 index 0000000..ced1033 Binary files /dev/null and b/kadai1/imgconv/imgconv differ diff --git a/kadai1/imgconv/pkg/imgconv/convert.go b/kadai1/imgconv/pkg/imgconv/convert.go new file mode 100644 index 0000000..fe88315 --- /dev/null +++ b/kadai1/imgconv/pkg/imgconv/convert.go @@ -0,0 +1,32 @@ +package imgconv + +import ( + "image/gif" + _ "image/gif" + "image/jpeg" + _ "image/jpeg" + "image/png" + _ "image/png" +) + +func (l ImageConfList) Convert() error { + for _, v := range l { + err := v.Convert() + if err != nil { + return err + } + } + return nil +} + +func (imgCf ImageConf) Convert() error { + switch imgCf.ToExt { + case "png": + return png.Encode(imgCf.ToFile, imgCf.DecodedFile) + case "gif": + return gif.Encode(imgCf.ToFile, imgCf.DecodedFile, nil) + case "jpg", "jpeg": + return jpeg.Encode(imgCf.ToFile, imgCf.DecodedFile, nil) + } + return nil +} diff --git a/kadai1/imgconv/pkg/imgconv/main.go b/kadai1/imgconv/pkg/imgconv/main.go new file mode 100644 index 0000000..fc9ceae --- /dev/null +++ b/kadai1/imgconv/pkg/imgconv/main.go @@ -0,0 +1,115 @@ +package imgconv + +import ( + "fmt" + "image" + "io" + "io/ioutil" + "os" + "path/filepath" + "strings" +) + +type ImageConf struct { + FromExt string + ToExt string + DecodedFile image.Image + ToFile io.Writer +} + +type ImageConfList []ImageConf + +// create ImageConfList +func NewImageConfList(dir, fromExt, toExt string) (ImageConfList, error) { + // read dir + paths, err := readDir(dir, strings.ToLower(fromExt)) + if err != nil { + return nil, err + } + imgCfList := make(ImageConfList, len(paths)) + for i, path := range paths { + imgCf := ImageConf{ + FromExt: strings.ToLower(fromExt), + ToExt: strings.ToLower(toExt), + } + + // set decode file + err = imgCf.SetDecodedFile(path) + if err != nil { + return nil, err + } + + // set output file + err = imgCf.SetToFile(getConvertedPath(path, strings.ToLower(toExt))) + if err != nil { + return nil, err + } + + imgCfList[i] = imgCf + } + return imgCfList, nil +} + +// set ImageConf.DecodedFile +func (imgCf *ImageConf) SetDecodedFile(path string) (err error) { + // open file + file, err := os.Open(path) + if err != nil { + return + } + defer func() { + err = file.Close() + }() + + // decode file + img, _, err := image.Decode(file) + if err != nil { + return + } + imgCf.DecodedFile = img + return +} + +// set ImageConf.ToFile +func (imgCf *ImageConf) SetToFile(path string) error { + // create output file + toFile, err := os.Create(path) + if err != nil { + return err + } + imgCf.ToFile = toFile + return nil +} + +// recursively read directory +func readDir(dir, fromExt string) ([]string, error) { + files, err := ioutil.ReadDir(dir) + if err != nil { + return nil, err + } + + var paths []string + for _, file := range files { + if file.IsDir() { + paths2, err := readDir(filepath.Join(dir, file.Name()), fromExt) + if err != nil { + return nil, err + } + paths = append(paths, paths2...) + continue + } + extStart := strings.LastIndex(file.Name(), ".") + if extStart > 0 && strings.ToLower(file.Name()[extStart+1:]) == fromExt { + paths = append(paths, filepath.Join(dir, file.Name())) + } else { + continue + } + } + return paths, nil +} + +// get converted file path +func getConvertedPath(path, toExt string) string { + extStart := strings.LastIndex(path, ".") + return fmt.Sprintf("%s.%s", path[:extStart], toExt) +} diff --git a/kadai1/imgconv/testutils/testdata/test.jpg b/kadai1/imgconv/testutils/testdata/test.jpg new file mode 100644 index 0000000..fe679aa Binary files /dev/null and b/kadai1/imgconv/testutils/testdata/test.jpg differ diff --git a/kadai1/imgconv/testutils/testdata/test.png b/kadai1/imgconv/testutils/testdata/test.png new file mode 100644 index 0000000..66b47c7 Binary files /dev/null and b/kadai1/imgconv/testutils/testdata/test.png differ