# CIHazeFilterSample

- `Download example`

A PyObjC Example without documentation

## Sources

### HazeFilterView.py

    import Cocoa
    import MyHazeFilter
    import objc
    import Quartz

    class HazeFilterView(Cocoa.NSView):
        filter = objc.ivar()  # noqa: A003
        distance = objc.ivar(type=objc._C_FLT)
        slope = objc.ivar(type=objc._C_FLT)

        def distanceSliderChanged_(self, sender):
            self.distance = sender.floatValue()
            self.setNeedsDisplay_(True)

        def slopeSliderChanged_(self, sender):
            self.slope = sender.floatValue()
            self.setNeedsDisplay_(True)

        def drawRect_(self, rect):
            cg = Quartz.CGRectMake(
                Cocoa.NSMinX(rect),
                Cocoa.NSMinY(rect),
                Cocoa.NSWidth(rect),
                Cocoa.NSHeight(rect),
            )

            context = Cocoa.NSGraphicsContext.currentContext().CIContext()

            if self.filter is None:
                # make sure initialize is called
                MyHazeFilter.MyHazeFilter.pyobjc_classMethods.class__()

                url = Cocoa.NSURL.fileURLWithPath_(
                    Cocoa.NSBundle.mainBundle().pathForResource_ofType_("CraterLake", "jpg")
                )
                self.filter = Quartz.CIFilter.filterWithName_("MyHazeRemover")
                self.filter.setValue_forKey_(
                    Quartz.CIImage.imageWithContentsOfURL_(url), "inputImage"
                )

                self.filter.setValue_forKey_(
                    Quartz.CIColor.colorWithRed_green_blue_(0.7, 0.9, 1), "inputColor"
                )

            self.filter.setValue_forKey_(self.distance, "inputDistance")
            self.filter.setValue_forKey_(self.slope, "inputSlope")

            if context is not None:
                context.drawImage_atPoint_fromRect_(
                    self.filter.valueForKey_("outputImage"), cg.origin, cg
                )

### MyHazeFilter.py

    import Cocoa
    import objc
    import Quartz
    from objc import super  # noqa: A004

    _hazeRemovalKernel = None

    class MyHazeFilter(Quartz.CIFilter):
        inputImage = objc.ivar()
        inputColor = objc.ivar()
        inputDistance = objc.ivar()
        inputSlope = objc.ivar()

        @classmethod
        def initialize(cls):
            Quartz.CIFilter.registerFilterName_constructor_classAttributes_(
                "MyHazeRemover",
                cls,
                {
                    Quartz.kCIAttributeFilterDisplayName: "Haze Remover",
                    Quartz.kCIAttributeFilterCategories: [
                        Quartz.kCICategoryColorAdjustment,
                        Quartz.kCICategoryVideo,
                        Quartz.kCICategoryStillImage,
                        Quartz.kCICategoryInterlaced,
                        Quartz.kCICategoryNonSquarePixels,
                    ],
                    "inputDistance": {
                        Quartz.kCIAttributeMin: 0.0,
                        Quartz.kCIAttributeMax: 1.0,
                        Quartz.kCIAttributeSliderMin: 0.0,
                        Quartz.kCIAttributeSliderMax: 0.7,
                        Quartz.kCIAttributeDefault: 0.2,
                        Quartz.kCIAttributeIdentity: 0.0,
                        Quartz.kCIAttributeType: Quartz.kCIAttributeTypeScalar,
                    },
                    "inputSlope": {
                        Quartz.kCIAttributeSliderMin: -0.01,
                        Quartz.kCIAttributeSliderMax: 0.01,
                        Quartz.kCIAttributeDefault: 0.0,
                        Quartz.kCIAttributeIdentity: 0.0,
                        Quartz.kCIAttributeType: Quartz.kCIAttributeTypeScalar,
                    },
                    "inputColor": {
                        Quartz.kCIAttributeDefault: Quartz.CIColor.colorWithRed_green_blue_alpha_(
                            1.0, 1.0, 1.0, 1.0
                        )
                    },
                },
            )

        @classmethod
        def filterWithName_(cls, name):
            return cls.alloc().init()

        def init(self):
            global _hazeRemovalKernel

            if _hazeRemovalKernel is None:
                bundle = Cocoa.NSBundle.bundleForClass_(type(self))
                with open(
                    bundle.pathForResource_ofType_("MyHazeRemoval", "cikernel")
                ) as fp:
                    code = fp.read()
                kernels = Quartz.CIKernel.kernelsWithString_(code)
                _hazeRemovalKernel = kernels[0]

            return super().init()

        def outputImage(self):
            src = Quartz.CISampler.samplerWithImage_(self.inputImage)

            return self.apply_arguments_options_(
                _hazeRemovalKernel,
                (src, self.inputColor, self.inputDistance, self.inputSlope),
                {"definition": src.definition()},
            )

### main.py

    import HazeFilterView  # noqa: F401
    import MyHazeFilter  # noqa: F401
    from PyObjCTools import AppHelper

    AppHelper.runEventLoop()

### setup.py

    """
    Script for building the example.

    Usage:
        python3 setup.py py2app
    """
    from setuptools import setup

    setup(
        name="CIHazeFilterSample",
        app=["main.py"],
        data_files=["English.lproj", "MyHazeRemoval.cikernel", "CraterLake.jpg"],
        setup_requires=["py2app", "pyobjc-framework-Cocoa", "pyobjc-framework-Quartz"],
    )