Skip to content

Instantly share code, notes, and snippets.

@Codelaby
Last active February 27, 2025 09:46
Show Gist options
  • Select an option

  • Save Codelaby/52625b07fff3a9f93fcb7aced7cf12ac to your computer and use it in GitHub Desktop.

Select an option

Save Codelaby/52625b07fff3a9f93fcb7aced7cf12ac to your computer and use it in GitHub Desktop.
Navigation UI custom
//
// TranslucentDemo.swift
// FestivES
//
// Created by Codelaby on 27/2/25.
//
import SwiftUI
// MARK: Translucent
extension UIBlurEffect {
static func effect(blurRadius: CGFloat) -> UIBlurEffect? {
let selector = NSSelectorFromString("effectWithBlurRadius:")
guard self.responds(to: selector) else { return nil }
let blurEffect = self.perform(selector, with: blurRadius).takeUnretainedValue()
return blurEffect as? UIBlurEffect
}
}
/// MARK: For apply all UIViewCront
//extension UIViewController {
//
// var topbarHeight: CGFloat {
// let safeAreaTop: CGFloat = view.safeAreaInsets.top
//
// let statusBarHeight: CGFloat
// if #available(iOS 13.0, *) {
// statusBarHeight = view.window?.windowScene?.statusBarManager?.statusBarFrame.height ?? 0.0
// } else {
// statusBarHeight = UIApplication.shared.statusBarFrame.height
// }
//
// let navigationBarHeight = self.navigationController?.navigationBar.frame.height ?? 0.0
// print("Status Bar Height: \(statusBarHeight)")
// print("Navigation Bar Height: \(navigationBarHeight)")
//
// return statusBarHeight + navigationBarHeight + safeAreaTop
// }
//
//}
// MARK: Translucent Top Nav bar
struct TranslucentDemo: View {
init() {
// Customize the navigation bar appearance
let standard = UINavigationBarAppearance()
standard.backgroundColor = .clear
standard.backgroundEffect = UIBlurEffect.effect(blurRadius: 22)
standard.shadowColor = .clear
// Apply the appearance to all navigation bar modes
UINavigationBar.appearance().standardAppearance = standard
UINavigationBar.appearance().compactAppearance = standard
UINavigationBar.appearance().scrollEdgeAppearance = standard
}
var body: some View {
NavigationStack {
ScrollView {
ForEach(0..<3) { _ in
ForEach(ColorDemoModel.allItems) { item in
VStack {
HStack {
ForEach(0..<3) { _ in
Spacer()
Rectangle()
.fill(item.color)
.frame(width: 50, height: 50)
}
Spacer()
}
}
}
}
}
.navigationTitle("Navigation Blur")
#if os(iOS)
.navigationBarTitleDisplayMode(.inline)
#endif
}
}
}
#Preview("Nav Bar") {
TranslucentDemo()
}
// MARK: Translucent Nav Bar & Tab nav
struct TranslucentDemo2: View {
@State private var selectedTab: TabEnum = .listBooks
init() {
// HEADER: Customize the navigation bar
if let blurEffect = UIBlurEffect.effect(blurRadius: 22) {
// Customize the navigation bar appearance
let standard = UINavigationBarAppearance()
standard.backgroundColor = .clear
standard.backgroundEffect = blurEffect
standard.shadowColor = .clear
// Apply the appearance to all navigation bar modes
UINavigationBar.appearance().standardAppearance = standard
UINavigationBar.appearance().compactAppearance = standard
UINavigationBar.appearance().scrollEdgeAppearance = standard
}
// FOOTER: Customize the tab bar
if let blurEffect = UIBlurEffect.effect(blurRadius: 22) {
// Customize the tab bar appearance
let tabBarAppearance = UITabBarAppearance()
tabBarAppearance.backgroundColor = .clear
tabBarAppearance.backgroundEffect = blurEffect
tabBarAppearance.shadowColor = .clear
// Apply the appearance to all navigation tab bar modes
UITabBar.appearance().isTranslucent = true
UITabBar.appearance().backgroundColor = .clear
UITabBar.appearance().scrollEdgeAppearance = tabBarAppearance
UITabBar.appearance().standardAppearance = tabBarAppearance
}
}
var body: some View {
TabView(selection: $selectedTab) {
ForEach(TabEnum.allCases) { tab in
NavigationStack {
VStack {
switch tab {
case .listBooks:
SampleList()
case .listMovies:
SampleList()
case .profile:
SampleList()
}
}
.navigationTitle(tab.description)
#if os(iOS)
.navigationBarTitleDisplayMode(.inline)
#endif
}
.tabItem {
Image(systemName: tab.rawValue)
Text(tab.description)
}
}
}
}
enum TabEnum: String, CaseIterable, Identifiable, CustomStringConvertible {
case listBooks = "book.fill"
case listMovies = "movieclapper.fill"
case profile = "person.fill"
var id: Self { self }
var description: String {
return switch self {
case .listBooks:
"Books"
case .listMovies:
"Movies"
case .profile:
"Profile"
}
}
}
}
// MARK: SampleList
struct SampleList: View {
@State private var selectedItem: ColorDemoModel?
var body: some View {
ScrollView {
VStack {
Text("Large Title").font(.largeTitle)
Image("graphic_color")
.resizable()
.scaledToFit()
Group {
Text("Title").font(.title)
Text("Headline").font(.headline)
Text("Subheadline").font(.subheadline)
Text("Body").font(.body)
Text("Callout").font(.callout)
Text("Footnote").font(.footnote)
Text("Caption").font(.caption)
}
.frame(maxWidth: .infinity, alignment: .leading)
.padding(.horizontal)
ForEach(ColorDemoModel.allItems) { item in
VStack {
HStack {
ForEach(0..<3) { _ in
Spacer()
Rectangle()
.fill(item.color)
.frame(width: 80, height: 50)
.cornerRadius(10)
.onTapGesture {
selectedItem = item // Asigna el item seleccionado
}
}
Spacer()
}
}
}
Image("graphic_color")
.resizable()
.scaledToFit()
Group {
Text("Title").font(.title)
Text("Headline").font(.headline)
Text("Subheadline").font(.subheadline)
Text("Body").font(.body)
Text("Callout").font(.callout)
Text("Footnote").font(.footnote)
Text("Caption").font(.caption)
}
.frame(maxWidth: .infinity, alignment: .trailing)
.padding(.horizontal)
ForEach(ColorDemoModel.allItems) { item in
VStack {
HStack {
ForEach(0..<3) { _ in
Spacer()
Rectangle()
.fill(item.color)
.frame(width: 80, height: 50)
.cornerRadius(10)
.onTapGesture {
selectedItem = item // Asigna el item seleccionado
}
}
Spacer()
}
}
}
}
}
.sheet(item: $selectedItem) { item in
ColorDetailView(item: item)
.presentationDetents([.height(250)])
}
}
}
struct ColorDetailView: View {
let item: ColorDemoModel
@State private var navigationBarHeight: CGFloat = 48
var body: some View {
NavigationStack {
ScrollView {
VStack(spacing: 20) {
Text(item.title)
.font(.largeTitle)
.bold()
Rectangle()
.fill(item.color)
.frame(width: 200, height: 100)
.cornerRadius(10)
Text("Variant of \(item.title)")
.font(.body)
.multilineTextAlignment(.center)
.padding()
Rectangle()
.fill(item.color.secondary)
.frame(width: 200, height: 100)
.cornerRadius(10)
Rectangle()
.fill(item.color.tertiary)
.frame(width: 200, height: 100)
.cornerRadius(10)
Rectangle()
.fill(item.color.quaternary)
.frame(width: 200, height: 100)
.cornerRadius(10)
Rectangle()
.fill(item.color.quinary)
.frame(width: 200, height: 100)
.cornerRadius(10)
}
.frame(maxWidth: .infinity)
//.toolbarBackground(.hidden, for: .navigationBar) // Hide background nav
}
.navigationTitle("Color Detail")
#if os(iOS)
.navigationBarTitleDisplayMode(.inline)
#endif
}
}
}
#Preview("Nav bar & tab nav") {
TranslucentDemo2()
}
// MARK: Sample Model
struct ColorDemoModel: Identifiable, Hashable, Sendable {
let id: UUID = .init()
let title: String
let summary: String
let color: Color
static let allItems: [ColorDemoModel] = [
ColorDemoModel(title: "Red", summary: "This is red", color: .red),
ColorDemoModel(title: "Green", summary: "This is green", color: .green),
ColorDemoModel(title: "Blue", summary: "This is blue", color: .blue),
ColorDemoModel(title: "Yellow", summary: "This is yellow", color: .yellow),
ColorDemoModel(title: "Orange", summary: "This is orange", color: .orange),
ColorDemoModel(title: "Pink", summary: "This is pink", color: .pink),
ColorDemoModel(title: "Mint", summary: "This is Mint", color: .mint),
ColorDemoModel(title: "Teal", summary: "This is teal", color: .teal),
ColorDemoModel(title: "Cyan", summary: "This is cyan", color: .cyan),
ColorDemoModel(title: "Indigo", summary: "This is indigo", color: .indigo),
ColorDemoModel(title: "Purple", summary: "This is purple", color: .purple),
ColorDemoModel(title: "Gray", summary: "This is Gray", color: .gray),
ColorDemoModel(title: "Brown", summary: "This is Brown", color: .brown),
]
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment