タブレット用プログラムの書き止め

android OS & iPadOS の記録。

【Swift P4.6.2】SlideMenu

2025-02-14 21:09:32 | Swift iPadOS用

なんちゃってスライドメニュー

スイッチボタンをタップするとメニューがスクリーン外へ出て行ったり外から入ってきたりする。

作業用のViewとメニュー用のViewを用意して、ContentViewに配置する。
メニューのViewのオフセットを変更するとメニューがスライドする感じで。
x: を変更すると左右にスライド。
y: を変更すると上下にスライド。

 

【MyApp.swift】

@main
struct MyApp: App {
    @StateObject var dataModel = DataModel()
    var body: some Scene {
        WindowGroup {
            ContentView()
                .environmentObject(dataModel)
        }
    }
}


・分かりやすいようにデータをまとめておく。

【DataModel.swift】

class DataModel: ObservableObject {
    @Published var viewWidth: CGFloat = CGFloat.zero
    @Published var viewHeight: CGFloat = CGFloat.zero
    @Published var menuWidth: CGFloat = 200.0
    @Published var menuHeight: CGFloat = 300.0
    @Published var showMenu: Bool = true
    @Published var originalImage: UIImage? = UIImage(named: "Test1") // フォルダに画像ファイルを用意
    
    func MenuWidthOffset() -> CGFloat {
        let value: CGFloat = (menuWidth - viewWidth)/2.0
        return showMenu ? (value) : (value - menuWidth)
    }
    func MenuHeightOffset() -> CGFloat {
        return (menuHeight - viewHeight)/2.0
    }
}


・ContentViewが表示された時に .onAppearで幅と縦を保存しておく。

【ContentView.swift】

struct ContentView: View {
    @EnvironmentObject var dataModel: DataModel
    var body: some View {
        GeometryReader{ geometry in
            ZStack {
                ImageView()
                MenuView()
                    .offset(x:dataModel.MenuWidthOffset(),y:dataModel.MenuHeightOffset())
            }
            .onAppear{
                dataModel.viewWidth = geometry.size.width
                dataModel.viewHeight = geometry.size.height
            }
        }
    }
}


・基本という事でシンプル構成で。

【MenuView.swift】

struct MenuView: View {
    @EnvironmentObject var dataModel: DataModel
    var body: some View {
        HStack(alignment: .top) { 
            ZStack {
                RoundedRectangle(cornerRadius: 15.0) // メニューの下地
                    .fill(Color.white)
                    .frame(width: dataModel.menuWidth, height: dataModel.menuHeight )
                    .shadow(color: .black,radius: 10 , x: 5, y: 5)
                VStack(alignment: .center, content: {
                    Button("Test1") {
                        withAnimation { // Test1、2、画像ファイルをフォルダに用意した
                            dataModel.originalImage = UIImage(named: "Test1")
                        }
                    }
                    Button("Test2") {
                        withAnimation { 
                            dataModel.originalImage = UIImage(named: "Test2")
                        }
                    }
                })
            }
            // メニューの開閉ボタン。矢印を左向き右向きに切り替え
            Image(systemName: dataModel.showMenu ?  "arrowshape.left.fill":"arrowshape.right.fill")
                .background(Color.white)
                .offset(x:dataModel.showMenu ? -40: 10,y:20) // 微調整(笑)
                .gesture(
                    TapGesture()
                        .onEnded{_ in
                            withAnimation { 
                                dataModel.showMenu.toggle()
                            }
                        }
                )
        }
    }
}


・作業用Viewの代わり。

【ImageView.swift】

struct ImageView: View {
    @EnvironmentObject var dataModel: DataModel
    
    var body: some View {
        if let image = dataModel.originalImage { // 画像ファイル読み込みで問題有無の分岐
            Image(uiImage: image)
                .resizable()
                .scaledToFill()
        }
        else {
            Image(systemName: "doc")
            Text("No data")
        }
    }    
}

 

作成アプリを初回起動した時にメニュー位置がバグります。
終了して起動し直すと正常な位置にメニューが表示されます。
作成ツールのバグか、お行儀がよろしくないか、後で調査する。

 

この記事についてブログを書く
  • X
  • Facebookでシェアする
  • はてなブックマークに追加する
  • LINEでシェアする
« 【Swift P4.5.1】SideBar | トップ | 【Swift P4.6.2】 SlideMenu ... »

Swift iPadOS用 」カテゴリの最新記事