@@ -1575,6 +1575,70 @@ export const transformationSchema: TransformationSchema[] = [
15751575 } ,
15761576 ] ,
15771577 } ,
1578+ {
1579+ key : "adjust-border" ,
1580+ name : "Border" ,
1581+ description :
1582+ "Add a border to the image. Specify a border width and color." ,
1583+ docsLink : "https://imagekit.io/docs/effects-and-enhancements#border---b" ,
1584+ defaultTransformation : { } ,
1585+ schema : z
1586+ . object ( {
1587+ borderWidth : z . coerce
1588+ . number ( {
1589+ invalid_type_error : "Should be a number." ,
1590+ } )
1591+ . int ( )
1592+ . min ( 1 )
1593+ . optional ( ) ,
1594+ borderColor : colorValidator
1595+ } )
1596+ . refine (
1597+ ( val ) => {
1598+ if (
1599+ Object . values ( val ) . some ( ( v ) => v !== undefined && v !== null )
1600+ ) {
1601+ return true
1602+ }
1603+ return false
1604+ } ,
1605+ {
1606+ message : "Border width and color are required" ,
1607+ path : [ ] ,
1608+ } ,
1609+ ) ,
1610+ transformations : [
1611+ {
1612+ label : "Border Width" ,
1613+ name : "borderWidth" ,
1614+ fieldType : "input" ,
1615+ isTransformation : false ,
1616+ transformationGroup : "border" ,
1617+ helpText :
1618+ "Enter a border width" ,
1619+ fieldProps : {
1620+ defaultValue : 1 ,
1621+ min : 1 ,
1622+ max : 99 ,
1623+ step : 1 ,
1624+ } ,
1625+ } ,
1626+ {
1627+ label : "Border Color" ,
1628+ name : "borderColor" ,
1629+ fieldType : "color-picker" ,
1630+ isTransformation : false ,
1631+ transformationGroup : "border" ,
1632+ helpText :
1633+ "Select the color of the border." ,
1634+ fieldProps :{
1635+ hideOpacity : true ,
1636+ showHexAlpha : false ,
1637+ defaultValue : "#000000" ,
1638+ } ,
1639+ } ,
1640+ ] ,
1641+ } ,
15781642 {
15791643 key : "adjust-trim" ,
15801644 name : "Trim" ,
@@ -1713,21 +1777,87 @@ export const transformationSchema: TransformationSchema[] = [
17131777 transformationGroup : "colorReplace" ,
17141778 helpText :
17151779 "Select the source color you want to replace (optional - if not specified, dominant color will be replaced)." ,
1780+ } ,
1781+ ] ,
1782+ } ,
1783+ {
1784+ key : "adjust-sharpen" ,
1785+ name : "Sharpen" ,
1786+ description :
1787+ "Sharpen the image to highlight the edges and finer details within an image." ,
1788+ docsLink : "https://imagekit.io/docs/effects-and-enhancements#sharpen---e-sharpen" ,
1789+ defaultTransformation : { } ,
1790+ schema : z
1791+ . object ( {
1792+ sharpenEnabled : z . coerce
1793+ . boolean ( {
1794+ invalid_type_error : "Should be a boolean." ,
1795+ } )
1796+ . optional ( ) ,
1797+ sharpen :
1798+ z . union ( [
1799+ z . literal ( "auto" ) ,
1800+ z . coerce
1801+ . number ( {
1802+ invalid_type_error : "Should be a number." ,
1803+ } )
1804+ . int ( )
1805+ . min ( 1 )
1806+ . max ( 99 )
1807+ ] )
1808+ . optional ( ) ,
1809+ } )
1810+ . refine (
1811+ ( val ) => {
1812+ if (
1813+ Object . values ( val ) . some ( ( v ) => v !== undefined && v !== null )
1814+ ) {
1815+ return true
1816+ }
1817+ return false
1818+ } ,
1819+ {
1820+ message : "At least one value is required" ,
1821+ path : [ ] ,
1822+ } ,
1823+ ) ,
1824+ transformations : [
1825+ {
1826+ label : "Sharpen Image" ,
1827+ name : "sharpenEnabled" ,
1828+ fieldType : "switch" ,
1829+ isTransformation : false ,
1830+ transformationGroup : "sharpen" ,
1831+ helpText :
1832+ "Toggle to sharpen the image to highlight the edges and finer details within an image." ,
1833+ } ,
1834+ {
1835+ label : "Threshold" ,
1836+ name : "sharpen" ,
1837+ fieldType : "slider" ,
1838+ isTransformation : false ,
1839+ transformationGroup : "sharpen" ,
1840+ helpText :
1841+ "Sharpen the image to highlight the edges and finer details within an image. Use a threshold between 1 and 99." ,
1842+ fieldProps : {
1843+ autoOption : true ,
1844+ defaultValue : "auto" ,
1845+ min : 1 ,
1846+ max : 99 ,
1847+ step : 1 ,
1848+ } ,
1849+ isVisible : ( { sharpenEnabled } ) => sharpenEnabled === true ,
17161850 } ,
1717-
1718-
17191851 ] ,
17201852 } ,
17211853 ] ,
17221854 } ,
17231855 {
17241856 key : "ai" ,
17251857 name : "AI Transformations" ,
1726- items : [
1727- {
1858+ items : [ {
17281859 key : "ai-removedotbg" ,
17291860 name : "Remove Background using Remove.bg" ,
1730- // This option removes the background using the third-party remove.bg service.
17311861 description :
17321862 "Remove the background of the image using Remove.bg (external service). This isolates the subject and makes the background transparent." ,
17331863 docsLink :
@@ -2589,6 +2719,29 @@ export const transformationSchema: TransformationSchema[] = [
25892719 invalid_type_error : "Should be a number." ,
25902720 } )
25912721 . optional ( ) ,
2722+ borderWidth : z . coerce
2723+ . number ( {
2724+ invalid_type_error : "Should be a number." ,
2725+ } )
2726+ . optional ( ) ,
2727+ borderColor : colorValidator . optional ( ) ,
2728+ sharpenEnabled : z . coerce
2729+ . boolean ( {
2730+ invalid_type_error : "Should be a boolean." ,
2731+ } )
2732+ . optional ( ) ,
2733+ sharpen : z
2734+ . union ( [
2735+ z . literal ( "auto" ) ,
2736+ z . coerce
2737+ . number ( {
2738+ invalid_type_error : "Should be a number." ,
2739+ } )
2740+ . int ( )
2741+ . min ( 1 )
2742+ . max ( 99 ) ,
2743+ ] )
2744+ . optional ( ) ,
25922745 } )
25932746 . refine (
25942747 ( val ) => {
@@ -2789,6 +2942,66 @@ export const transformationSchema: TransformationSchema[] = [
27892942 defaultValue : "0" ,
27902943 } ,
27912944 } ,
2945+ {
2946+ label : "Border Width" ,
2947+ name : "borderWidth" ,
2948+ fieldType : "input" ,
2949+ isTransformation : false ,
2950+ transformationKey : "borderWidth" ,
2951+ transformationGroup : "imageLayer" ,
2952+ fieldProps : {
2953+ defaultValue : 0 ,
2954+ } ,
2955+ helpText :
2956+ "Enter the width of the border of the overlay image." ,
2957+ } ,
2958+ {
2959+ label : "Border Color" ,
2960+ name : "borderColor" ,
2961+ fieldType : "color-picker" ,
2962+ isTransformation : false ,
2963+ transformationKey : "borderColor" ,
2964+ transformationGroup : "imageLayer" ,
2965+ isVisible : ( { borderWidth } ) => borderWidth as number > 0 ,
2966+ helpText :
2967+ "Select the color of the border of the overlay image." ,
2968+ fieldProps : {
2969+ hideOpacity : true ,
2970+ showHexAlpha : false ,
2971+ defaultValue : "#000000" ,
2972+ } ,
2973+ } ,
2974+ {
2975+ label : "Sharpen Overlay" ,
2976+ name : "sharpenEnabled" ,
2977+ fieldType : "switch" ,
2978+ isTransformation : true ,
2979+ transformationKey : "sharpenEnabled" ,
2980+ transformationGroup : "imageLayer" ,
2981+ helpText :
2982+ "Toggle to sharpen the overlay image to highlight edges and fine details." ,
2983+ fieldProps : {
2984+ defaultValue : false ,
2985+ } ,
2986+ } ,
2987+ {
2988+ label : "Sharpen Threshold" ,
2989+ name : "sharpen" ,
2990+ fieldType : "slider" ,
2991+ isTransformation : true ,
2992+ transformationKey : "sharpen" ,
2993+ transformationGroup : "imageLayer" ,
2994+ helpText :
2995+ "Sharpen the overlay image. Use a threshold between 1 and 99 (or auto)." ,
2996+ fieldProps : {
2997+ autoOption : true ,
2998+ defaultValue : "auto" ,
2999+ min : 1 ,
3000+ max : 99 ,
3001+ step : 1 ,
3002+ } ,
3003+ isVisible : ( { sharpenEnabled } ) => sharpenEnabled === true ,
3004+ }
27923005 ] ,
27933006 } ,
27943007 ] ,
@@ -3170,6 +3383,18 @@ export const transformationFormatters: Record<
31703383 overlayTransform . blur = values . blur
31713384 }
31723385
3386+ // Sharpen overlay (same semantics as base-image sharpen: auto => empty string)
3387+ if ( values . sharpenEnabled === true ) {
3388+ if ( values . sharpen === "auto" ) {
3389+ overlayTransform . sharpen = ""
3390+ } else if ( typeof values . sharpen === "number" ) {
3391+ overlayTransform . sharpen = values . sharpen
3392+ }
3393+ }
3394+ if ( ( values . borderWidth && typeof values . borderWidth === "number" && values . borderWidth > 0 ) && ( values . borderColor && typeof values . borderColor === "string" ) ) {
3395+ overlayTransform . b = `${ values . borderWidth } _${ values . borderColor . replace ( / ^ # / , "" ) } `
3396+ }
3397+
31733398 if ( Object . keys ( overlayTransform ) . length > 0 ) {
31743399 overlay . transformation = [ overlayTransform ]
31753400 }
@@ -3265,4 +3490,25 @@ export const transformationFormatters: Record<
32653490
32663491 transforms . cr = params . join ( "_" )
32673492 } ,
3493+ border : ( values , transforms ) => {
3494+ const { borderWidth, borderColor } = values as {
3495+ borderWidth ?: number
3496+ borderColor ?: string
3497+ }
3498+ if ( ! borderWidth || ! borderColor ) return
3499+ const cleanBorderColor = borderColor . replace ( / ^ # / , "" )
3500+ transforms . b = `${ borderWidth } _${ cleanBorderColor } `
3501+ } ,
3502+ sharpen : ( values , transforms ) => {
3503+ const { sharpenEnabled, sharpen } = values as {
3504+ sharpenEnabled ?: boolean
3505+ sharpen ?: "auto" | number
3506+ }
3507+ if ( ! sharpenEnabled ) return
3508+ if ( sharpen === "auto" ) {
3509+ transforms . sharpen = ""
3510+ } else {
3511+ transforms . sharpen = sharpen
3512+ }
3513+ } ,
32683514}
0 commit comments