Advertisement
Guest User

Untitled

a guest
Jan 13th, 2023
42
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Swift 6.28 KB | None | 0 0
  1. import CoreImage
  2. import CoreImage.CIFilterBuiltins
  3. import SwiftUI
  4.  
  5. struct ContentView: View {
  6.    
  7.     @State private var image: Image?
  8.     @State private var filterIntensity = 0.5
  9.     @State private var filterRadius = 5.0
  10.     @State private var filterScale = 5.0
  11.    
  12.     @State private var showingImagePicker = false
  13.     @State private var inputImage: UIImage?
  14.     @State private var processedImage: UIImage?
  15.    
  16.     @State private var currentFilter: CIFilter = CIFilter.sepiaTone()
  17.     let context = CIContext()
  18.    
  19.     @State private var showingFilterSheet = false
  20.     @State private var showingSaveError: Bool = false
  21.  
  22.    
  23.     var body: some View {
  24.         NavigationStack {
  25.             VStack{
  26.                 ZStack{
  27.                     Rectangle()
  28.                         .fill(.secondary)
  29.                     Text("Tap to select a picture")
  30.                         .foregroundColor(.white)
  31.                         .font(.headline)
  32.                    
  33.                     image?
  34.                         .resizable()
  35.                         .scaledToFit()
  36.                 }
  37.                 .onTapGesture {
  38.                     showingImagePicker = true
  39.                 }
  40.                 VStack{
  41.                    
  42.                     if currentFilter.inputKeys.contains(kCIInputIntensityKey){
  43.                        
  44.                         HStack{
  45.                             Text("Intensity")
  46.                             Slider(value: $filterIntensity)
  47.                                 .onChange(of: filterIntensity) { _ in
  48.                                     applyProcessing()
  49.                                 }
  50.                         }.padding(.vertical)
  51.                     }
  52.                     if currentFilter.inputKeys.contains(kCIInputRadiusKey){
  53.                        
  54.                         HStack{
  55.                             Text("Radius")
  56.                             Slider(value: $filterRadius, in: 0...200)
  57.                                 .onChange(of: filterRadius) { _ in
  58.                                     applyProcessing()
  59.                                 }
  60.                            
  61.                         }.padding(.vertical)
  62.                     }
  63.                     if currentFilter.inputKeys.contains(kCIInputScaleKey){
  64.                        
  65.                         HStack{
  66.                             Text("Scale")
  67.                             Slider(value: $filterScale, in: 0...10)
  68.                                 .onChange(of: filterScale) { _ in
  69.                                     applyProcessing()
  70.                                 }
  71.                         }.padding(.vertical)
  72.                     }
  73.                 }
  74.                 .padding(.vertical)
  75.                
  76.                 HStack {
  77.                     Button("Change filter") {
  78.                         showingFilterSheet = true
  79.                     }
  80.                     Spacer()
  81.                    
  82.                     Button("Save", action: save)
  83.                         .disabled(inputImage == nil)
  84.                 }
  85.             }
  86.             .padding([.horizontal, .bottom])
  87.             .navigationTitle("Instafilter")
  88.             .onChange(of: inputImage) { _ in loadImage() }
  89.             .sheet(isPresented: $showingImagePicker) {
  90.                 ImagePicker(image: $inputImage)
  91.             }
  92.             .confirmationDialog("Select a filter", isPresented: $showingFilterSheet) {
  93.                 Group{
  94.                     Button("Bloom") { setFilter(CIFilter.bloom()) }
  95.                     Button("Crystallize") { setFilter(CIFilter.crystallize()) }
  96.                     Button("Edges") { setFilter(CIFilter.edges()) }
  97.                     Button("Gaussian Blur") { setFilter(CIFilter.gaussianBlur()) }
  98.                     Button("Noir") { setFilter(CIFilter.photoEffectNoir()) }
  99.                     Button("Pixellate") { setFilter(CIFilter.pixellate()) }
  100.                     Button("Pointillize") { setFilter(CIFilter.pointillize()) }
  101.                     Button("Sepia Tone") { setFilter(CIFilter.sepiaTone()) }
  102.                     Button("Unsharp mask") { setFilter(CIFilter.unsharpMask()) }
  103.                     Button("Vignette") { setFilter(CIFilter.vignette()) }
  104.                 }
  105.                 Group{
  106.                     Button("Cancel", role: .cancel ) {}
  107.                 }
  108.             }
  109.             .alert("oops", isPresented: $showingSaveError) {
  110.                 Button("Ok") { }
  111.             } message: {
  112.                     Text("Sorry, there was an error saving your image – please check that you have allowed permission for this app to save photos.")
  113.                 }
  114.             }
  115.         }
  116.     func loadImage() {
  117.         guard let inputImage = inputImage else { return }
  118.         let beginImage = CIImage(image: inputImage)
  119.             currentFilter.setValue(beginImage, forKey: kCIInputImageKey)
  120.             applyProcessing()
  121.     }
  122.    
  123.     func save() {
  124.         guard let processedImage = processedImage else { return }
  125.         let imageSaver = ImageSaver()
  126.         imageSaver.successHandler = {
  127.             print("Success!")
  128.         }
  129.         imageSaver.errorHandler = { _ in
  130.             showingSaveError = true
  131.         }
  132.         imageSaver.writeToPhotoAlbum(image: processedImage)
  133.     }
  134.    
  135.     func applyProcessing() {
  136.         let inputKeys = currentFilter.inputKeys
  137.        
  138.         if inputKeys.contains(kCIInputIntensityKey) {
  139.             currentFilter.setValue(filterIntensity, forKey: kCIInputIntensityKey) }
  140.         if inputKeys.contains(kCIInputRadiusKey) {
  141.             currentFilter.setValue(filterRadius, forKey: kCIInputRadiusKey) }
  142.         if inputKeys.contains(kCIInputScaleKey) {
  143.             currentFilter.setValue(filterScale, forKey: kCIInputScaleKey) }
  144.        
  145.         guard let outputImage = currentFilter.outputImage else { return }
  146.        
  147.         if let cgimg = context.createCGImage(outputImage, from: outputImage.extent) {
  148.             let uiImage = UIImage(cgImage: cgimg)
  149.             image = Image(uiImage: uiImage)
  150.             processedImage = uiImage
  151.         }
  152.     }
  153.    
  154.     func setFilter(_ filter: CIFilter) {
  155.         currentFilter = filter
  156.         loadImage()
  157.     }
  158. }
  159.  
  160. struct ContentView_Previews: PreviewProvider {
  161.     static var previews: some View {
  162.         ContentView()
  163.        
  164.     }
  165. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement