Search code examples
swiftswiftuimenubarextra

ProgressView not showing in MenuBarExtra


The issue

I'm having trouble having a linear ProgressView show in a MenuBarExtra, it would simply not appear.

Apparently, there is no counter-indication indicating that it is impossible to do so but I still fail to implement it.

Here is the minimal code structure:

import SwiftUI
import AppKit

@main
struct Menubar_InfoApp: App {
    @State private var pct: String = "34%"

    var body: some Scene {
        MBE()
    }

    @SceneBuilder
    func MBE() -> some Scene {
        MenuBarExtra() {
            VStack {
                Text("Percentage: \(pct)")
                    .padding()
                
                ProgressView(value: Double(pct.dropLast(1)) ?? 0, total: 100)
                    .progressViewStyle(LinearProgressViewStyle())
                    .padding([.leading, .trailing])
                    .frame(width: 100)
            }
            
        } label: {
            Text("sample")
        }
    }
}

Goal

I'm just looking for a way to have a linear ProgressView in a MenuBarExtra (that has the same appearance and behaviour as one at least - the app being composed a multiple MenuBarExtra elements, the intent would be not to have them overlap) similar to:

Screenshot of an app that has this functionality

What I've tried

  • I don't think the issue is linked with the value itself as I tried setting a hard value (doesn't work).
  • The issue doesn't seem to be linked with the MenuBarExtra being called through a separate function, not directly in the body, but still, even if I move it there it fails to work.

Solution

  • Try this approach adding .menuBarExtraStyle(.window) to your MenuBarExtra{...}. Works for me, tested on macOS 15.2, using Xcode 16.2.

     @SceneBuilder
     func MBE() -> some Scene {
         MenuBarExtra() {
             VStack {
                 Text("Percentage: \(pct)").padding()
                 ProgressView(value: Double(pct.dropLast(1)) ?? 0, total: 100)
                     .progressViewStyle(LinearProgressViewStyle())
                     .padding([.leading, .trailing])
                     .frame(width: 100)
             }
         } label: {
             Text("sample")
         }
         .menuBarExtraStyle(.window) // <-- here
     }