-
-
Notifications
You must be signed in to change notification settings - Fork 5
/
Copy pathoptimization_utils.gradle
153 lines (128 loc) · 4.92 KB
/
optimization_utils.gradle
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
import groovy.json.JsonOutput
import groovy.json.JsonSlurper
import java.nio.file.Files
import java.nio.file.StandardCopyOption
import java.security.MessageDigest
static def calculateMD5Hash(File file) {
MessageDigest md = MessageDigest.getInstance("MD5")
file.withInputStream { md.update(it.bytes) }
byte[] digest = md.digest()
return digest.collect { String.format("%02x", it) }.join()
}
// Load cache with file hashes, to avoid re-optimizing files that are untouched
def getOrCreateCache(String cacheFileName) {
LinkedHashMap<?, ?> cache = [:]
if (file(cacheFileName).exists()) {
cache = new JsonSlurper().parse(file(cacheFileName)) as LinkedHashMap<?, ?>
println("Loaded %s entries from cache (%s).".formatted(cache.size(), cacheFileName))
} else {
file(cacheFileName).createNewFile()
println("Created new cache file: %s".formatted(cacheFileName))
}
return cache
}
processResources {
// Minify JSON files
doLast {
long minifyStart = System.currentTimeMillis()
int filesMinified = 0
int bytesSaved = 0
int bytesProcessed = 0
println("Discovering JSON files in %s...".formatted(outputs.files.asPath))
ConfigurableFileTree jsonFiles = fileTree(dir: outputs.files.asPath, include: ['**/*.json', '**/*.mcmeta'])
int totalFiles = jsonFiles.size()
println("Found %s JSON files in %sms.".formatted(totalFiles, (System.currentTimeMillis() - minifyStart)))
int processedFiles = 0
jsonFiles.each {
File file = it
filesMinified++
long oldLength = file.length()
bytesProcessed += oldLength
file.text = JsonOutput.toJson(new JsonSlurper().parse(file))
bytesSaved += (oldLength - file.length())
processedFiles++
int progress = (int) Math.ceil((processedFiles * 100) / totalFiles)
print("\rMinifying JSON files... %s%% (%s KB processed)".formatted(progress, (bytesProcessed / 1024).round()))
System.out.flush() // Ensure the output is flushed
}
println("\nFinished minifying %s files, saving %s KB in %sms.".formatted(filesMinified, (bytesSaved / 1024).round(), (System.currentTimeMillis() - minifyStart)))
}
}
tasks.named('jar', Jar).configure {
// Run optimize tasks
dependsOn('optimizePng')
dependsOn('optimizeOgg')
}
void optimizeFile(File file, String command, File tempDir = null) {
long size = file.length()
File tempFile = tempDir ? new File(tempDir, file.name) : file
if (command == "optipng") {
exec {
commandLine command, "-q", "-o7", "-zm1-9", "-strip", "all", file
}
} else if (command == "optivorbis") {
exec {
commandLine command, "-q", file, tempFile
}
}
if (tempDir && tempFile.length() < size) {
Files.move(tempFile.toPath(), file.toPath(), StandardCopyOption.REPLACE_EXISTING)
}
}
void optimizeFiles(String fileType, String command, String cacheFileName, String includePattern) {
try {
exec {
commandLine command, "--version"
}
println("\nBeginning optimization of %s files...".formatted(fileType))
long minifyStart = System.currentTimeMillis()
int originalSize = 0
int newSize = 0
int filesOptimized = 0
println("Discovering %s files in %s...".formatted(fileType, sourceSets.main.resources.srcDirs[0]))
ConfigurableFileTree files = fileTree(dir: sourceSets.main.resources.srcDirs[0], include: includePattern)
int totalFiles = files.size()
println("Found %s %s files in %sms.".formatted(totalFiles, fileType, (System.currentTimeMillis() - minifyStart)))
LinkedHashMap<?, ?> cache = getOrCreateCache(cacheFileName)
File tempDir = fileType == "OGG" ? Files.createTempDirectory("optimizeOgg").toFile() : null
int processedFiles = 0
files.each {
originalSize += it.length()
int progress = (int) Math.ceil((processedFiles * 100) / totalFiles)
print("\rOptimizing %s files... %s%% (%s KB processed)".formatted(fileType, progress, (originalSize / 1024).round()))
System.out.flush()
processedFiles++
if (cache.containsKey(it.path) && cache[it.path] == calculateMD5Hash(it)) {
newSize += it.length()
return
} else {
filesOptimized++
optimizeFile(it, command, tempDir)
newSize += it.length()
cache.put(it.path, calculateMD5Hash(it))
}
}
if (tempDir) {
tempDir.delete()
}
println("\nFinished optimizing %s files, saving %s KB in %sms.".formatted(filesOptimized, ((originalSize - newSize) / 1024).toLong(), (System.currentTimeMillis() - minifyStart)))
if (filesOptimized > 0) {
file(cacheFileName).text = JsonOutput.toJson(cache)
println("Saved " + cache.size() + " entries to cache.")
}
} catch (Exception e) {
println("An error occurred while attempting to optimize %s files.".formatted(fileType))
println("%s may not be available. Please consider installing %s, and ensure it is added to your PATH.".formatted(command, command))
e.printStackTrace()
}
}
tasks.register('optimizePng').configure {
doLast {
optimizeFiles("PNG", "optipng", ".optimizePngCache", '**/*.png')
}
}
tasks.register('optimizeOgg').configure {
doLast {
optimizeFiles("OGG", "optivorbis", ".optimizeOggCache", '**/*.ogg')
}
}