1
0
mirror of https://github.com/imgproxy/imgproxy.git synced 2024-11-24 08:12:38 +02:00

Implement padding option (#358)

* Implement padding option

* Move padding `embed` to the right place

* Move padding `embed` to the right place

* Use general background option instead of specific padding's one

* Make padding options css-like and fully optional

* Add docs for new padding option

* Return error if padding embed fails

* Make padding outbounds and apply dpr for it

Co-authored-by: Ilya Melnitskiy <melnitskiy_i_m@onyx-team.com>
This commit is contained in:
ILYA 2020-04-09 12:43:56 +03:00 committed by GitHub
parent 026fb617b1
commit 12b415c9bd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 90 additions and 0 deletions

View File

@ -170,6 +170,24 @@ Defines an area of the image to be processed (crop before resize).
* `width` and `height` define the size of the area. When `width` or `height` is set to `0`, imgproxy will use the full width/height of the source image.
* `gravity` _(optional)_ accepts the same values as [gravity](#gravity) option. When `gravity` is not set, imgproxy will use the value of the [gravity](#gravity) option.
#### Padding
```
padding:%top:%right:%bottom:%left
pd:%top:%right:%bottom:%left
```
Defines padding size in css manner. All arguments are optional but at least one dimension must be set. Padded space is filled according to [background](#background) option.
* `top` - top padding (and all other sides if they won't be set explicitly);
* `right` - right padding (and left if it won't be set explicitly);
* `bottom` - bottom padding;
* `left` - left padding.
**📝Notes:**
* Padding is applied after all image transformations (except watermark) and enlarges generated image which means that if your resize dimensions were 100x200px and you applied `padding:10` option then you will get 120x220px image.
* Padding follows [dpr](#dpr) option so it will be scaled too if you set it.
#### Trim
```

View File

@ -453,6 +453,22 @@ func transformImage(ctx context.Context, img *vipsImage, data []byte, po *proces
}
}
if po.Padding.Enabled {
paddingTop := scaleInt(po.Padding.Top, po.Dpr)
paddingRight := scaleInt(po.Padding.Right, po.Dpr)
paddingBottom := scaleInt(po.Padding.Bottom, po.Dpr)
paddingLeft := scaleInt(po.Padding.Left, po.Dpr)
if err = img.Embed(
img.Width()+paddingLeft+paddingRight,
img.Height()+paddingTop+paddingBottom,
paddingLeft,
paddingTop,
po.Background,
); err != nil {
return err
}
}
checkTimeout(ctx)
if po.Watermark.Enabled && watermark != nil {

View File

@ -100,6 +100,14 @@ type cropOptions struct {
Gravity gravityOptions
}
type paddingOptions struct {
Enabled bool
Top int
Right int
Bottom int
Left int
}
type trimOptions struct {
Enabled bool
Threshold float64
@ -126,6 +134,7 @@ type processingOptions struct {
Enlarge bool
Extend extendOptions
Crop cropOptions
Padding paddingOptions
Trim trimOptions
Format imageType
Quality int
@ -208,6 +217,7 @@ func newProcessingOptions() *processingOptions {
Gravity: gravityOptions{Type: gravityCenter},
Enlarge: false,
Extend: extendOptions{Enabled: false, Gravity: gravityOptions{Type: gravityCenter}},
Padding: paddingOptions{Enabled: false},
Trim: trimOptions{Enabled: false, Threshold: 10, Smart: true},
Quality: conf.Quality,
MaxBytes: 0,
@ -556,6 +566,50 @@ func applyCropOption(po *processingOptions, args []string) error {
return nil
}
func applyPaddingOption(po *processingOptions, args []string) error {
nArgs := len(args)
if nArgs < 1 || nArgs > 4 {
return fmt.Errorf("Invalid padding arguments: %v", args)
}
po.Padding.Enabled = true
if nArgs > 0 && len(args[0]) > 0 {
if err := parseDimension(&po.Padding.Top, "padding top (+all)", args[0]); err != nil {
return err
}
po.Padding.Right = po.Padding.Top
po.Padding.Bottom = po.Padding.Top
po.Padding.Left = po.Padding.Top
}
if nArgs > 1 && len(args[1]) > 0 {
if err := parseDimension(&po.Padding.Right, "padding right (+left)", args[1]); err != nil {
return err
}
po.Padding.Left = po.Padding.Right
}
if nArgs > 2 && len(args[2]) > 0 {
if err := parseDimension(&po.Padding.Bottom, "padding bottom", args[2]); err != nil {
return err
}
}
if nArgs > 3 && len(args[3]) > 0 {
if err := parseDimension(&po.Padding.Left, "padding left", args[3]); err != nil {
return err
}
}
if po.Padding.Top == 0 && po.Padding.Right == 0 && po.Padding.Bottom == 0 && po.Padding.Left == 0 {
po.Padding.Enabled = false
}
return nil
}
func applyTrimOption(po *processingOptions, args []string) error {
nArgs := len(args)
@ -820,6 +874,8 @@ func applyProcessingOption(po *processingOptions, name string, args []string) er
return applyCropOption(po, args)
case "trim", "t":
return applyTrimOption(po, args)
case "padding", "pd":
return applyPaddingOption(po, args)
case "quality", "q":
return applyQualityOption(po, args)
case "max_bytes", "mb":