SnapShield
Protect sensitive SwiftUI views from screenshots and screen recordings with customizable placeholders. Simple, lightweight, and easy to integrate.
Install / Use
/learn @EmadBeyrami/SnapShieldREADME
🛡️ SnapShield
A lightweight Swift package that protects sensitive content in your iOS, VisionOS, MacOS and tvOS apps from screenshots, screen recordings, and screen sharing.
</div>🎯 Features
- 🔒 Complete Protection - Secures content from screenshots, screen recordings, and screen sharing
- 🎨 Customizable Placeholders - Show custom views when content is being captured
- ⚡ Easy Integration - Simple SwiftUI modifier API
- 🪶 Lightweight - Zero dependencies, minimal footprint
- 📱 Cross-Platform - Works on iOS and tvOS
- 🎮 Example Project Included - Learn from real-world implementations
- 🎮 Example Project Included - Learn from real-world implementations
📸 Demo
Normal View vs Screenshot
<!-- Add screenshot showing normal app view -->Normal View:
https://github.com/user-attachments/assets/7a6c29a3-26b5-4264-92fc-e62959e52638
<!-- Add screenshot showing what appears when screenshot is taken -->When Screenshot/Recording:
https://github.com/user-attachments/assets/dc37695e-a6b6-434a-8473-a19e9a9be6cc
🚀 Installation
Swift Package Manager
Option 1: Install via Xcode
- Open your project in Xcode
- Go to File → Add Package Dependencies
- Enter the package URL:
https://github.com/EmadBeyrami/SnapShield.git - Click Add Package
- Select your desired version (Dependency Rule)
- Click Add Package again to confirm
Option 2: Install via Package.swift
Add SnapShield to your Package.swift dependencies:
dependencies: [
.package(url: "https://github.com/EmadBeyrami/SnapShield.git", from: "1.0.0")
]
Then add it to your target dependencies:
targets: [
.target(
name: "YourTarget",
dependencies: ["SnapShield"]
)
]
⚡ Quick Start
After installing the package, import SnapShield and start protecting your content:
import SwiftUI
import SnapShield
struct ContentView: View {
var body: some View {
VStack(spacing: 20) {
// Hide content completely
Text("Password: MySecret123")
.snapShield()
// Show custom placeholder
Text("Credit Card: 1234-5678-9012-3456")
.snapShield {
Text("🔒 Protected")
.font(.headline)
}
}
}
}
That's it! Your sensitive content is now protected from screenshots, screen recordings, and screen sharing.
🎮 Example Project
Want to see SnapShield in action? Check out the included example project in the repository!
The example app demonstrates:
- Basic Protection - Simple content hiding with
.snapShield() - Custom Placeholders - Showing custom views during screenshots
- Bank Card Demo - Realistic credit card protection with styled placeholder
- Multiple Protected Views - Combining different protection strategies in one screen
To run the example:
git clone https://github.com/EmadBeyrami/SnapShield.git
cd SnapShield
open SnapShieldExample/SnapShieldExample.xcodeproj
Then build and run on a simulator or device to test screenshot protection!
💡 Tip: To test the protection, run the app on a real device and try taking screenshots (Power + Volume Up) or start screen recording. You'll see the protected content is replaced with either a blank view or your custom placeholder!
📖 Usage
Import SnapShield in your SwiftUI views:
import SwiftUI
import SnapShield
Basic Usage - Hide Content
Simply hide sensitive content when screenshots or recordings are attempted:
Text("Secret Password: 12345")
.snapShield()
The content will be completely hidden (blank) during screenshots, screen recordings, or screen sharing.
Advanced Usage - Custom Placeholder
Show a custom view when content is being captured:
Text("Credit Card: 1234-5678-9012-3456")
.snapShield {
VStack {
Image(systemName: "lock.shield")
.font(.system(size: 60))
.foregroundColor(.red)
Text("Protected Content")
.font(.headline)
.foregroundColor(.gray)
}
}
💡 Examples
Simple Text Placeholder
VStack {
Text("Bank Account: 123456789")
Text("Balance: $50,000")
}
.snapShield {
Text("🔒 This content is hidden")
.font(.title)
.foregroundColor(.gray)
}
Image Placeholder
Image("sensitiveDocument")
.resizable()
.scaledToFit()
.snapShield {
Image("protectedPlaceholder")
.resizable()
.scaledToFit()
}
Styled Placeholder
PersonalInfoView()
.snapShield {
ZStack {
Color.black
VStack(spacing: 20) {
Image(systemName: "eye.slash.fill")
.font(.system(size: 100))
.foregroundColor(.white)
Text("Content Protected")
.font(.title)
.foregroundColor(.white)
Text("This information cannot be captured")
.font(.caption)
.foregroundColor(.gray)
}
}
}
Bank Card Example
Protect sensitive financial information with a professional placeholder:
struct BankCardView: View {
var body: some View {
// Your card UI design
ZStack {
LinearGradient(colors: [.blue, .purple], startPoint: .topLeading, endPoint: .bottomTrailing)
VStack(alignment: .leading, spacing: 20) {
Text("4532 1234 5678 9010")
.font(.system(size: 24, design: .monospaced))
Text("JOHN DOE")
// ... more card details
}
}
.snapShield {
// Placeholder shown in screenshots
ZStack {
LinearGradient(colors: [.gray, .gray.opacity(0.5)], startPoint: .topLeading, endPoint: .bottomTrailing)
VStack(spacing: 15) {
Image(systemName: "lock.shield.fill")
.font(.system(size: 50))
.foregroundColor(.white)
Text("Card Information Protected")
.font(.headline)
.foregroundColor(.white)
}
}
}
}
}
Multiple Protected Views
You can protect different sections with different strategies on the same screen:
ScrollView {
VStack(spacing: 20) {
// Section 1: Completely hidden
VStack {
Text("Password: super_secret_123")
}
.padding()
.background(Color.red.opacity(0.1))
.snapShield()
// Section 2: Custom placeholder
VStack {
Text("API Key: sk_live_abcd1234efgh5678")
}
.padding()
.background(Color.orange.opacity(0.1))
.snapShield {
VStack {
Image(systemName: "key.fill")
.font(.largeTitle)
Text("API Key Hidden")
}
.padding()
}
// Section 3: Not protected (public info)
VStack {
Text("Public Info: This is visible in screenshots")
}
.padding()
.background(Color.green.opacity(0.1))
}
}
Custom View Component
Create reusable placeholder components:
struct ProtectedPlaceholder: View {
var body: some View {
VStack(spacing: 16) {
Image(systemName: "hand.raised.fill")
.font(.system(size: 80))
.foregroundColor(.red)
Text("Screenshot Blocked")
.font(.title2)
.bold()
Text("This content is protected for your security")
.font(.body)
.multilineTextAlignment(.center)
.foregroundColor(.secondary)
}
.padding()
}
}
// Usage
SensitiveDataView()
.snapShield {
ProtectedPlaceholder()
}
Alert-Style Protection
VStack(spacing: 15) {
Image(systemName: "creditcard.fill")
.font(.system(size: 50))
Text("Credit Card: 1234-5678-9012-3456")
Text("CVV: 123")
Text("Exp: 12/25")
}
.padding()
.snapShield {
ZStack {
Color.red.opacity(0.2)
VStack(spacing: 15) {
Image(systemName: "exclamationmark.shield.fill")
.font(.system(size: 60))
.foregroundColor(.red)
Text("Protected Content")
.font(.headline)
Text("Screenshots are not allowed")
.font(.caption)
}
}
}
For more examples, check out the SnapShieldExample project in the repository!
🔧 How It Works
SnapShield leverages iOS's secure text field behavior to protect your content. When you mark a view with .snapShield():
- The content is rendered inside a secure container (similar to password fields)
- During screenshots, screen recordings, or screen sharing, the secure container becomes invisible
- If you've provided a custom placeholder, it appears in place of the hidden content
- Normal app usage is unaffected - users see and interact with content nor
Related Skills
healthcheck
354.0kHost security hardening and risk-tolerance configuration for OpenClaw deployments
prose
354.0kOpenProse VM skill pack. Activate on any `prose` command, .prose files, or OpenProse mentions; orchestrates multi-agent workflows.
qqbot-channel
354.0kQQ 频道管理技能。查询频道列表、子频道、成员、发帖、公告、日程等操作。使用 qqbot_channel_api 工具代理 QQ 开放平台 HTTP 接口,自动处理 Token 鉴权。当用户需要查看频道、管理子频道、查询成员、发布帖子/公告/日程时使用。
Writing Hookify Rules
112.2kThis skill should be used when the user asks to "create a hookify rule", "write a hook rule", "configure hookify", "add a hookify rule", or needs guidance on hookify rule syntax and patterns.
