code: func (opts *DecodeOpts) rescaleDimensions(b image.Rectangle, swapDimensions bool) (width, height int, needRescale bool) {
  	w, h := b.Dx(), b.Dy()
  	mw, mh := opts.MaxWidth, opts.MaxHeight
  	mwf, mhf := opts.ScaleWidth, opts.ScaleHeight
  	if mw == 0 && mh == 0 && mwf == 0 && mhf == 0 {
  		return w, h, false
  	}
  
  	// Floating point compares probably only allow this to work if the values
  	// were specified as the literal 1 or 1.0, computed values will likely be
  	// off.  If Scale{Width,Height} end up being 1.0-epsilon we'll rescale
  	// when it probably wouldn't even be noticeable but that's okay.
  	if opts.ScaleWidth == 1.0 && opts.ScaleHeight == 1.0 {
  		return w, h, false
  	}
  
  	if swapDimensions {
  		w, h = h, w
  	}
  
  	// ScaleWidth and ScaleHeight overrule MaxWidth and MaxHeight
  	if mwf > 0.0 && mwf <= 1 {
  		mw = int(mwf * float32(w))
  	}
  	if mhf > 0.0 && mhf <= 1 {
  		mh = int(mhf * float32(h))
  	}
  
  	neww, newh := ScaledDimensions(w, h, mw, mh)
  	if neww > w || newh > h {
  		// Don't scale up.
  		return w, h, false
  	}
  
  	needRescale = neww != w || newh != h
  	if swapDimensions {
  		return newh, neww, needRescale
  	}
  	return neww, newh, needRescale
  }
docs: // rescaleDimensions computes the width & height in the pre-rotated
  // orientation needed to meet the post-rotation constraints of opts.
  // The image bound by b represents the pre-rotated dimensions of the image.
  // needRescale is true if the image requires a resize.