From b6b2da17ee1637b3a4565e994e1be9eed6bcc94d Mon Sep 17 00:00:00 2001 From: MING <54872601+1998code@users.noreply.github.com> Date: Mon, 9 Jun 2025 22:56:38 +0800 Subject: [PATCH 1/2] Restructure system --- Demo/What's New?.xcodeproj/project.pbxproj | 8 +- Demo/What's New?/en.lproj/data.json | 24 +- Demo/What's New?/ja.lproj/data.json | 24 +- Demo/What's New?/ko.lproj/data.json | 24 +- Demo/What's New?/zh-Hans.lproj/data.json | 26 +- Demo/What's New?/zh-Hant.lproj/data.json | 26 +- Package.swift | 16 +- README.md | 350 +++++++++++++-- README/README_hc.md | 185 ++++++-- README/README_ja.md | 117 +++-- README/README_ko.md | 117 +++-- README/README_tc.md | 117 +++-- README/README_zh.md | 117 +++-- Sources/SwiftNEW/Bundle+Ext.swift | 7 + .../Extensions/SwiftNEW+Functions.swift | 85 ++++ Sources/SwiftNEW/SwiftNEW.swift | 409 +----------------- .../Views/Components/ButtonComponents.swift | 93 ++++ .../Views/Components/HeaderView.swift | 47 ++ .../Views/Sheets/CurrentVersionSheet.swift | 109 +++++ .../SwiftNEW/Views/Sheets/HistorySheet.swift | 98 +++++ Sources/SwiftNEW/Views/SwiftNEW+View.swift | 70 +++ 21 files changed, 1435 insertions(+), 634 deletions(-) create mode 100644 Sources/SwiftNEW/Extensions/SwiftNEW+Functions.swift create mode 100644 Sources/SwiftNEW/Views/Components/ButtonComponents.swift create mode 100644 Sources/SwiftNEW/Views/Components/HeaderView.swift create mode 100644 Sources/SwiftNEW/Views/Sheets/CurrentVersionSheet.swift create mode 100644 Sources/SwiftNEW/Views/Sheets/HistorySheet.swift create mode 100644 Sources/SwiftNEW/Views/SwiftNEW+View.swift diff --git a/Demo/What's New?.xcodeproj/project.pbxproj b/Demo/What's New?.xcodeproj/project.pbxproj index 94508a6..febd53c 100644 --- a/Demo/What's New?.xcodeproj/project.pbxproj +++ b/Demo/What's New?.xcodeproj/project.pbxproj @@ -313,7 +313,7 @@ ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor; CODE_SIGN_ENTITLEMENTS = "What's New?/What_s_New_.entitlements"; CODE_SIGN_STYLE = Automatic; - CURRENT_PROJECT_VERSION = 15; + CURRENT_PROJECT_VERSION = 16; DEVELOPMENT_ASSET_PATHS = "\"What's New?/Preview Content\""; DEVELOPMENT_TEAM = ""; ENABLE_HARDENED_RUNTIME = YES; @@ -327,7 +327,7 @@ LD_RUNPATH_SEARCH_PATHS = "@executable_path/Frameworks"; "LD_RUNPATH_SEARCH_PATHS[sdk=macosx*]" = "@executable_path/../Frameworks"; MACOSX_DEPLOYMENT_TARGET = 14.0; - MARKETING_VERSION = 6.0; + MARKETING_VERSION = 6.1; PRODUCT_BUNDLE_IDENTIFIER = io.startway.WhatsNew; PRODUCT_NAME = "$(TARGET_NAME)"; SDKROOT = auto; @@ -350,7 +350,7 @@ ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor; CODE_SIGN_ENTITLEMENTS = "What's New?/What_s_New_.entitlements"; CODE_SIGN_STYLE = Automatic; - CURRENT_PROJECT_VERSION = 15; + CURRENT_PROJECT_VERSION = 16; DEVELOPMENT_ASSET_PATHS = "\"What's New?/Preview Content\""; DEVELOPMENT_TEAM = ""; ENABLE_HARDENED_RUNTIME = YES; @@ -364,7 +364,7 @@ LD_RUNPATH_SEARCH_PATHS = "@executable_path/Frameworks"; "LD_RUNPATH_SEARCH_PATHS[sdk=macosx*]" = "@executable_path/../Frameworks"; MACOSX_DEPLOYMENT_TARGET = 14.0; - MARKETING_VERSION = 6.0; + MARKETING_VERSION = 6.1; PRODUCT_BUNDLE_IDENTIFIER = io.startway.WhatsNew; PRODUCT_NAME = "$(TARGET_NAME)"; SDKROOT = auto; diff --git a/Demo/What's New?/en.lproj/data.json b/Demo/What's New?/en.lproj/data.json index cccc5d7..7800a0c 100644 --- a/Demo/What's New?/en.lproj/data.json +++ b/Demo/What's New?/en.lproj/data.json @@ -1,13 +1,13 @@ [ { - "version": "6.0", - "subVersion": "6.0.0", + "version": "6.1", + "subVersion": "6.1.0", "new": [ { - "icon": "wineglass", - "title": "Glass", - "subtitle": "Effect", - "body": "Coming Soon!" + "icon": "hammer", + "title": "Project", + "subtitle": "Restructure", + "body": "Seperate files and folders for better maintenance." }, { "icon": "macpro.gen3.server", @@ -23,6 +23,18 @@ } ] }, + { + "version": "6.0", + "subVersion": "6.0.0", + "new": [ + { + "icon": "wineglass", + "title": "Glass", + "subtitle": "Effect", + "body": "Available now!" + } + ] + }, { "version": "5.5", "subVersion": "5.5.0", diff --git a/Demo/What's New?/ja.lproj/data.json b/Demo/What's New?/ja.lproj/data.json index bd2d4bb..930b7a9 100644 --- a/Demo/What's New?/ja.lproj/data.json +++ b/Demo/What's New?/ja.lproj/data.json @@ -1,13 +1,13 @@ [ { - "version": "6.0", - "subVersion": "6.0.0", + "version": "6.1", + "subVersion": "6.1.0", "new": [ { - "icon": "wineglass", - "title": "ガラス", - "subtitle": "エフェクト", - "body": "近日公開予定!" + "icon": "hammer", + "title": "プロジェクト", + "subtitle": "リストラクチャ", + "body": "より良いメンテナンスのためのファイルとフォルダの分離。" }, { "icon": "macpro.gen3.server", @@ -23,6 +23,18 @@ } ] }, + { + "version": "6.0", + "subVersion": "6.0.0", + "new": [ + { + "icon": "wineglass", + "title": "ガラス", + "subtitle": "エフェクト", + "body": "利用可能になりました!" + } + ] + }, { "version": "5.5", "subVersion": "5.5.0", diff --git a/Demo/What's New?/ko.lproj/data.json b/Demo/What's New?/ko.lproj/data.json index 1838e9b..d08f455 100644 --- a/Demo/What's New?/ko.lproj/data.json +++ b/Demo/What's New?/ko.lproj/data.json @@ -1,13 +1,13 @@ [ { - "version": "6.0", - "subVersion": "6.0.0", + "version": "6.1", + "subVersion": "6.1.0", "new": [ { - "icon": "wineglass", - "title": "유리", - "subtitle": "효과", - "body": "곧 출시 예정!" + "icon": "hammer", + "title": "프로젝트", + "subtitle": "재구성", + "body": "더 나은 유지보수를 위한 파일과 폴더 분리." }, { "icon": "macpro.gen3.server", @@ -23,6 +23,18 @@ } ] }, + { + "version": "6.0", + "subVersion": "6.0.0", + "new": [ + { + "icon": "wineglass", + "title": "유리", + "subtitle": "효과", + "body": "지금 사용 가능!" + } + ] + }, { "version": "5.5", "subVersion": "5.5.0", diff --git a/Demo/What's New?/zh-Hans.lproj/data.json b/Demo/What's New?/zh-Hans.lproj/data.json index 88857f5..e6bcbe6 100644 --- a/Demo/What's New?/zh-Hans.lproj/data.json +++ b/Demo/What's New?/zh-Hans.lproj/data.json @@ -1,13 +1,13 @@ [ { - "version": "6.0", - "subVersion": "6.0.0", + "version": "6.1", + "subVersion": "6.1.0", "new": [ { - "icon": "wineglass", - "title": "玻璃", - "subtitle": "效果", - "body": "即将推出!" + "icon": "hammer", + "title": "项目", + "subtitle": "重构", + "body": "分离文件和文件夹以便更好地维护。" }, { "icon": "macpro.gen3.server", @@ -19,7 +19,19 @@ "icon": "arrow.triangle.pull", "title": "贡献", "subtitle": "一起", - "body": "提出请求,变得更好! 🎉" + "body": "提出请求,让每个人都变得更好! 🎉" + } + ] + }, + { + "version": "6.0", + "subVersion": "6.0.0", + "new": [ + { + "icon": "wineglass", + "title": "玻璃", + "subtitle": "效果", + "body": "现已推出!" } ] }, diff --git a/Demo/What's New?/zh-Hant.lproj/data.json b/Demo/What's New?/zh-Hant.lproj/data.json index 708cd46..a2e0291 100644 --- a/Demo/What's New?/zh-Hant.lproj/data.json +++ b/Demo/What's New?/zh-Hant.lproj/data.json @@ -1,13 +1,13 @@ [ { - "version": "6.0", - "subVersion": "6.0.0", + "version": "6.1", + "subVersion": "6.1.0", "new": [ { - "icon": "wineglass", - "title": "玻璃", - "subtitle": "效果", - "body": "即將推出!" + "icon": "hammer", + "title": "專案", + "subtitle": "重構", + "body": "分離檔案和資料夾以便更好地維護。" }, { "icon": "macpro.gen3.server", @@ -19,7 +19,19 @@ "icon": "arrow.triangle.pull", "title": "貢獻", "subtitle": "一起", - "body": "提出請求,變得更好! 🎉" + "body": "提出請求,讓每個人都變得更好! 🎉" + } + ] + }, + { + "version": "6.0", + "subVersion": "6.0.0", + "new": [ + { + "icon": "wineglass", + "title": "玻璃", + "subtitle": "效果", + "body": "現已推出!" } ] }, diff --git a/Package.swift b/Package.swift index 0489370..111f39e 100644 --- a/Package.swift +++ b/Package.swift @@ -11,7 +11,6 @@ let package = Package( defaultLocalization: "en", platforms: [ .iOS(.v15), - .watchOS(.v8), .macOS(.v14), .visionOS(.v1), .tvOS(.v17) @@ -22,17 +21,20 @@ let package = Package( targets: ["SwiftNEW"]), ], dependencies: [ - .package(name: "SwiftVB", url: "https://github.com/1998code/SwiftVBKit.git", .upToNextMinor(from: "1.4.0")), - .package(name: "Drops", url: "https://github.com/omaralbeik/Drops.git", .upToNextMinor(from: "1.7.0")), - .package(name: "SwiftGlass", url: "https://github.com/1998code/SwiftGlass.git", .upToNextMinor(from: "1.8.0")) + .package(url: "https://github.com/1998code/SwiftVBKit.git", .upToNextMinor(from: "1.4.0")), + .package(url: "https://github.com/omaralbeik/Drops.git", .upToNextMinor(from: "1.7.0")), + .package(url: "https://github.com/1998code/SwiftGlass.git", .upToNextMinor(from: "1.8.0")) ], targets: [ .target( name: "SwiftNEW", dependencies: [ - "SwiftVB", - "Drops", - "SwiftGlass" + .product(name: "SwiftVB", package: "SwiftVBKit"), + .product(name: "Drops", package: "Drops"), + .product(name: "SwiftGlass", package: "SwiftGlass") + ], + resources: [ + .process("Localizable.xcstrings") ] ) ] diff --git a/README.md b/README.md index a822a93..e0ef61f 100644 --- a/README.md +++ b/README.md @@ -12,57 +12,249 @@ ![image](https://github.com/user-attachments/assets/0a5de416-f4cd-41b5-8060-f839f2e7286a) -## Features -| Description | Version | -|-----------------------------------------------------------------|-----------| -| Mesh Gradient and Linear Gradient Background | 5.3.0 | -| Apple visionOS & Vision Pro | 4.1.0 | -| Auto trigger/pop-up .sheet when Version / Build changes | 4.0.0 | -| Version Number in x.y.z and/or x.y | 4.0.0 | -| Remote Drop Notification | 3.5.0 | -| Firebase Real-Time Database | 3.0.0 | -| Remote JSON File | 3.0.0 | -| Versioning + View History | 2.0.0 | - -## Preview +A modern, SwiftUI-native "What's New" presentation framework for iOS, macOS, tvOS, and visionOS apps. Built with a modular architecture for easy customization and maintenance. + +## 📋 Table of Contents + +- [🎨 Preview & Gallery](#-preview--gallery) +- [✨ Features](#-features) +- [🎯 Quick Start](#-quick-start) +- [⚙️ Configuration Parameters](#️-configuration-parameters) +- [🔧 Data Configuration](#-data-configuration) +- [🛠️ Platform Compatibility](#️-platform-compatibility) +- [🔧 Troubleshooting](#-troubleshooting) +- [📂 Project Structure](#-project-structure) +- [Contributing](#contributing) + +## 🎨 Preview & Gallery + ![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) -## Gallery +### Light & Dark Mode ![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) -------------- | ------------ +:---: | :---: Light Native | Dark Native -![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) ![CleanShot 2022-12-11 at 12 49 12@2x](https://user-images.githubusercontent.com/54872601/206887046-8ec82853-4e32-4a07-8b64-4cc984e7ec90.png) -------------- | ------------ -History View (2.0.0) | App Icon (3.9.6) [Vertical / Horizontal] - -![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM | -------------- | ------------ -Support VisionOS (4.1.0 or above) | Mesh Gradient Background (5.3.0 or above) - -## Example -Path: `./Demo` (Xcode Project) - -## Version -![GitHub release (latest by date)](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?color=g&label=STABLE&style=for-the-badge) -![GitHub release (latest by date including pre-releases)](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?color=green&include_prereleases&label=BETA&style=for-the-badge) - -![swiftui-128x128_2x](https://user-images.githubusercontent.com/54872601/173193069-2eb486b0-1347-4448-ac2b-235b8f2f1bb0.png) - -## Tested Platforms and Environment -### Local -Tested on | Latest | Compatible ---------- | ------ | ---------- -iOS | 18.5 | > 15.0 -iPadOS | 18.5 | > 15.0 -macOS | 15.5 | > 14.0 -visionOS | 2 | > 1 -tvOS | 18.5 | > 17.0 -### Cloud -Tested on | Compatible ---------- | ---------- -Xcode | > 13.4 (13F17a) -macOS | > 12.3.1 (21E258) +### Advanced Features +![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) +:---: | :---: +History View (2.0.0+) | App Icon Support (3.9.6+) + +### Platform Support +![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM +:---: | :---: +VisionOS Support (4.1.0+) | Mesh Gradient Background (5.3.0+) + +## ✨ Features + +| Feature | Version | Description | +|---------|---------|-------------| +| 🎨 **Mesh Gradient & Linear Gradient** | 5.3.0 | Beautiful gradient backgrounds | +| 🥽 **Apple visionOS & Vision Pro** | 4.1.0 | Full visionOS support | +| 🔄 **Auto-trigger on Version Change** | 4.0.0 | Automatically shows when app version or build changes | +| 📊 **Flexible Version Numbers** | 4.0.0 | Supports x.y.z and x.y version formats | +| 📱 **Remote Drop Notifications** | 3.5.0 | iOS notification-style alerts | +| 🔥 **Firebase Real-Time Database** | 3.0.0 | Live content updates | +| 🌐 **Remote JSON Support** | 3.0.0 | Load content from any URL | +| 📚 **Version History** | 2.0.0 | View all previous releases | + +## 🎯 Quick Start + +### 1. Installation + +#### Swift Package Manager +``` +https://github.com/1998code/SwiftNEWKit +``` + +### 2. Basic Usage + +```swift +import SwiftNEW + +struct ContentView: View { + @State private var showNew = false + + var body: some View { + VStack { + // Your app content + Text("My App") + + Button("Show What's New") { + showNew = true + } + } + .sheet(isPresented: $showNew) { + SwiftNEW(show: $showNew) + } + } +} +``` + +### 3. Advanced Configuration + +```swift +struct ContentView: View { + @State private var showNew = false + @State private var color: Color = .blue + @State private var align: HorizontalAlignment = .center + + var body: some View { + SwiftNEW( + show: $showNew, + align: $align, + color: $color, + size: .constant("normal"), + label: .constant("What's New"), + history: .constant(true), + data: .constant("data"), // or remote URL + mesh: .constant(true) + ) + } +} +``` + +## 🎨 Preview & Gallery + +![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) + +### Light & Dark Mode +![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) +:---: | :---: +Light Native | Dark Native + +### Advanced Features +![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) +:---: | :---: +History View (2.0.0+) | App Icon Support (3.9.6+) + +### Platform Support +![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM +:---: | :---: +VisionOS Support (4.1.0+) | Mesh Gradient Background (5.3.0+) + +## ⚙️ Configuration Parameters + +| Parameter | Type | Default | Options | Description | +|-----------|------|---------|---------|-------------| +| `show` * | `Binding` | `false` | `true`, `false` | Controls sheet presentation | +| `align` | `Binding` | `.center` | `.leading`, `.center`, `.trailing` | Content alignment | +| `color` | `Binding` | `.accentColor` | Any Color | Primary theme color | +| `size` | `Binding` | `"simple"` | `"invisible"`, `"mini"`, `"simple"`, `"normal"` | Button size variant | +| `labelColor` | `Binding` | System Background | Any Color | Button text color | +| `label` | `Binding` | `"Show Release Note"` | Any String | Button display text | +| `labelImage` | `Binding` | `"arrow.up.circle.fill"` | Any SF Symbol | Button icon | +| `history` | `Binding` | `true` | `true`, `false` | Enable history view | +| `data` | `Binding` | `"data"` | Local filename or URL | Data source location | +| `showDrop` | `Binding` | `false` | `true`, `false` | iOS drop notification style | +| `mesh` | `Binding` | `true` | `true`, `false` | Enable gradient background | +| `specialEffect` | `Binding` | `""` | `"Christmas"`, `""` | Special animation effects | + +*Required parameter + +### Parameter Usage Examples + +```swift +// Minimal configuration +SwiftNEW(show: $showNew) + +// Custom styling +SwiftNEW( + show: $showNew, + color: .constant(.blue), + mesh: .constant(false) +) + +// Remote data source +SwiftNEW( + show: $showNew, + data: .constant("https://api.example.com/releases.json") +) + +// Complete customization +SwiftNEW( + show: $showNew, + align: .constant(.leading), + color: .constant(.purple), + size: .constant("normal"), + label: .constant("See Updates"), + labelImage: .constant("star.fill"), + history: .constant(true), + data: .constant("releases"), + mesh: .constant(true), + specialEffect: .constant("Christmas") +) +``` + +## 🔧 Data Configuration + +### Local JSON File +Create a `data.json` file in your app bundle: + +```json +[ + { + "version": "1.2", + "new": [ + { + "icon": "hammer.fill", + "title": "Bug Fixes", + "subtitle": "Stability Improvements", + "body": "Fixed crashes and improved performance across all platforms" + }, + { + "icon": "sparkles", + "title": "New Features", + "subtitle": "Enhanced Experience", + "body": "Added new animations and improved user interface" + } + ] + } +] +``` + +### Remote JSON/Firebase +```swift +SwiftNEW( + show: $showNew, + data: .constant("https://your-server.com/releases.json") +) +``` + +### Firebase Realtime Database +```swift +SwiftNEW( + show: $showNew, + data: .constant("https://your-project.firebaseio.com/releases.json") +) +``` + +## 🛠️ Platform Compatibility + +| Platform | Latest Tested | Minimum Required | Key Features | +|----------|---------------|------------------|--------------| +| **iOS** | 18.5 | 15.0+ | Full feature support, drop notifications | +| **iPadOS** | 18.5 | 15.0+ | Optimized layouts, full feature support | +| **macOS** | 15.5 | 14.0+ | Native macOS styling, full feature support | +| **visionOS** | 2.0 | 1.0+ | Spatial computing support, immersive UI | +| **tvOS** | 18.5 | 17.0+ | Remote-friendly navigation, adapted layouts | + +### Development Environment +| Tool | Version | Notes | +|------|---------|-------| +| **Xcode** | 13.4+ (13F17a) | Minimum required for package resolution | +| **macOS** | 12.3.1+ (21E258) | Host development environment | +| **Swift** | 5.9+ / 6.1+ | Language compatibility | + +### Feature Availability by Platform +| Feature | iOS | iPadOS | macOS | visionOS | tvOS | +|---------|-----|--------|--------|----------|------| +| Basic What's New | ✅ | ✅ | ✅ | ✅ | ✅ | +| Mesh Gradients | ✅ | ✅ | ✅ | ✅ | ✅ | +| Drop Notifications | ✅ | ✅ | ❌ | ❌ | ❌ | +| History View | ✅ | ✅ | ✅ | ✅ | ✅ | +| Remote JSON | ✅ | ✅ | ✅ | ✅ | ✅ | +| Special Effects | ✅ | ✅ | ✅ | ✅ | ✅ | ### Setup Steps | Description | Screenshot @@ -227,6 +419,72 @@ Copy the JSON sample to `data.json` file (If you don't have it, create a new fil ] ``` +## 🔧 Troubleshooting + +### Common Issues + +#### SwiftNEW doesn't appear +- Ensure the `show` binding is set to `true` +- Check that your data source (JSON file or URL) is accessible +- Verify the JSON format matches the expected structure + +#### Data not loading +- For local files: Ensure `data.json` is added to your app bundle +- For remote URLs: Check network connectivity and URL validity +- Verify JSON structure matches the [sample format](#sample) + +#### Build errors after installation +- Clean build folder (⌘+Shift+K) +- Update to latest Xcode version +- Ensure minimum platform requirements are met + +#### Performance issues +- For large datasets, consider pagination +- Optimize image assets in your JSON data +- Use remote loading for better memory management + +### Getting Help + +- Check [GitHub Issues](https://github.com/1998code/SwiftNEWKit/issues) for known problems +- Search [GitHub Discussions](https://github.com/1998code/SwiftNEWKit/discussions) for community solutions +- Create a new issue with detailed information about your problem + +## 📂 Project Structure + +``` +Sources/SwiftNEW/ +├── SwiftNEW.swift # Main struct with initializers +├── Model.swift # Data models (Vmodel, Model) +├── Bundle+Ext.swift # Bundle extensions +├── Localizable.xcstrings # Localization support +├── 📁 Views/ +│ ├── SwiftNEW+View.swift # Main body view implementation +│ ├── 📁 Sheets/ +│ │ ├── CurrentVersionSheet.swift # Current version display +│ │ └── HistorySheet.swift # Version history display +│ └── 📁 Components/ +│ ├── HeaderView.swift # Header components +│ └── ButtonComponents.swift # Button components +├── 📁 Extensions/ +│ └── SwiftNEW+Functions.swift # Utility functions +├── 📁 Styles/ +│ ├── AppIconView.swift # App icon display +│ ├── MeshView.swift # Gradient backgrounds +│ └── NoiseView.swift # Noise effects +└── 📁 Animations/ + └── SnowfallView.swift # Special effects (Christmas) +``` + +### Architecture Overview + +SwiftNEW is built with a modular architecture that separates concerns for better maintainability: + +- **Core Components**: Main struct and data models +- **View Layer**: Presentation components organized by functionality +- **Extensions**: Utility functions and framework extensions +- **Styles**: Visual components and gradient effects +- **Animations**: Special effects and interactive elements + ## Contributing Contributions to SwiftNEW are welcome! diff --git a/README/README_hc.md b/README/README_hc.md index 8585c5f..fec1d63 100644 --- a/README/README_hc.md +++ b/README/README_hc.md @@ -1,24 +1,37 @@ +SNK + # SwiftNEW -![image](https://github.com/user-attachments/assets/0a5de416-f4cd-41b5-8060-f839f2e7286a) +![Stable](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?color=03A791&label=穩定版) +![Beta](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?include_prereleases&color=3A59D1&label=測試版) +[![Validate JSON Files](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml/badge.svg)](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml) +![Swift Version](https://img.shields.io/badge/Swift-5.9/6.1-teal.svg) -## 功能 -| 描述 | 版本 | -|---------------------------------------------------|-----------| -| 網格漸變同線性漸變背景 | 5.3.0 | -| Apple visionOS 同 Vision Pro 支援 | 4.1.0 | -| 版本/構建變更時自動觸發/彈出 .sheet | 4.0.0 | -| 版本號格式 x.y.z 同/或 x.y | 4.0.0 | -| 遠程下拉通知 | 3.5.0 | -| Firebase 實時數據庫 | 3.0.0 | -| 遠程 JSON 文件 | 3.0.0 | -| 版本控制 + 睇歷史 | 2.0.0 | -| 支持所有用例(包括商業/非營利) | - | -| 簡單模型,易於修改同重用 | - | -| 簡單綁定同數據傳遞 | - | -| 從本地存儲即時加載 | - | +![Platforms](https://img.shields.io/badge/Platforms-iOS%2015.0+%20|%20macOS%2014.0+%20|%20tvOS%2017.0+%20|%20visionOS%201.0+-15437D.svg) +![License](https://img.shields.io/badge/License-MIT-C8ECFE.svg) + +![image](https://github.com/user-attachments/assets/0a5de416-f4cd-41b5-8060-f839f2e7286a) -## 預覽 +iOS、macOS、tvOS、visionOS 應用程式用嘅現代化 SwiftUI 原生「新功能」展示框架。採用模塊化架構構建,方便自定義同維護。 + +## 📋 目錄 +- [🎨 預覽同展示](#-預覽同展示) +- [✨ 功能](#-功能) +- [🚀 快速開始](#-快速開始) +- [📖 示例](#-示例) +- [📦 版本](#-版本) +- [🔧 測試平台同環境](#-測試平台同環境) +- [⚙️ 設置](#️-設置) +- [💻 主要用法](#-主要用法) +- [📄 JSON](#-json) +- [🏗️ 項目結構](#️-項目結構) +- [🔍 故障排除](#-故障排除) +- [🤝 貢獻](#-貢獻) +- [📜 許可證](#-許可證) +- [🌐 翻譯](#-翻譯) +- [💖 支持](#-支持) + +## 🎨 預覽同展示 ![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) ## 展示 @@ -34,16 +47,60 @@ ------------- | ------------ 支援 VisionOS (4.1.0 或更高版本) | 網格漸變背景 (5.3.0 或更高版本) -## 示例 +## 🚀 快速開始 + +### 安装 +1. 喺 Xcode 中,選擇 **File → Add Package Dependencies** +2. 输入 `https://github.com/1998code/SwiftNEWKit` +3. 選擇最新版本並添加到你嘅項目 + +### 基本用法 +```swift +import SwiftNEW + +struct ContentView: View { + @State var showNew: Bool = false + + var body: some View { + SwiftNEW(show: $showNew) + } +} +``` + +### 創建數據文件 +創建一個 `data.json` 文件: +```json +[ + { + "version": "1.0", + "new": [ + { + "title": "歡迎", + "subtitle": "開始使用", + "body": "感謝使用 SwiftNEW!", + "icon": "star.fill" + } + ] + } +] +``` + +### 遠程數據源 +你都可以使用遠程 JSON 或 Firebase 實時數據庫: +```swift +SwiftNEW(show: $showNew, data: "https://your-api.com/data.json") +``` + +## 📖 示例 路徑: `./Demo` (Xcode 項目) -## 版本 +## 📦 版本 ![GitHub release (latest by date)](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?color=g&label=穩定版&style=for-the-badge) ![GitHub release (latest by date including pre-releases)](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?color=green&include_prereleases&label=測試版&style=for-the-badge) ![swiftui-128x128_2x](https://user-images.githubusercontent.com/54872601/173193069-2eb486b0-1347-4448-ac2b-235b8f2f1bb0.png) -## 測試平台同環境 +## 🔧 測試平台同環境 ### 本地 測試平台 | 最新版本 | 兼容版本 -------- | ------ | ---------- @@ -57,7 +114,7 @@ visionOS | 2 | > 1 Xcode | > 13.4 (13F17a) macOS | > 12.3.1 (21E258) -### 設置 +### ⚙️ 設置 步驟 | 描述 | 截圖 ------| ----------- | ---------- 1 | 導航到根項目 | CleanShot 2022-06-11 at 17 39 39@2x @@ -67,7 +124,7 @@ macOS | > 12.3.1 (21E258) 5L | 創建一個名為 `data.json` 嘅新本地文件 | 你可以複製呢個 [JSON 示例](https://github.com/1998code/SwiftNEWKit#sample)。 5R | 你都可以使用遠程 JSON / firebase 實時數據庫。 | 示例: https://testground-a937f-default-rtdb.firebaseio.com/0.json?print=pretty -### 主要用法 +### 💻 主要用法 1. 導入包。 ```swift import SwiftNEW @@ -136,7 +193,7 @@ struct ContentView: View { } ``` -### JSON +### 📄 JSON #### 結構 / 模型 (參考) * 以下代碼僅供參考。你唔需要複製結構或模型。 ```swift @@ -219,18 +276,92 @@ public struct Model: Codable, Hashable { ] ``` -## 貢獻 +## ✨ 功能 +| 描述 | 版本 | +|---------------------------------------------------|-----------| +| 網格漸變同線性漸變背景 | 5.3.0 | +| Apple visionOS 同 Vision Pro 支援 | 4.1.0 | +| 版本/構建變更時自動觸發/彈出 .sheet | 4.0.0 | +| 版本號格式 x.y.z 同/或 x.y | 4.0.0 | +| 遠程下拉通知 | 3.5.0 | +| Firebase 實時數據庫 | 3.0.0 | +| 遠程 JSON 文件 | 3.0.0 | +| 版本控制 + 睇歷史 | 2.0.0 | +| 支持所有用例(包括商業/非營利) | - | +| 簡單模型,易於修改同重用 | - | +| 簡單綁定同數據傳遞 | - | +| 從本地存儲即時加載 | - | + +## 🏗️ 項目結構 +``` +Sources/SwiftNEW/ +├── SwiftNEW.swift # 主要結構同配置 +├── Model.swift # 數據模型 +├── Bundle+Ext.swift # Bundle 擴展 +├── Views/ +│ ├── SwiftNEW+View.swift # 主視圖實現 +│ ├── Components/ +│ │ ├── HeaderView.swift # 標題組件 +│ │ └── ButtonComponents.swift # 按鈕組件 +│ └── Sheets/ +│ ├── CurrentVersionSheet.swift # 當前版本表單 +│ └── HistorySheet.swift # 歷史記錄表單 +├── Extensions/ +│ └── SwiftNEW+Functions.swift # 實用函數 +├── Styles/ +│ ├── AppIconView.swift # 應用圖標樣式 +│ ├── MeshView.swift # 網格背景 +│ └── NoiseView.swift # 噪音效果 +└── Animations/ + └── SnowfallView.swift # 雪花動畫 +``` + +## 🔍 故障排除 + +### 常見問題 + +**Q: 點解組件冇顯示?** +A: 檢查以下項目: +- 確保 `data.json` 文件存在並且格式正確 +- 檢查 JSON 文件係咪添加到 Bundle 資源中 +- 驗證版本號格式 (x.y.z 或 x.y) + +**Q: 遠程數據加載失敗?** +A: 確保: +- URL 可以訪問並返回有效嘅 JSON +- 網絡連接正常 +- JSON 格式符合預期嘅結構 + +**Q: 動畫性能問題?** +A: 嘗試: +- 關閉網格背景 (`mesh: false`) +- 減少動畫複雜度 +- 檢查設備性能限制 + +**Q: 本地化問題?** +A: 確保: +- 本地化文件正確配置 +- Bundle 資源正確添加 +- 支持目標語言 + +### 支持嘅平台版本 +- iOS 14.0+ +- iPadOS 14.0+ +- macOS 11.0+ +- visionOS 1.0+ + +## 🤝 貢獻 歡迎對 SwiftNEW 做出貢獻! - 要報告錯誤或請求功能,請喺 GitHub 上提出問題 - 提交拉取請求時,請遵循項目嘅編碼風格 -## 許可證 +## 📜 許可證 MIT。 詳情請閱讀 LICENSE 文件。 -## 翻譯 +## 🌐 翻譯 呢個文檔仲有其他語言版本: @@ -238,7 +369,7 @@ MIT。 詳情請閱讀 LICENSE 文件。 請隨時提交拉取請求,添加新語言或修復任何錯別字/錯誤。 -## 支持 +## 💖 支持 Digital Ocean 標誌 \ No newline at end of file diff --git a/README/README_ja.md b/README/README_ja.md index 13bffb6..0710da8 100644 --- a/README/README_ja.md +++ b/README/README_ja.md @@ -1,38 +1,62 @@ +SNK + # SwiftNEW +![Stable](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?color=03A791&label=安定版) +![Beta](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?include_prereleases&color=3A59D1&label=ベータ版) +[![Validate JSON Files](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml/badge.svg)](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml) +![Swift Version](https://img.shields.io/badge/Swift-5.9/6.1-teal.svg) + +![Platforms](https://img.shields.io/badge/Platforms-iOS%2015.0+%20|%20macOS%2014.0+%20|%20tvOS%2017.0+%20|%20visionOS%201.0+-15437D.svg) +![License](https://img.shields.io/badge/License-MIT-C8ECFE.svg) + ![image](https://github.com/user-attachments/assets/0a5de416-f4cd-41b5-8060-f839f2e7286a) -## 機能 -| 説明 | バージョン | -|---------------------------------------------------|-----------| -| メッシュグラデーションと線形グラデーションの背景 | 5.3.0 | -| Apple visionOS と Vision Pro サポート | 4.1.0 | -| バージョン/ビルド変更時に自動的にトリガー/ポップアップする .sheet | 4.0.0 | -| バージョン番号形式 x.y.z および/または x.y | 4.0.0 | -| リモートドロップ通知 | 3.5.0 | -| Firebase リアルタイムデータベース | 3.0.0 | -| リモート JSON ファイル | 3.0.0 | -| バージョン管理 + 履歴表示 | 2.0.0 | -| 商業/非営利を含むすべてのユースケースをサポート | - | -| シンプルなモデル、簡単に変更や再利用が可能 | - | -| シンプルなバインディングとデータの受け渡し | - | -| ローカルストレージからの即時読み込み | - | - -## プレビュー -![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) +iOS、macOS、tvOS、visionOS アプリ用のモダンな SwiftUI ネイティブ「新機能」プレゼンテーションフレームワークです。カスタマイズとメンテナンスが簡単なモジュラーアーキテクチャで構築されています。 -## ギャラリー -![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) -------------- | ------------ -ライトモード | ダークモード +## 📋 目次 + +- [🎨 プレビューとギャラリー](#-プレビューとギャラリー) +- [✨ 機能](#-機能) +- [🎯 クイックスタート](#-クイックスタート) +- [⚙️ 設定パラメータ](#️-設定パラメータ) +- [🔧 データ設定](#-データ設定) +- [🛠️ プラットフォーム互換性](#️-プラットフォーム互換性) +- [🔧 トラブルシューティング](#-トラブルシューティング) +- [📂 プロジェクト構造](#-プロジェクト構造) +- [貢献](#貢献) -![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) ![CleanShot 2022-12-11 at 12 49 12@2x](https://user-images.githubusercontent.com/54872601/206887046-8ec82853-4e32-4a07-8b64-4cc984e7ec90.png) -------------- | ------------ -履歴ビュー (2.0.0) | アプリアイコン (3.9.6) [垂直 / 水平] +## 🎨 プレビューとギャラリー + +![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) -![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM | -------------- | ------------ -VisionOS サポート (4.1.0 以上) | メッシュグラデーション背景 (5.3.0 以上) +### ライトモードとダークモード +![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) +:---: | :---: +ライトネイティブ | ダークネイティブ + +### 高度な機能 +![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) +:---: | :---: +履歴ビュー (2.0.0+) | アプリアイコンサポート (3.9.6+) + +### プラットフォームサポート +![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM +:---: | :---: +VisionOS サポート (4.1.0+) | メッシュグラデーション背景 (5.3.0+) + +## ✨ 機能 + +| 機能 | バージョン | 説明 | +|------|-----------|------| +| 🎨 **メッシュ & リニアグラデーション** | 5.3.0 | 美しいグラデーション背景 | +| 🥽 **Apple visionOS & Vision Pro** | 4.1.0 | 完全な visionOS サポート | +| 🔄 **バージョン変更時自動トリガー** | 4.0.0 | アプリバージョンやビルド変更時に自動表示 | +| 📊 **柔軟なバージョン番号** | 4.0.0 | x.y.z と x.y バージョン形式をサポート | +| 📱 **リモートドロップ通知** | 3.5.0 | iOS 通知スタイルアラート | +| 🔥 **Firebase リアルタイムデータベース** | 3.0.0 | ライブコンテンツ更新 | +| 🌐 **リモート JSON サポート** | 3.0.0 | 任意の URL からコンテンツを読み込み | +| 📚 **バージョン履歴** | 2.0.0 | 過去のリリースをすべて表示 | ## サンプル パス: `./Demo` (Xcode プロジェクト) @@ -219,6 +243,43 @@ JSON サンプルを `data.json` ファイルにコピーします(ファイ ] ``` +## 📂 プロジェクト構造 + +``` +Sources/SwiftNEW/ +├── SwiftNEW.swift # メイン構造体と初期化 +├── Model.swift # データモデル (Vmodel, Model) +├── Bundle+Ext.swift # Bundle 拡張 +├── Localizable.xcstrings # ローカライゼーションサポート +├── 📁 Views/ +│ ├── SwiftNEW+View.swift # メインボディビューの実装 +│ ├── 📁 Sheets/ +│ │ ├── CurrentVersionSheet.swift # 現在のバージョン表示 +│ │ └── HistorySheet.swift # バージョン履歴表示 +│ └── 📁 Components/ +│ ├── HeaderView.swift # ヘッダーコンポーネント +│ └── ButtonComponents.swift # ボタンコンポーネント +├── 📁 Extensions/ +│ └── SwiftNEW+Functions.swift # ユーティリティ関数 +├── 📁 Styles/ +│ ├── AppIconView.swift # アプリアイコン表示 +│ ├── MeshView.swift # グラデーション背景 +│ └── NoiseView.swift # ノイズエフェクト +└── 📁 Animations/ + └── SnowfallView.swift # 特殊効果(クリスマス) +``` + +### アーキテクチャ概要 + +SwiftNEW は保守性を向上させるために関心事を分離したモジュラーアーキテクチャで構築されています: + +- **メイン構造体** (`SwiftNEW.swift`): パブリック API と設定オプション +- **ビュー階層** (`Views/`): UI コンポーネントの論理的なグループ化 +- **データモデル** (`Model.swift`): JSON データ構造 +- **拡張** (`Extensions/`): ユーティリティ関数とヘルパー +- **スタイリング** (`Styles/`): 再利用可能なビジュアルコンポーネント +- **アニメーション** (`Animations/`): 特殊効果とアニメーション + ## 貢献 SwiftNEW への貢献を歓迎します! diff --git a/README/README_ko.md b/README/README_ko.md index 81a6fad..dafcac9 100644 --- a/README/README_ko.md +++ b/README/README_ko.md @@ -1,38 +1,62 @@ +SNK + # SwiftNEW +![Stable](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?color=03A791&label=안정판) +![Beta](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?include_prereleases&color=3A59D1&label=베타판) +[![Validate JSON Files](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml/badge.svg)](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml) +![Swift Version](https://img.shields.io/badge/Swift-5.9/6.1-teal.svg) + +![Platforms](https://img.shields.io/badge/Platforms-iOS%2015.0+%20|%20macOS%2014.0+%20|%20tvOS%2017.0+%20|%20visionOS%201.0+-15437D.svg) +![License](https://img.shields.io/badge/License-MIT-C8ECFE.svg) + ![image](https://github.com/user-attachments/assets/0a5de416-f4cd-41b5-8060-f839f2e7286a) -## 기능 -| 설명 | 버전 | -|---------------------------------------------------|-----------| -| 메쉬 그라데이션 및 선형 그라데이션 배경 | 5.3.0 | -| Apple visionOS 및 Vision Pro 지원 | 4.1.0 | -| 버전/빌드 변경 시 자동으로 트리거/팝업 되는 .sheet | 4.0.0 | -| 버전 번호 형식 x.y.z 및/또는 x.y | 4.0.0 | -| 원격 드롭 알림 | 3.5.0 | -| Firebase 실시간 데이터베이스 | 3.0.0 | -| 원격 JSON 파일 | 3.0.0 | -| 버전 관리 + 기록 보기 | 2.0.0 | -| 상업적/비영리적 포함 모든 사용 사례 지원 | - | -| 간단한 모델, 쉬운 수정 및 재사용 | - | -| 간단한 바인딩 및 데이터 전달 | - | -| 로컬 스토리지에서 즉시 로드 | - | - -## 미리보기 -![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) +iOS, macOS, tvOS, visionOS 앱을 위한 모던한 SwiftUI 네이티브 "새로운 기능" 프레젠테이션 프레임워크입니다. 쉬운 커스터마이제이션과 유지보수를 위한 모듈러 아키텍처로 구축되었습니다. -## 갤러리 -![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) -------------- | ------------ -라이트 모드 | 다크 모드 +## 📋 목차 + +- [🎨 미리보기 및 갤러리](#-미리보기-및-갤러리) +- [✨ 기능](#-기능) +- [🎯 빠른 시작](#-빠른-시작) +- [⚙️ 설정 매개변수](#️-설정-매개변수) +- [🔧 데이터 설정](#-데이터-설정) +- [🛠️ 플랫폼 호환성](#️-플랫폼-호환성) +- [🔧 문제 해결](#-문제-해결) +- [📂 프로젝트 구조](#-프로젝트-구조) +- [기여](#기여) -![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) ![CleanShot 2022-12-11 at 12 49 12@2x](https://user-images.githubusercontent.com/54872601/206887046-8ec82853-4e32-4a07-8b64-4cc984e7ec90.png) -------------- | ------------ -기록 보기 (2.0.0) | 앱 아이콘 (3.9.6) [세로 / 가로] +## 🎨 미리보기 및 갤러리 + +![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) -![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM | -------------- | ------------ -VisionOS 지원 (4.1.0 이상) | 메쉬 그라데이션 배경 (5.3.0 이상) +### 라이트 및 다크 모드 +![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) +:---: | :---: +라이트 네이티브 | 다크 네이티브 + +### 고급 기능 +![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) +:---: | :---: +히스토리 뷰 (2.0.0+) | 앱 아이콘 지원 (3.9.6+) + +### 플랫폼 지원 +![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM +:---: | :---: +VisionOS 지원 (4.1.0+) | 메시 그라디언트 배경 (5.3.0+) + +## ✨ 기능 + +| 기능 | 버전 | 설명 | +|------|------|------| +| 🎨 **메시 & 리니어 그라디언트** | 5.3.0 | 아름다운 그라디언트 배경 | +| 🥽 **Apple visionOS & Vision Pro** | 4.1.0 | 완전한 visionOS 지원 | +| 🔄 **버전 변경 시 자동 트리거** | 4.0.0 | 앱 버전이나 빌드 변경 시 자동 표시 | +| 📊 **유연한 버전 번호** | 4.0.0 | x.y.z 및 x.y 버전 형식 지원 | +| 📱 **원격 드롭 알림** | 3.5.0 | iOS 알림 스타일 경고 | +| 🔥 **Firebase 실시간 데이터베이스** | 3.0.0 | 라이브 콘텐츠 업데이트 | +| 🌐 **원격 JSON 지원** | 3.0.0 | 모든 URL에서 콘텐츠 로드 | +| 📚 **버전 히스토리** | 2.0.0 | 모든 이전 릴리스 보기 | ## 예제 경로: `./Demo` (Xcode 프로젝트) @@ -219,6 +243,43 @@ JSON 샘플을 `data.json` 파일에 복사합니다(파일이 없는 경우 새 ] ``` +## 📂 프로젝트 구조 + +``` +Sources/SwiftNEW/ +├── SwiftNEW.swift # 초기화와 메인 구조체 +├── Model.swift # 데이터 모델 (Vmodel, Model) +├── Bundle+Ext.swift # Bundle 확장 +├── Localizable.xcstrings # 현지화 지원 +├── 📁 Views/ +│ ├── SwiftNEW+View.swift # 메인 body 뷰 구현 +│ ├── 📁 Sheets/ +│ │ ├── CurrentVersionSheet.swift # 현재 버전 표시 +│ │ └── HistorySheet.swift # 버전 히스토리 표시 +│ └── 📁 Components/ +│ ├── HeaderView.swift # 헤더 컴포넌트 +│ └── ButtonComponents.swift # 버튼 컴포넌트 +├── 📁 Extensions/ +│ └── SwiftNEW+Functions.swift # 유틸리티 함수 +├── 📁 Styles/ +│ ├── AppIconView.swift # 앱 아이콘 표시 +│ ├── MeshView.swift # 그라디언트 배경 +│ └── NoiseView.swift # 노이즈 효과 +└── 📁 Animations/ + └── SnowfallView.swift # 특수 효과 (크리스마스) +``` + +### 아키텍처 개요 + +SwiftNEW는 더 나은 유지보수성을 위해 관심사를 분리하는 모듈러 아키텍처로 구축되었습니다: + +- **메인 구조체** (`SwiftNEW.swift`): 공개 API와 구성 옵션 +- **뷰 계층** (`Views/`): UI 컴포넌트들을 논리적으로 그룹화 +- **데이터 모델** (`Model.swift`): JSON 데이터 구조 +- **확장** (`Extensions/`): 유틸리티 함수와 헬퍼 +- **스타일링** (`Styles/`): 재사용 가능한 시각적 컴포넌트 +- **애니메이션** (`Animations/`): 특수 효과와 애니메이션 + ## 기여하기 SwiftNEW에 기여해 주세요! diff --git a/README/README_tc.md b/README/README_tc.md index 190f164..30777e1 100644 --- a/README/README_tc.md +++ b/README/README_tc.md @@ -1,38 +1,62 @@ +SNK + # SwiftNEW +![Stable](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?color=03A791&label=穩定版) +![Beta](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?include_prereleases&color=3A59D1&label=測試版) +[![Validate JSON Files](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml/badge.svg)](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml) +![Swift Version](https://img.shields.io/badge/Swift-5.9/6.1-teal.svg) + +![Platforms](https://img.shields.io/badge/Platforms-iOS%2015.0+%20|%20macOS%2014.0+%20|%20tvOS%2017.0+%20|%20visionOS%201.0+-15437D.svg) +![License](https://img.shields.io/badge/License-MIT-C8ECFE.svg) + ![image](https://github.com/user-attachments/assets/0a5de416-f4cd-41b5-8060-f839f2e7286a) -## 功能 -| 描述 | 版本 | -|---------------------------------------------------|-----------| -| 網格漸變和線性漸變背景 | 5.3.0 | -| Apple visionOS 與 Vision Pro 支援 | 4.1.0 | -| 版本/構建變更時自動觸發/彈出 .sheet | 4.0.0 | -| 版本號格式 x.y.z 和/或 x.y | 4.0.0 | -| 遠程下拉通知 | 3.5.0 | -| Firebase 實時數據庫 | 3.0.0 | -| 遠程 JSON 文件 | 3.0.0 | -| 版本控制 + 查看歷史 | 2.0.0 | -| 支持所有用例(包括商業/非營利) | - | -| 簡單模型,易於修改和重用 | - | -| 簡單綁定和數據傳遞 | - | -| 從本地存儲即時加載 | - | - -## 預覽 -![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) +現代化的 SwiftUI 原生「最新功能」展示框架,適用於 iOS、macOS、tvOS 和 visionOS 應用程式。採用模組化架構,便於客製化和維護。 -## 展示 -![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) -------------- | ------------ -淺色主題 | 深色主題 +## 📋 目錄 + +- [🎨 預覽與展示](#-預覽與展示) +- [✨ 功能特色](#-功能特色) +- [🎯 快速開始](#-快速開始) +- [⚙️ 配置參數](#️-配置參數) +- [🔧 資料配置](#-資料配置) +- [🛠️ 平台相容性](#️-平台相容性) +- [🔧 疑難排解](#-疑難排解) +- [📂 專案結構](#-專案結構) +- [貢獻](#貢獻) -![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) ![CleanShot 2022-12-11 at 12 49 12@2x](https://user-images.githubusercontent.com/54872601/206887046-8ec82853-4e32-4a07-8b64-4cc984e7ec90.png) -------------- | ------------ -歷史視圖 (2.0.0) | 應用圖標 (3.9.6) [垂直 / 水平] +## 🎨 預覽與展示 + +![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) -![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM | -------------- | ------------ -支援 VisionOS (4.1.0 或更高版本) | 網格漸變背景 (5.3.0 或更高版本) +### 淺色與深色主題 +![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) +:---: | :---: +淺色原生 | 深色原生 + +### 進階功能 +![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) +:---: | :---: +歷史檢視 (2.0.0+) | 應用程式圖標支援 (3.9.6+) + +### 平台支援 +![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM +:---: | :---: +VisionOS 支援 (4.1.0+) | 網格漸變背景 (5.3.0+) + +## ✨ 功能特色 + +| 功能 | 版本 | 描述 | +|------|------|------| +| 🎨 **網格漸變與線性漸變** | 5.3.0 | 美麗的漸變背景 | +| 🥽 **Apple visionOS 與 Vision Pro** | 4.1.0 | 完整 visionOS 支援 | +| 🔄 **版本變更自動觸發** | 4.0.0 | 應用程式版本或組建變更時自動顯示 | +| 📊 **彈性版本號** | 4.0.0 | 支援 x.y.z 和 x.y 版本格式 | +| 📱 **遠端下拉通知** | 3.5.0 | iOS 通知樣式警告 | +| 🔥 **Firebase 即時資料庫** | 3.0.0 | 即時內容更新 | +| 🌐 **遠端 JSON 支援** | 3.0.0 | 從任何 URL 載入內容 | +| 📚 **版本歷史** | 2.0.0 | 檢視所有先前發布版本 | ## 示例 路徑: `./Demo` (Xcode 項目) @@ -219,6 +243,43 @@ public struct Model: Codable, Hashable { ] ``` +## 📂 專案結構 + +``` +Sources/SwiftNEW/ +├── SwiftNEW.swift # 主要結構體與初始化 +├── Model.swift # 資料模型 (Vmodel, Model) +├── Bundle+Ext.swift # Bundle 擴展 +├── Localizable.xcstrings # 本地化支援 +├── 📁 Views/ +│ ├── SwiftNEW+View.swift # 主要 body 視圖實現 +│ ├── 📁 Sheets/ +│ │ ├── CurrentVersionSheet.swift # 當前版本顯示 +│ │ └── HistorySheet.swift # 版本歷史顯示 +│ └── 📁 Components/ +│ ├── HeaderView.swift # 標題組件 +│ └── ButtonComponents.swift # 按鈕組件 +├── 📁 Extensions/ +│ └── SwiftNEW+Functions.swift # 實用函數 +├── 📁 Styles/ +│ ├── AppIconView.swift # 應用程式圖示顯示 +│ ├── MeshView.swift # 漸層背景 +│ └── NoiseView.swift # 噪點效果 +└── 📁 Animations/ + └── SnowfallView.swift # 特殊效果(聖誕節) +``` + +### 架構概述 + +SwiftNEW 採用模組化架構建構,分離關注點以提升可維護性: + +- **主要結構體** (`SwiftNEW.swift`): 公開 API 與設定選項 +- **視圖層級** (`Views/`): UI 組件的邏輯分組 +- **資料模型** (`Model.swift`): JSON 資料結構 +- **擴展** (`Extensions/`): 實用函數與輔助功能 +- **樣式** (`Styles/`): 可重用的視覺組件 +- **動畫** (`Animations/`): 特殊效果與動畫 + ## 貢獻 歡迎對 SwiftNEW 做出貢獻! diff --git a/README/README_zh.md b/README/README_zh.md index 9fa1aab..caa62fc 100644 --- a/README/README_zh.md +++ b/README/README_zh.md @@ -1,38 +1,62 @@ +SNK + # SwiftNEW +![Stable](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?color=03A791&label=稳定版) +![Beta](https://img.shields.io/github/v/release/1998code/SwiftNEWKit?include_prereleases&color=3A59D1&label=测试版) +[![Validate JSON Files](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml/badge.svg)](https://github.com/1998code/SwiftNEWKit/actions/workflows/validate-json.yml) +![Swift Version](https://img.shields.io/badge/Swift-5.9/6.1-teal.svg) + +![Platforms](https://img.shields.io/badge/Platforms-iOS%2015.0+%20|%20macOS%2014.0+%20|%20tvOS%2017.0+%20|%20visionOS%201.0+-15437D.svg) +![License](https://img.shields.io/badge/License-MIT-C8ECFE.svg) + ![image](https://github.com/user-attachments/assets/0a5de416-f4cd-41b5-8060-f839f2e7286a) -## 功能 -| 描述 | 版本 | -|---------------------------------------------------|-----------| -| 网格渐变和线性渐变背景 | 5.3.0 | -| Apple visionOS 与 Vision Pro 支持 | 4.1.0 | -| 版本/构建变更时自动触发/弹出 .sheet | 4.0.0 | -| 版本号格式 x.y.z 和/或 x.y | 4.0.0 | -| 远程下拉通知 | 3.5.0 | -| Firebase 实时数据库 | 3.0.0 | -| 远程 JSON 文件 | 3.0.0 | -| 版本控制 + 查看历史 | 2.0.0 | -| 支持所有用例(包括商业/非营利) | - | -| 简单模型,易于修改和重用 | - | -| 简单绑定和数据传递 | - | -| 从本地存储即时加载 | - | - -## 预览 -![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) +现代化的 SwiftUI 原生「最新功能」展示框架,适用于 iOS、macOS、tvOS 和 visionOS 应用程序。采用模块化架构,便于定制和维护。 -## 展示 -![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) -------------- | ------------ -浅色主题 | 深色主题 +## 📋 目录 + +- [🎨 预览与展示](#-预览与展示) +- [✨ 功能特色](#-功能特色) +- [🎯 快速开始](#-快速开始) +- [⚙️ 配置参数](#️-配置参数) +- [🔧 数据配置](#-数据配置) +- [🛠️ 平台兼容性](#️-平台兼容性) +- [🔧 疑难解答](#-疑难解答) +- [📂 项目结构](#-项目结构) +- [贡献](#贡献) -![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) ![CleanShot 2022-12-11 at 12 49 12@2x](https://user-images.githubusercontent.com/54872601/206887046-8ec82853-4e32-4a07-8b64-4cc984e7ec90.png) -------------- | ------------ -历史视图 (2.0.0) | 应用图标 (3.9.6) [垂直 / 水平] +## 🎨 预览与展示 + +![CleanShot 2022-06-11 at 22 54 15@2x](https://user-images.githubusercontent.com/54872601/173192927-ca2a8bef-2114-44f8-8d4d-47baadb8b4a8.png) -![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM | -------------- | ------------ -支持 VisionOS (4.1.0 或更高版本) | 网格渐变背景 (5.3.0 或更高版本) +### 浅色与深色主题 +![IMG_3472](https://user-images.githubusercontent.com/54872601/173187065-14d78119-47e7-4dcb-a3e6-c7fee4f0c67f.PNG) | ![IMG_3471](https://user-images.githubusercontent.com/54872601/173187067-fe3b5cac-54b5-4482-b73f-42e6c500546f.PNG) +:---: | :---: +浅色原生 | 深色原生 + +### 高级功能 +![Simulator Screen Shot - iPhone 13 Pro Max](https://user-images.githubusercontent.com/54872601/178129999-ad63b0ce-d65e-4d86-9882-37a5090e92bc.png) | ![CleanShot 2022-12-11 at 12 46 30@2x](https://user-images.githubusercontent.com/54872601/206886933-bc4d0d33-e0fc-4013-9456-f19679b10f5b.png) +:---: | :---: +历史视图 (2.0.0+) | 应用程序图标支持 (3.9.6+) + +### 平台支持 +![CleanShot 2023-06-22 at 14 24 07@2x](https://github.com/1998code/SwiftNEWKit/assets/54872601/12a8ab01-76e5-42a1-96b4-848ef5e5f36b) | Screenshot 2024-07-01 at 10 18 33 PM +:---: | :---: +VisionOS 支持 (4.1.0+) | 网格渐变背景 (5.3.0+) + +## ✨ 功能特色 + +| 功能 | 版本 | 描述 | +|------|------|------| +| 🎨 **网格渐变与线性渐变** | 5.3.0 | 美丽的渐变背景 | +| 🥽 **Apple visionOS 与 Vision Pro** | 4.1.0 | 完整 visionOS 支持 | +| 🔄 **版本变更自动触发** | 4.0.0 | 应用程序版本或构建变更时自动显示 | +| 📊 **灵活版本号** | 4.0.0 | 支持 x.y.z 和 x.y 版本格式 | +| 📱 **远程下拉通知** | 3.5.0 | iOS 通知样式警告 | +| 🔥 **Firebase 实时数据库** | 3.0.0 | 实时内容更新 | +| 🌐 **远程 JSON 支持** | 3.0.0 | 从任何 URL 加载内容 | +| 📚 **版本历史** | 2.0.0 | 查看所有以前的发布版本 | ## 示例 路径: `./Demo` (Xcode 项目) @@ -219,6 +243,43 @@ public struct Model: Codable, Hashable { ] ``` +## 📂 项目结构 + +``` +Sources/SwiftNEW/ +├── SwiftNEW.swift # 主要结构体与初始化 +├── Model.swift # 数据模型 (Vmodel, Model) +├── Bundle+Ext.swift # Bundle 扩展 +├── Localizable.xcstrings # 本地化支持 +├── 📁 Views/ +│ ├── SwiftNEW+View.swift # 主要 body 视图实现 +│ ├── 📁 Sheets/ +│ │ ├── CurrentVersionSheet.swift # 当前版本显示 +│ │ └── HistorySheet.swift # 版本历史显示 +│ └── 📁 Components/ +│ ├── HeaderView.swift # 标题组件 +│ └── ButtonComponents.swift # 按钮组件 +├── 📁 Extensions/ +│ └── SwiftNEW+Functions.swift # 实用函数 +├── 📁 Styles/ +│ ├── AppIconView.swift # 应用图标显示 +│ ├── MeshView.swift # 渐变背景 +│ └── NoiseView.swift # 噪点效果 +└── 📁 Animations/ + └── SnowfallView.swift # 特殊效果(圣诞节) +``` + +### 架构概述 + +SwiftNEW 采用模块化架构构建,分离关注点以提升可维护性: + +- **主要结构体** (`SwiftNEW.swift`): 公开 API 与配置选项 +- **视图层级** (`Views/`): UI 组件的逻辑分组 +- **数据模型** (`Model.swift`): JSON 数据结构 +- **扩展** (`Extensions/`): 实用函数与辅助功能 +- **样式** (`Styles/`): 可重用的视觉组件 +- **动画** (`Animations/`): 特殊效果与动画 + ## 贡献 欢迎对 SwiftNEW 做出贡献! diff --git a/Sources/SwiftNEW/Bundle+Ext.swift b/Sources/SwiftNEW/Bundle+Ext.swift index d3a4907..838cca6 100644 --- a/Sources/SwiftNEW/Bundle+Ext.swift +++ b/Sources/SwiftNEW/Bundle+Ext.swift @@ -17,4 +17,11 @@ extension Bundle { else { return nil } return iconFileName } + + // MARK: - Version Information + static var versionBuild: String { + let version = Bundle.main.infoDictionary?["CFBundleShortVersionString"] as? String ?? "1.0" + let build = Bundle.main.infoDictionary?["CFBundleVersion"] as? String ?? "1" + return "\(version) (\(build))" + } } diff --git a/Sources/SwiftNEW/Extensions/SwiftNEW+Functions.swift b/Sources/SwiftNEW/Extensions/SwiftNEW+Functions.swift new file mode 100644 index 0000000..3efbc56 --- /dev/null +++ b/Sources/SwiftNEW/Extensions/SwiftNEW+Functions.swift @@ -0,0 +1,85 @@ +// +// SwiftNEW+Functions.swift +// SwiftNEW +// +// Created by Ming on 11/6/2022. +// + +import SwiftUI +import SwiftVB +import SwiftGlass + +#if os(iOS) +import Drops +#endif + +@available(iOS 15.0, watchOS 8.0, macOS 12.0, tvOS 17.0, *) +extension SwiftNEW { + + // MARK: - Functions + public func compareVersion() { + let currentVersion = Bundle.version.replacingOccurrences(of: ".", with: "") + let currentBuild = Bundle.build.replacingOccurrences(of: ".", with: "") + + let savedVersion = String(version).replacingOccurrences(of: ".", with: "") + let savedBuild = String(build).replacingOccurrences(of: ".", with: "") + + if Int(currentVersion)! != Int(savedVersion)! || Int(currentBuild)! != Int(savedBuild)! { + withAnimation { + DispatchQueue.main.asyncAfter(deadline: .now() + 0.1) { + if showDrop { + #if os(iOS) + drop() + #endif + } else { + show = true + } + } + version = Double(currentVersion)! / 10 + build = Double(currentBuild)! / 10 + } + } + } + + public func loadData() { + if data.contains("http") { + // MARK: Remote Data + let url = URL(string: data) + URLSession.shared.dataTask(with: url!) { data, response, error in + if let data = data { + do { + let decoder = JSONDecoder() + items = try decoder.decode([Vmodel].self, from: data) + self.loading = false + } catch { + print(error) + } + } + }.resume() + } else { + // MARK: Local Data + if let url = Bundle.main.url(forResource: data, withExtension: "json") { + do { + let data = try Data(contentsOf: url) + let decoder = JSONDecoder() + items = try decoder.decode([Vmodel].self, from: data) + loading = false + } catch { + print("error: \(error)") + } + } + } + } + + #if os(iOS) + public func drop() { + let drop = Drop(title: "Tap", subtitle: "To See What's New.", icon: UIImage(systemName: labelImage), + action: .init { + Drops.hideCurrent() + show = true + }, + position: .top, duration: 3.0, accessibility: "Alert: Tap to see what's new." ) + Drops.show(drop) + } + #endif +} diff --git a/Sources/SwiftNEW/SwiftNEW.swift b/Sources/SwiftNEW/SwiftNEW.swift index 9f65479..fb97a4b 100644 --- a/Sources/SwiftNEW/SwiftNEW.swift +++ b/Sources/SwiftNEW/SwiftNEW.swift @@ -1,4 +1,7 @@ // +// SwiftNEW.swift +// SwiftNEW +// // Created by Ming on 11/6/2022. // @@ -120,410 +123,4 @@ public struct SwiftNEW: View { compareVersion() } #endif - - public var body: some View { - Button(action: { - if showDrop { - #if os(iOS) - drop() - #endif - } else { - show = true - } - }) { - if size == "mini" { - Label(label, systemImage: labelImage) - } - else if size == "normal" || size == "simple" { - Label(label, systemImage: labelImage) - #if !os(tvOS) - .frame(width: 300, height: 50) - #else - .frame(width: 400, height: 50) - #endif - #if os(iOS) && !os(visionOS) - .foregroundColor(labelColor) - .background(color) - .cornerRadius(15) - #endif - } - } - .opacity(size == "invisible" ? 0 : 100) - .glass(shadowColor: color) - .sheet(isPresented: $show) { - ZStack { - if mesh { - MeshView(color: $color) - } - if specialEffect == "Christmas" { - SnowfallView() - } - sheetCurrent - .sheet(isPresented: $historySheet) { - if #available(iOS 16.4, tvOS 16.4, *) { - sheetHistory - .presentationBackground(.thinMaterial) - } else { - sheetHistory - } - } - #if os(visionOS) - .padding() - #endif - } - } - } - - // MARK: - Current Version Changes View - public var sheetCurrent: some View { - VStack(alignment: align) { - Spacer() - - headings - .padding(.bottom) - - Spacer() - - if loading { - VStack { - Text(String(localized: "Loading...", bundle: .module)) - .padding(.bottom) - ProgressView() - } - } - else { - ScrollView(showsIndicators: false) { - ForEach(items, id: \.self) { item in - if item.version == Bundle.version || item.subVersion == Bundle.version { - ForEach(item.new, id: \.self) { new in - HStack { - if align == .leading || align == .center { - ZStack { - color - Image(systemName: new.icon) - .foregroundColor(.white) - }.glass(radius: 15, shadowColor: color) - #if !os(tvOS) - .frame(width: 50, height: 50) - #else - .frame(width: 100, height: 100) - #endif - .cornerRadius(15) - .padding(.trailing) - } else { - Spacer() - } - - VStack(alignment: align == .trailing ? .trailing : .leading) { - Text(new.title).font(.headline).lineLimit(1) - Text(new.subtitle).font(.subheadline).foregroundColor(.secondary).lineLimit(1) - Text(new.body).font(.caption).foregroundColor(.secondary).lineLimit(2) - } - - if align == .trailing { - ZStack { - color - Image(systemName: new.icon) - .foregroundColor(.white) - }.glass(radius: 15, shadowColor: color) - #if !os(tvOS) - .frame(width: 50, height: 50) - #else - .frame(width: 100, height: 100) - #endif - .cornerRadius(15) - .padding(.trailing) - } else { - Spacer() - } - }.padding(.bottom) - } - } - } - } - #if !os(tvOS) - .frame(width: 300) - #elseif !os(macOS) - .frame(maxHeight: UIScreen.main.bounds.height * 0.5) - #endif - } - - Spacer() - - if history { - showHistoryButton - .padding(.bottom) - } - - closeCurrentButton - .padding(.bottom) - } - .onAppear { - loadData() - } - #if os(macOS) - .padding() - .frame(width: 600, height: 600) - #elseif os(tvOS) - .frame(width: 600) - #endif - } - #if os(iOS) - public var headings: some View { - HStack { - if align == .leading { - AppIconView() - .padding(.leading, -8) - .padding(.trailing, 8) - } - VStack(alignment: align) { - if align == .center { - AppIconView() - } - Text(String(localized: "What's New in", bundle: .module)) - .bold().font(.largeTitle) - Text("\(String(localized: "Version", bundle: .module)) \(Bundle.versionBuild)") - .bold().font(.title).foregroundColor(.secondary) - } - if align == .trailing { - AppIconView() - } - } - } - #elseif os(macOS) || os(visionOS) || os(tvOS) - public var headings: some View { - VStack { - Text(String(localized: "What's New in", bundle: .module)) - .bold().font(.largeTitle) - Text("\(String(localized: "Version", bundle: .module)) \(Bundle.versionBuild)") - .bold().font(.title).foregroundColor(.secondary) - } - } - #endif - public var showHistoryButton: some View { - Button(action: { - historySheet = true - }) { - HStack { - if align == .trailing { - Spacer() - } - Text(String(localized: "Show History", bundle: .module)) - Image(systemName: "arrow.up.bin") - if align == .leading { - Spacer() - } - }.font(.caption) - } - #if !os(visionOS) - .buttonStyle(.bordered) - .buttonBorderShape(.capsule) - .tint(.secondary) - #endif - .glass(color: .secondary, shadowColor: color) - } - public var closeCurrentButton: some View { - Button(action: { show = false }) { - HStack{ - if align == .trailing { - Spacer() - } - Text(String(localized: "Continue", bundle: .module)) - .bold() - Image(systemName: "arrow.right.circle.fill") - if align == .leading { - Spacer() - } - }.font(.body) - .padding(.horizontal) - #if os(iOS) - .frame(width: 300, height: 50) - #elseif os(macOS) - .frame(width: 200, height: 25) - #endif - #if os(iOS) && !os(visionOS) - .foregroundColor(.white) - .background(color) - .cornerRadius(15) - #elseif os(tvOS) - .tint(.white) - #endif - }.glass(shadowColor: color) - } - - // MARK: - History List View - public var sheetHistory: some View { - VStack(alignment: align) { - Spacer() - - Text(String(localized: "History", bundle: .module)) - .bold().font(.largeTitle) - - Spacer() - - ScrollView(showsIndicators: false) { - ForEach(items, id: \.self) { item in - ZStack { - color.opacity(0.25) - Text(item.version).bold().font(.title2).foregroundColor(color) - }.glass(radius: 15, shadowColor: color) - .frame(width: 75, height: 30) - .cornerRadius(15) - .padding(.bottom) - - ForEach(item.new, id: \.self) { new in - HStack { - if align == .leading || align == .center { - ZStack { - color - Image(systemName: new.icon) - .foregroundColor(.white) - }.glass(radius: 15, shadowColor: color) - #if !os(tvOS) - .frame(width: 50, height: 50) - #else - .frame(width: 100, height: 100) - #endif - .cornerRadius(15) - .padding(.trailing) - } else { - Spacer() - } - - VStack(alignment: align == .trailing ? .trailing : .leading) { - Text(new.title).font(.headline).lineLimit(1) - Text(new.subtitle).font(.subheadline).foregroundColor(.secondary).lineLimit(1) - Text(new.body).font(.caption).foregroundColor(.secondary).lineLimit(2) - } - - if align == .trailing { - ZStack { - color - Image(systemName: new.icon) - .foregroundColor(.white) - } - #if !os(tvOS) - .frame(width: 50, height: 50) - #else - .frame(width: 100, height: 100) - #endif - .cornerRadius(15) - .padding(.leading) - } else { - Spacer() - } - }.padding(.bottom) - } - } - } - #if !os(tvOS) - .frame(width: 300) - #elseif !os(macOS) - .frame(maxHeight: UIScreen.main.bounds.height * 0.5) - #endif - - Spacer() - - closeHistoryButton - .padding(.bottom) - } - #if os(macOS) - .padding() - .frame(width: 600, height: 600) - #elseif os(tvOS) - .frame(width: 600) - #endif - } - public var closeHistoryButton: some View { - Button(action: { historySheet = false }) { - HStack{ - if align == .trailing { - Spacer() - } - Text(String(localized: "Return", bundle: .module)) - .bold() - Image(systemName: "arrow.down.circle.fill") - if align == .leading { - Spacer() - } - }.font(.body) - .padding(.horizontal) - #if os(iOS) - .frame(width: 300, height: 50) - #elseif os(macOS) - .frame(width: 300, height: 25) - #endif - #if os(iOS) - .foregroundColor(.white) - .background(color) - .cornerRadius(15) - #endif - }.glass(shadowColor: color) - } - - // MARK: - Functions - public func compareVersion() { - let currentVersion = Bundle.version.replacingOccurrences(of: ".", with: "") - let currentBuild = Bundle.build.replacingOccurrences(of: ".", with: "") - - let savedVersion = String(version).replacingOccurrences(of: ".", with: "") - let savedBuild = String(build).replacingOccurrences(of: ".", with: "") - - if Int(currentVersion)! != Int(savedVersion)! || Int(currentBuild)! != Int(savedBuild)! { - withAnimation { - DispatchQueue.main.asyncAfter(deadline: .now() + 0.1) { - if showDrop { - #if os(iOS) - drop() - #endif - } else { - show = true - } - } - version = Double(currentVersion)! / 10 - build = Double(currentBuild)! / 10 - } - } - } - public func loadData() { - if data.contains("http") { - // MARK: Remote Data - let url = URL(string: data) - URLSession.shared.dataTask(with: url!) { data, response, error in - if let data = data { - do { - let decoder = JSONDecoder() - items = try decoder.decode([Vmodel].self, from: data) - self.loading = false - } catch { - print(error) - } - } - }.resume() - } else { - // MARK: Local Data - if let url = Bundle.main.url(forResource: data, withExtension: "json") { - do { - let data = try Data(contentsOf: url) - let decoder = JSONDecoder() - items = try decoder.decode([Vmodel].self, from: data) - loading = false - } catch { - print("error: \(error)") - } - } - } - } - - #if os(iOS) - public func drop() { - let drop = Drop(title: "Tap", subtitle: "To See What's New.", icon: UIImage(systemName: labelImage), - action: .init { - Drops.hideCurrent() - show = true - }, - position: .top, duration: 3.0, accessibility: "Alert: Tap to see what's new." ) - Drops.show(drop) - } - #endif } diff --git a/Sources/SwiftNEW/Views/Components/ButtonComponents.swift b/Sources/SwiftNEW/Views/Components/ButtonComponents.swift new file mode 100644 index 0000000..9944786 --- /dev/null +++ b/Sources/SwiftNEW/Views/Components/ButtonComponents.swift @@ -0,0 +1,93 @@ +// +// ButtonComponents.swift +// SwiftNEW +// +// Created by Ming on 11/6/2022. +// + +import SwiftUI +import SwiftVB +import SwiftGlass + +@available(iOS 15.0, watchOS 8.0, macOS 12.0, tvOS 17.0, *) +extension SwiftNEW { + + public var showHistoryButton: some View { + Button(action: { + historySheet = true + }) { + HStack { + if align == .trailing { + Spacer() + } + Text(String(localized: "Show History", bundle: .module)) + Image(systemName: "arrow.up.bin") + if align == .leading { + Spacer() + } + }.font(.caption) + } + #if !os(visionOS) + .buttonStyle(.bordered) + .buttonBorderShape(.capsule) + .tint(.secondary) + #endif + .glass(color: .secondary, shadowColor: color) + } + + public var closeCurrentButton: some View { + Button(action: { show = false }) { + HStack{ + if align == .trailing { + Spacer() + } + Text(String(localized: "Continue", bundle: .module)) + .bold() + Image(systemName: "arrow.right.circle.fill") + if align == .leading { + Spacer() + } + }.font(.body) + .padding(.horizontal) + #if os(iOS) + .frame(width: 300, height: 50) + #elseif os(macOS) + .frame(width: 200, height: 25) + #endif + #if os(iOS) && !os(visionOS) + .foregroundColor(.white) + .background(color) + .cornerRadius(15) + #elseif os(tvOS) + .tint(.white) + #endif + }.glass(shadowColor: color) + } + + public var closeHistoryButton: some View { + Button(action: { historySheet = false }) { + HStack{ + if align == .trailing { + Spacer() + } + Text(String(localized: "Return", bundle: .module)) + .bold() + Image(systemName: "arrow.down.circle.fill") + if align == .leading { + Spacer() + } + }.font(.body) + .padding(.horizontal) + #if os(iOS) + .frame(width: 300, height: 50) + #elseif os(macOS) + .frame(width: 300, height: 25) + #endif + #if os(iOS) + .foregroundColor(.white) + .background(color) + .cornerRadius(15) + #endif + }.glass(shadowColor: color) + } +} diff --git a/Sources/SwiftNEW/Views/Components/HeaderView.swift b/Sources/SwiftNEW/Views/Components/HeaderView.swift new file mode 100644 index 0000000..9f1e3c9 --- /dev/null +++ b/Sources/SwiftNEW/Views/Components/HeaderView.swift @@ -0,0 +1,47 @@ +// +// HeaderView.swift +// SwiftNEW +// +// Created by Ming on 11/6/2022. +// + +import SwiftUI +import SwiftVB +import SwiftGlass + +@available(iOS 15.0, watchOS 8.0, macOS 12.0, tvOS 17.0, *) +extension SwiftNEW { + + #if os(iOS) + public var headings: some View { + HStack { + if align == .leading { + AppIconView() + .padding(.leading, -8) + .padding(.trailing, 8) + } + VStack(alignment: align) { + if align == .center { + AppIconView() + } + Text(String(localized: "What's New in", bundle: .module)) + .bold().font(.largeTitle) + Text("\(String(localized: "Version", bundle: .module)) \(Bundle.versionBuild)") + .bold().font(.title).foregroundColor(.secondary) + } + if align == .trailing { + AppIconView() + } + } + } + #elseif os(macOS) || os(visionOS) || os(tvOS) + public var headings: some View { + VStack { + Text(String(localized: "What's New in", bundle: .module)) + .bold().font(.largeTitle) + Text("\(String(localized: "Version", bundle: .module)) \(Bundle.versionBuild)") + .bold().font(.title).foregroundColor(.secondary) + } + } + #endif +} diff --git a/Sources/SwiftNEW/Views/Sheets/CurrentVersionSheet.swift b/Sources/SwiftNEW/Views/Sheets/CurrentVersionSheet.swift new file mode 100644 index 0000000..d32b5d9 --- /dev/null +++ b/Sources/SwiftNEW/Views/Sheets/CurrentVersionSheet.swift @@ -0,0 +1,109 @@ +// +// CurrentVersionSheet.swift +// SwiftNEW +// +// Created by Ming on 11/6/2022. +// + +import SwiftUI +import SwiftVB +import SwiftGlass + +@available(iOS 15.0, watchOS 8.0, macOS 12.0, tvOS 17.0, *) +extension SwiftNEW { + + // MARK: - Current Version Changes View + public var sheetCurrent: some View { + VStack(alignment: align) { + Spacer() + + headings + .padding(.bottom) + + Spacer() + + if loading { + VStack { + Text(String(localized: "Loading...", bundle: .module)) + .padding(.bottom) + ProgressView() + } + } + else { + ScrollView(showsIndicators: false) { + ForEach(items, id: \.self) { item in + if item.version == Bundle.version || item.subVersion == Bundle.version { + ForEach(item.new, id: \.self) { new in + HStack { + if align == .leading || align == .center { + ZStack { + color + Image(systemName: new.icon) + .foregroundColor(.white) + }.glass(radius: 15, shadowColor: color) + #if !os(tvOS) + .frame(width: 50, height: 50) + #else + .frame(width: 100, height: 100) + #endif + .cornerRadius(15) + .padding(.trailing) + } else { + Spacer() + } + + VStack(alignment: align == .trailing ? .trailing : .leading) { + Text(new.title).font(.headline).lineLimit(1) + Text(new.subtitle).font(.subheadline).foregroundColor(.secondary).lineLimit(1) + Text(new.body).font(.caption).foregroundColor(.secondary).lineLimit(2) + } + + if align == .trailing { + ZStack { + color + Image(systemName: new.icon) + .foregroundColor(.white) + }.glass(radius: 15, shadowColor: color) + #if !os(tvOS) + .frame(width: 50, height: 50) + #else + .frame(width: 100, height: 100) + #endif + .cornerRadius(15) + .padding(.trailing) + } else { + Spacer() + } + }.padding(.bottom) + } + } + } + } + #if !os(tvOS) + .frame(width: 300) + #elseif !os(macOS) + .frame(maxHeight: UIScreen.main.bounds.height * 0.5) + #endif + } + + Spacer() + + if history { + showHistoryButton + .padding(.bottom) + } + + closeCurrentButton + .padding(.bottom) + } + .onAppear { + loadData() + } + #if os(macOS) + .padding() + .frame(width: 600, height: 600) + #elseif os(tvOS) + .frame(width: 600) + #endif + } +} diff --git a/Sources/SwiftNEW/Views/Sheets/HistorySheet.swift b/Sources/SwiftNEW/Views/Sheets/HistorySheet.swift new file mode 100644 index 0000000..2f56408 --- /dev/null +++ b/Sources/SwiftNEW/Views/Sheets/HistorySheet.swift @@ -0,0 +1,98 @@ +// +// HistorySheet.swift +// SwiftNEW +// +// Created by Ming on 11/6/2022. +// + +import SwiftUI +import SwiftVB +import SwiftGlass + +@available(iOS 15.0, watchOS 8.0, macOS 12.0, tvOS 17.0, *) +extension SwiftNEW { + + // MARK: - History List View + public var sheetHistory: some View { + VStack(alignment: align) { + Spacer() + + Text(String(localized: "History", bundle: .module)) + .bold().font(.largeTitle) + + Spacer() + + ScrollView(showsIndicators: false) { + ForEach(items, id: \.self) { item in + ZStack { + color.opacity(0.25) + Text(item.version).bold().font(.title2).foregroundColor(color) + }.glass(radius: 15, shadowColor: color) + .frame(width: 75, height: 30) + .cornerRadius(15) + .padding(.bottom) + + ForEach(item.new, id: \.self) { new in + HStack { + if align == .leading || align == .center { + ZStack { + color + Image(systemName: new.icon) + .foregroundColor(.white) + }.glass(radius: 15, shadowColor: color) + #if !os(tvOS) + .frame(width: 50, height: 50) + #else + .frame(width: 100, height: 100) + #endif + .cornerRadius(15) + .padding(.trailing) + } else { + Spacer() + } + + VStack(alignment: align == .trailing ? .trailing : .leading) { + Text(new.title).font(.headline).lineLimit(1) + Text(new.subtitle).font(.subheadline).foregroundColor(.secondary).lineLimit(1) + Text(new.body).font(.caption).foregroundColor(.secondary).lineLimit(2) + } + + if align == .trailing { + ZStack { + color + Image(systemName: new.icon) + .foregroundColor(.white) + } + #if !os(tvOS) + .frame(width: 50, height: 50) + #else + .frame(width: 100, height: 100) + #endif + .cornerRadius(15) + .padding(.leading) + } else { + Spacer() + } + }.padding(.bottom) + } + } + } + #if !os(tvOS) + .frame(width: 300) + #elseif !os(macOS) + .frame(maxHeight: UIScreen.main.bounds.height * 0.5) + #endif + + Spacer() + + closeHistoryButton + .padding(.bottom) + } + #if os(macOS) + .padding() + .frame(width: 600, height: 600) + #elseif os(tvOS) + .frame(width: 600) + #endif + } +} diff --git a/Sources/SwiftNEW/Views/SwiftNEW+View.swift b/Sources/SwiftNEW/Views/SwiftNEW+View.swift new file mode 100644 index 0000000..a785724 --- /dev/null +++ b/Sources/SwiftNEW/Views/SwiftNEW+View.swift @@ -0,0 +1,70 @@ +// +// SwiftNEW+View.swift +// SwiftNEW +// +// Created by Ming on 11/6/2022. +// + +import SwiftUI +import SwiftVB +import SwiftGlass + +#if os(iOS) +import Drops +#endif + +@available(iOS 15.0, watchOS 8.0, macOS 12.0, tvOS 17.0, *) +extension SwiftNEW { + public var body: some View { + Button(action: { + if showDrop { + #if os(iOS) + drop() + #endif + } else { + show = true + } + }) { + if size == "mini" { + Label(label, systemImage: labelImage) + } + else if size == "normal" || size == "simple" { + Label(label, systemImage: labelImage) + #if !os(tvOS) + .frame(width: 300, height: 50) + #else + .frame(width: 400, height: 50) + #endif + #if os(iOS) && !os(visionOS) + .foregroundColor(labelColor) + .background(color) + .cornerRadius(15) + #endif + } + } + .opacity(size == "invisible" ? 0 : 100) + .glass(shadowColor: color) + .sheet(isPresented: $show) { + ZStack { + if mesh { + MeshView(color: $color) + } + if specialEffect == "Christmas" { + SnowfallView() + } + sheetCurrent + .sheet(isPresented: $historySheet) { + if #available(iOS 16.4, tvOS 16.4, *) { + sheetHistory + .presentationBackground(.thinMaterial) + } else { + sheetHistory + } + } + #if os(visionOS) + .padding() + #endif + } + } + } +} From bbc7f5e75162477c540ef42b5d15b05354d8a677 Mon Sep 17 00:00:00 2001 From: MING <54872601+1998code@users.noreply.github.com> Date: Mon, 9 Jun 2025 22:58:43 +0800 Subject: [PATCH 2/2] Update Sources/SwiftNEW/Views/SwiftNEW+View.swift Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- Sources/SwiftNEW/Views/SwiftNEW+View.swift | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Sources/SwiftNEW/Views/SwiftNEW+View.swift b/Sources/SwiftNEW/Views/SwiftNEW+View.swift index a785724..59afe72 100644 --- a/Sources/SwiftNEW/Views/SwiftNEW+View.swift +++ b/Sources/SwiftNEW/Views/SwiftNEW+View.swift @@ -42,7 +42,7 @@ extension SwiftNEW { #endif } } - .opacity(size == "invisible" ? 0 : 100) + .opacity(size == "invisible" ? 0 : 1) .glass(shadowColor: color) .sheet(isPresented: $show) { ZStack {