import WidgetKit import SwiftUI // V1:写死文案的小组件(Small/Medium/Large + 点击跳转 Home) struct EmotionProvider: TimelineProvider { func placeholder(in context: Context) -> EmotionEntry { EmotionEntry(date: Date()) } func getSnapshot(in context: Context, completion: @escaping (EmotionEntry) -> ()) { completion(EmotionEntry(date: Date())) } func getTimeline(in context: Context, completion: @escaping (Timeline) -> ()) { // V1:内容写死,不做数据更新;给一个较长的刷新间隔(系统仍可能自行调度) let entry = EmotionEntry(date: Date()) let nextUpdate = Calendar.current.date(byAdding: .day, value: 7, to: Date()) ?? Date().addingTimeInterval(60 * 60 * 24 * 7) completion(Timeline(entries: [entry], policy: .after(nextUpdate))) } } struct EmotionEntry: TimelineEntry { let date: Date } struct EmotionWidgetView: View { var entry: EmotionProvider.Entry @Environment(\.widgetFamily) var family private let title = "正念" private let text = "你已经很努力了,今天也值得被温柔对待。" private let deepLink = URL(string: "client:///(app)/home") var body: some View { switch family { case .systemSmall: smallView() case .systemMedium: mediumView() case .systemLarge: largeView() default: smallView() } } private func smallView() -> some View { ZStack { LinearGradient( colors: [Color(red: 0.07, green: 0.09, blue: 0.13), Color(red: 0.15, green: 0.18, blue: 0.26)], startPoint: .topLeading, endPoint: .bottomTrailing ) VStack(alignment: .leading, spacing: 8) { Text(title).font(.headline).foregroundStyle(.white) Text(text) .font(.system(size: 14, weight: .semibold)) .foregroundStyle(Color.white.opacity(0.92)) .lineLimit(4) Spacer(minLength: 0) } .padding(14) } .widgetURL(deepLink) } private func mediumView() -> some View { ZStack { LinearGradient( colors: [Color(red: 0.07, green: 0.09, blue: 0.13), Color(red: 0.10, green: 0.12, blue: 0.18)], startPoint: .topLeading, endPoint: .bottomTrailing ) HStack(spacing: 14) { VStack(alignment: .leading, spacing: 8) { Text(title).font(.headline).foregroundStyle(.white) Text(text) .font(.system(size: 16, weight: .semibold)) .foregroundStyle(Color.white.opacity(0.92)) .lineLimit(5) Spacer(minLength: 0) } Spacer(minLength: 0) } .padding(16) } .widgetURL(deepLink) } private func largeView() -> some View { ZStack { LinearGradient( colors: [Color(red: 0.07, green: 0.09, blue: 0.13), Color(red: 0.17, green: 0.22, blue: 0.32)], startPoint: .topLeading, endPoint: .bottomTrailing ) VStack(alignment: .leading, spacing: 12) { Text(title) .font(.title3) .foregroundStyle(.white) .bold() Text(text) .font(.system(size: 18, weight: .semibold)) .foregroundStyle(Color.white.opacity(0.92)) .lineLimit(7) Spacer(minLength: 0) Text("轻轻呼吸,回到当下") .font(.footnote) .foregroundStyle(Color.white.opacity(0.7)) } .padding(18) } .widgetURL(deepLink) } } struct EmotionWidget: Widget { let kind: String = "EmotionWidget" var body: some WidgetConfiguration { StaticConfiguration(kind: kind, provider: EmotionProvider()) { entry in EmotionWidgetView(entry: entry) } .configurationDisplayName("情绪小组件") .description("一段温柔提醒,陪你回到当下。") .supportedFamilies([.systemSmall, .systemMedium, .systemLarge]) } }