@@ -3,9 +3,12 @@ package app.revanced.patches.youtube.layout.branding.header
3
3
import app.revanced.patcher.patch.PatchException
4
4
import app.revanced.patcher.patch.resourcePatch
5
5
import app.revanced.patcher.patch.stringOption
6
+ import app.revanced.patches.youtube.misc.playservice.is_19_25_or_greater
7
+ import app.revanced.patches.youtube.misc.playservice.versionCheckPatch
6
8
import app.revanced.util.ResourceGroup
7
9
import app.revanced.util.Utils.trimIndentMultiline
8
10
import app.revanced.util.copyResources
11
+ import app.revanced.util.findElementByAttributeValueOrThrow
9
12
import java.io.File
10
13
11
14
private const val HEADER_FILE_NAME = " yt_wordmark_header"
@@ -34,6 +37,8 @@ val changeHeaderPatch = resourcePatch(
34
37
description = " Applies a custom header in the top left corner within the app. Defaults to the ReVanced header." ,
35
38
use = false ,
36
39
) {
40
+ dependsOn(versionCheckPatch)
41
+
37
42
compatibleWith(" com.google.android.youtube" )
38
43
39
44
val header by stringOption(
@@ -79,7 +84,7 @@ val changeHeaderPatch = resourcePatch(
79
84
/* *
80
85
* A function that overwrites both header variants in the target resource directories.
81
86
*/
82
- val overwriteFromTo: ( String , String ) -> Unit = { from: String , to: String ->
87
+ fun overwriteFromTo ( from : String , to : String ) {
83
88
targetResourceDirectories.forEach { directory ->
84
89
variants.forEach { variant ->
85
90
val fromPath = directory.resolve(" ${from} _$variant .png" )
@@ -91,23 +96,28 @@ val changeHeaderPatch = resourcePatch(
91
96
}
92
97
93
98
// Functions to overwrite the header to the different variants.
94
- val toPremium = { overwriteFromTo(PREMIUM_HEADER_FILE_NAME , HEADER_FILE_NAME ) }
95
- val toHeader = { overwriteFromTo(HEADER_FILE_NAME , PREMIUM_HEADER_FILE_NAME ) }
96
- val toReVanced = {
99
+ fun toPremium () { overwriteFromTo(PREMIUM_HEADER_FILE_NAME , HEADER_FILE_NAME ) }
100
+ fun toHeader () { overwriteFromTo(HEADER_FILE_NAME , PREMIUM_HEADER_FILE_NAME ) }
101
+ fun toReVanced () {
97
102
// Copy the ReVanced header to the resource directories.
98
103
targetResourceFiles.forEach { copyResources(" change-header/revanced" , it) }
99
104
100
105
// Overwrite the premium with the custom header as well.
101
106
toHeader()
102
107
}
103
- val toReVancedBorderless = {
108
+ fun toReVancedBorderless () {
104
109
// Copy the ReVanced borderless header to the resource directories.
105
- targetResourceFiles.forEach { copyResources(" change-header/revanced-borderless" , it) }
110
+ targetResourceFiles.forEach {
111
+ copyResources(
112
+ " change-header/revanced-borderless" ,
113
+ it
114
+ )
115
+ }
106
116
107
117
// Overwrite the premium with the custom header as well.
108
118
toHeader()
109
119
}
110
- val toCustom = {
120
+ fun toCustom () {
111
121
val sourceFolders = File (header!! ).listFiles { file -> file.isDirectory }
112
122
? : throw PatchException (" The provided path is not a directory: $header " )
113
123
@@ -136,11 +146,42 @@ val changeHeaderPatch = resourcePatch(
136
146
}
137
147
138
148
when (header) {
139
- HEADER_OPTION -> toHeader
140
- PREMIUM_HEADER_OPTION -> toPremium
141
- REVANCED_HEADER_OPTION -> toReVanced
142
- REVANCED_BORDERLESS_HEADER_OPTION -> toReVancedBorderless
143
- else -> toCustom
144
- }()
149
+ HEADER_OPTION -> toHeader()
150
+ PREMIUM_HEADER_OPTION -> toPremium()
151
+ REVANCED_HEADER_OPTION -> toReVanced()
152
+ REVANCED_BORDERLESS_HEADER_OPTION -> toReVancedBorderless()
153
+ else -> toCustom()
154
+ }
155
+
156
+ // Fix 19.25+ A/B layout with different header icons:
157
+ // yt_ringo2_wordmark_header, yt_ringo2_premium_wordmark_header
158
+ //
159
+ // These images are webp and not png, so overwriting them is not so simple.
160
+ // Instead change styles.xml to use the old drawable resources.
161
+ if (is_19_25_or_greater) {
162
+ document(" res/values/styles.xml" ).use { document ->
163
+ arrayOf(
164
+ " CairoLightThemeRingo2Updates" to variants[0 ],
165
+ " CairoDarkThemeRingo2Updates" to variants[1 ]
166
+ ).forEach { (styleName, theme) ->
167
+ val style = document.childNodes.findElementByAttributeValueOrThrow(
168
+ " name" ,
169
+ styleName,
170
+ )
171
+
172
+ val drawable = " @drawable/${HEADER_FILE_NAME } _${theme} "
173
+
174
+ arrayOf(
175
+ " ytWordmarkHeader" ,
176
+ " ytPremiumWordmarkHeader"
177
+ ).forEach { itemName ->
178
+ style.childNodes.findElementByAttributeValueOrThrow(
179
+ " name" ,
180
+ itemName,
181
+ ).textContent = drawable
182
+ }
183
+ }
184
+ }
185
+ }
145
186
}
146
187
}
0 commit comments