File indexing completed on 2024-05-12 15:58:15
0001 /* 0002 * SPDX-FileCopyrightText: 2017 Wolthera van Hövell tot Westerflier <griffinvalley@gmail.com> 0003 * 0004 * SPDX-License-Identifier: GPL-2.0-or-later 0005 */ 0006 0007 #ifndef KIS_EDGE_DETECTION_KERNEL_H 0008 #define KIS_EDGE_DETECTION_KERNEL_H 0009 0010 #include "kritaimage_export.h" 0011 #include "kis_types.h" 0012 0013 #include <Eigen/Core> 0014 #include <boost/optional.hpp> 0015 0016 class QRect; 0017 0018 class KRITAIMAGE_EXPORT KisEdgeDetectionKernel 0019 { 0020 public: 0021 KisEdgeDetectionKernel(); 0022 0023 enum FilterType { 0024 Simple, //A weird simple method used in our old sobel filter 0025 Prewit, //The simpler prewitt detection, which doesn't smooth. 0026 SobelVector //Sobel does smooth. The creation of bigger kernels is based on an approach regarding vectors. 0027 }; 0028 0029 enum FilterOutput { 0030 pythagorean, 0031 xGrowth, 0032 xFall, 0033 yGrowth, 0034 yFall, 0035 radian 0036 }; 0037 0038 /** 0039 * @brief createHorizontalMatrix 0040 * @param radius the radius. 1 makes a 3x3 kernel. 0041 * @param type One of the entries in the enum Filtertype 0042 * @param reverse which direction the gradient goes. 0043 * The horizontal gradient by default detects the rightmost edges. 0044 * Reversed it selects the leftmost edges. 0045 * @return 0046 */ 0047 0048 static Eigen::Matrix<qreal, Eigen::Dynamic, Eigen::Dynamic> 0049 createHorizontalMatrix(qreal radius, FilterType type, bool reverse = false); 0050 /** 0051 * @brief createVerticalMatrix 0052 * @param radius the radius. 1 makes a 3x3 kernel. 0053 * @param type One of the entries in the enum Filtertype 0054 * @param reverse which direction the gradient goes. 0055 * The vertical gradient by default detects the topmost edges. 0056 * Reversed it selects the bottommost edges. 0057 * @return 0058 */ 0059 static Eigen::Matrix<qreal, Eigen::Dynamic, Eigen::Dynamic> 0060 createVerticalMatrix(qreal radius, FilterType type, bool reverse = false); 0061 0062 static KisConvolutionKernelSP 0063 createHorizontalKernel(qreal radius, FilterType type, bool denormalize = true, bool reverse = false); 0064 0065 static KisConvolutionKernelSP 0066 createVerticalKernel(qreal radius, FilterType type, bool denormalize = true, bool reverse = false); 0067 0068 static int kernelSizeFromRadius(qreal radius); 0069 static qreal sigmaFromRadius(qreal radius); 0070 0071 /** 0072 * @brief applyEdgeDetection 0073 * This applies the edge detection filter to the device. 0074 * @param device the device to apply to. 0075 * @param rect the affected rect. 0076 * @param xRadius the radius of the horizontal sampling, radius of 0 is effectively disabling it. 0077 * @param yRadius the radius of the vertical sampling, refius of 0 is effectively disabling it. 0078 * @param type the type can be prewitt, sobel or simple, each of which 0079 * have a different sampling for the eventual edge detection. 0080 * @param channelFlags the affected channels. 0081 * @param progressUpdater the progress updater if it exists. 0082 * @param output the output mode. 0083 * @param writeToAlpha whether or not to have the result applied to the transparency than the color channels, 0084 * this is useful for fringe effects. 0085 */ 0086 static void applyEdgeDetection(KisPaintDeviceSP device, 0087 const QRect& rect, 0088 qreal xRadius, qreal yRadius, 0089 FilterType type, 0090 const QBitArray &channelFlags, 0091 KoUpdater *progressUpdater, 0092 FilterOutput output = pythagorean, 0093 bool writeToAlpha = false); 0094 /** 0095 * @brief converToNormalMap 0096 * Convert a channel of the device to a normal map. The channel will be interpreted as a heightmap. 0097 * @param device the device 0098 * @param rect the rectangle to apply this to. 0099 * @param xRadius the xradius 0100 * @param yRadius the yradius 0101 * @param type the edge detection filter. 0102 * @param channelToConvert the channel to use as a grayscale. 0103 * @param channelOrder the order in which the xyz coordinates ought to be written to the pixels. 0104 * @param channelFlip whether to flip the channels 0105 * @param channelFlags the channel flags 0106 * @param progressUpdater 0107 */ 0108 static void convertToNormalMap(KisPaintDeviceSP device, 0109 const QRect & rect, 0110 qreal xRadius, 0111 qreal yRadius, 0112 FilterType type, 0113 int channelToConvert, 0114 QVector<int> channelOrder, 0115 QVector<bool> channelFlip, 0116 const QBitArray &channelFlags, 0117 KoUpdater *progressUpdater, 0118 boost::optional<bool> useFftw = boost::none); 0119 }; 0120 0121 #endif // KIS_EDGE_DETECTION_KERNEL_H