@@ -8,7 +8,7 @@ import { createDirectiveQuickPickItem, Directive } from '../../quickpicks/items/
8
8
import { showRepositoryPicker2 } from '../../quickpicks/repositoryPicker' ;
9
9
import { configuration } from '../../system/-webview/configuration' ;
10
10
import { getScopedCounter } from '../../system/counter' ;
11
- import { isPromise } from '../../system/promise' ;
11
+ import { getSettledValue , isPromise } from '../../system/promise' ;
12
12
import { compareSubstringIgnoreCase , equalsIgnoreCase , pluralize } from '../../system/string' ;
13
13
import type { View } from '../viewBase' ;
14
14
import type { PageableViewNode } from './abstract/viewNode' ;
@@ -153,15 +153,20 @@ export class GroupedHeaderNode extends ActionMessageNodeBase {
153
153
parent ,
154
154
view . grouped ? view . name . toLocaleUpperCase ( ) : 'Showing' ,
155
155
view . grouped ? view . description : undefined ,
156
+ undefined ,
157
+ undefined ,
158
+ view . grouped ? `gitlens:views:${ view . type } ` : undefined ,
156
159
) ;
157
160
}
158
161
159
162
override async action ( ) : Promise < void > {
160
- const { openRepositories : repositories } = this . view . container . git ;
161
- if ( repositories . length <= 1 ) return ;
163
+ if ( ! this . view . supportsRepositoryFilter ) return ;
164
+
165
+ const { openRepositories : repos } = this . view . container . git ;
166
+ if ( repos . length <= 1 ) return ;
162
167
163
168
if ( this . view . supportsWorktreeCollapsing ) {
164
- const grouped = await groupRepositories ( repositories ) ;
169
+ const grouped = await groupRepositories ( repos ) ;
165
170
if ( grouped . size <= 1 ) return ;
166
171
}
167
172
@@ -171,7 +176,7 @@ export class GroupedHeaderNode extends ActionMessageNodeBase {
171
176
this . view . container ,
172
177
`Select Repository or Worktree to Show` ,
173
178
`Choose a repository or worktree to show` ,
174
- repositories ,
179
+ repos ,
175
180
{
176
181
picked : isFiltered ? ( await this . view . getFilteredRepositories ( ) ) ?. [ 0 ] : undefined ,
177
182
additionalItem : createDirectiveQuickPickItem ( Directive . ReposAll , ! isFiltered ) ,
@@ -188,9 +193,16 @@ export class GroupedHeaderNode extends ActionMessageNodeBase {
188
193
}
189
194
190
195
override async getTreeItem ( ) : Promise < TreeItem > {
191
- const item = await super . getTreeItem ( ) ;
192
- item . description = await this . getDescription ( ) ;
193
- item . tooltip = await this . getTooltip ( ) ;
196
+ const [ itemResult , reposResult ] = await Promise . allSettled ( [
197
+ super . getTreeItem ( ) ,
198
+ this . view . getFilteredRepositories ( ) ,
199
+ ] ) ;
200
+
201
+ const item = getSettledValue ( itemResult ) ! ;
202
+ const repos = getSettledValue ( reposResult ) ?? [ ] ;
203
+
204
+ item . description = this . getDescription ( repos ) ;
205
+ item . tooltip = this . getTooltip ( repos ) ;
194
206
if ( ! this . view . grouped ) {
195
207
item . iconPath = this . view . isRepositoryFilterActive ( )
196
208
? new ThemeIcon ( 'filter-filled' )
@@ -199,41 +211,35 @@ export class GroupedHeaderNode extends ActionMessageNodeBase {
199
211
return item ;
200
212
}
201
213
202
- private async getDescription ( ) : Promise < string | undefined > {
214
+ private getDescription ( repos : Repository [ ] ) : string | undefined {
203
215
const description = this . getViewDescription ( ) ;
204
- const label = this . getRepositoryFilterLabel ( await this . view . getFilteredRepositories ( ) , true ) ;
216
+ const label = this . getRepositoryFilterLabel ( repos , true ) ;
205
217
return label
206
218
? description
207
219
? `${ description } ${ GlyphChars . Space } ${ GlyphChars . Dot } ${ GlyphChars . Space } ${ label } `
208
220
: label
209
221
: description ;
210
222
}
211
223
212
- private getViewDescription ( ) : string | undefined {
213
- let description = this . view . grouped ? this . view . description : undefined ;
214
- if ( description && ! equalsIgnoreCase ( this . view . name , description ) ) {
215
- const index = compareSubstringIgnoreCase ( description , this . view . name , 0 , this . view . name . length ) ;
216
- description = index === 0 ? description . substring ( this . view . name . length ) . trimStart ( ) : description ;
217
- if ( description . startsWith ( ':' ) ) {
218
- description = description . substring ( 1 ) . trimStart ( ) ;
219
- }
220
- return description ;
221
- }
222
-
223
- return undefined ;
224
- }
225
-
226
- private async getTooltip ( ) : Promise < MarkdownString > {
224
+ private getTooltip ( repos : Repository [ ] ) : MarkdownString {
227
225
const tooltip = new MarkdownString ( ) ;
228
226
if ( this . view . grouped ) {
229
227
tooltip . appendText ( this . view . name ) ;
230
228
const description = this . getViewDescription ( ) ;
231
229
if ( description ) {
232
- tooltip . appendMarkdown ( ` ${ description } ` ) ;
230
+ // TODO: This is so hacky
231
+ if ( description . startsWith ( '(' ) ) {
232
+ tooltip . appendMarkdown ( ` ${ description } ` ) ;
233
+ } else if ( description . startsWith ( GlyphChars . Dot ) ) {
234
+ tooltip . appendMarkdown ( ` ${ GlyphChars . Space } ${ description } ` ) ;
235
+ } else {
236
+ tooltip . appendMarkdown ( `: ${ description } ` ) ;
237
+ }
233
238
}
234
239
}
235
240
236
- const repos = await this . view . getFilteredRepositories ( ) ;
241
+ if ( ! this . view . supportsRepositoryFilter || repos . length <= 1 ) return tooltip ;
242
+
237
243
tooltip . appendMarkdown ( `\n\nShowing ${ this . getRepositoryFilterLabel ( repos , false ) } ` ) ;
238
244
if ( this . view . isRepositoryFilterActive ( ) ) {
239
245
tooltip . appendMarkdown ( '\\\nClick to change filtering' ) ;
@@ -244,26 +250,40 @@ export class GroupedHeaderNode extends ActionMessageNodeBase {
244
250
return tooltip ;
245
251
}
246
252
247
- private getRepositoryFilterLabel ( repositories ?: Repository [ ] , addSuffix ?: boolean ) : string | undefined {
253
+ private getRepositoryFilterLabel ( repos ?: Repository [ ] , addSuffix ?: boolean ) : string | undefined {
248
254
if ( ! this . view . supportsRepositoryFilter ) return undefined ;
249
- if ( ! repositories ?. length ) return undefined ;
255
+ if ( ! repos ?. length ) return undefined ;
250
256
251
257
const prefix = this . view . grouped ? 'showing ' : '' ;
252
258
253
- if ( repositories . length === 1 ) {
259
+ if ( repos . length === 1 ) {
254
260
if ( this . view . repositoryFilter ?. length ) {
255
- return addSuffix ? `${ prefix } ${ repositories [ 0 ] . name } — click to change` : repositories [ 0 ] . name ;
261
+ return addSuffix ? `${ prefix } ${ repos [ 0 ] . name } — click to change` : repos [ 0 ] . name ;
256
262
}
257
263
return undefined ;
258
264
}
259
265
260
266
const mixed = ! this . view . supportsWorktreeCollapsing ;
261
267
262
- const label = pluralize ( mixed ? 'repo / worktree' : 'repo' , repositories . length , {
268
+ const label = pluralize ( mixed ? 'repo / worktree' : 'repo' , repos . length , {
263
269
plural : mixed ? 'repos / worktrees' : 'repos' ,
264
270
} ) ;
265
271
return addSuffix ? `${ prefix } ${ label } — click to filter` : label ;
266
272
}
273
+
274
+ private getViewDescription ( ) : string | undefined {
275
+ let description = this . view . grouped ? this . view . description : undefined ;
276
+ if ( description && ! equalsIgnoreCase ( this . view . name , description ) ) {
277
+ const index = compareSubstringIgnoreCase ( description , this . view . name , 0 , this . view . name . length ) ;
278
+ description = index === 0 ? description . substring ( this . view . name . length ) . trimStart ( ) : description ;
279
+ if ( description . startsWith ( ':' ) ) {
280
+ description = description . substring ( 1 ) . trimStart ( ) ;
281
+ }
282
+ return description ;
283
+ }
284
+
285
+ return undefined ;
286
+ }
267
287
}
268
288
269
289
export abstract class PagerNode extends ViewNode < 'pager' > {
0 commit comments