fix(StatusImageCrop): fix wrong initial image fit
The initial fit was computed for the square crop-window updates: 5118
This commit is contained in:
parent
07e711e30c
commit
ee3effcdd1
|
@ -82,12 +82,7 @@ Item {
|
||||||
\qmlproperty rect StatusImageCropPanel::cropRect
|
\qmlproperty rect StatusImageCropPanel::cropRect
|
||||||
\sa StatusImageCrop::cropRect
|
\sa StatusImageCrop::cropRect
|
||||||
*/
|
*/
|
||||||
property alias cropRect: cropEditor.cropRect
|
readonly property alias cropRect: cropEditor.cropRect
|
||||||
/*!
|
|
||||||
\qmlproperty rect StatusImageCropPanel::cropRect
|
|
||||||
\sa StatusImageCrop::cropRect
|
|
||||||
*/
|
|
||||||
readonly property alias cropWindow: cropEditor.cropWindow
|
|
||||||
/*!
|
/*!
|
||||||
\qmlproperty real StatusImageCrop::scrollZoomFactor
|
\qmlproperty real StatusImageCrop::scrollZoomFactor
|
||||||
How fast is image scaled (zoomed) when using mouse scroll
|
How fast is image scaled (zoomed) when using mouse scroll
|
||||||
|
@ -116,16 +111,11 @@ Item {
|
||||||
QtObject {
|
QtObject {
|
||||||
id: d
|
id: d
|
||||||
|
|
||||||
|
readonly property int referenceWindowWidth: 1000
|
||||||
function updateAspectRatio(newAR) {
|
function updateAspectRatio(newAR) {
|
||||||
// Keep width and adjust height
|
if(root.sourceSize.width === 0 || root.sourceSize.height === 0)
|
||||||
const eW = cropEditor.cropRect.width
|
return
|
||||||
const w = (eW <= 0) ? cropEditor.sourceSize.width : eW
|
cropEditor.setCropRect(cropEditor.fillContentInWindow(root.sourceSize, Qt.size(referenceWindowWidth, referenceWindowWidth / root.aspectRatio)))
|
||||||
const h = w/newAR
|
|
||||||
const c = (eW <= 0)
|
|
||||||
? Qt.point(cropEditor.sourceSize.width/2, cropEditor.sourceSize.height/2)
|
|
||||||
: Qt.point(cropEditor.cropRect.x + w/2, cropEditor.cropRect.y + cropEditor.cropRect.height/2)
|
|
||||||
const nR = Qt.rect(c.x - w/2, c.y-h/2, w, h)
|
|
||||||
cropEditor.setCropRect(nR)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -123,12 +123,6 @@ Item {
|
||||||
e.g. to set the crop window to show and match image's AR use Qt.rect(0, 0, sourceSize.width, sourceSize.height)
|
e.g. to set the crop window to show and match image's AR use Qt.rect(0, 0, sourceSize.width, sourceSize.height)
|
||||||
*/
|
*/
|
||||||
readonly property rect cropRect: d.cropRect
|
readonly property rect cropRect: d.cropRect
|
||||||
/*!
|
|
||||||
\qmlproperty rect StatusImageCrop::cropRect
|
|
||||||
|
|
||||||
The position and zis of the crop rectangle in item's space; without extra spacing
|
|
||||||
*/
|
|
||||||
readonly property alias cropWindow: d.cropWindow
|
|
||||||
/*!
|
/*!
|
||||||
\qmlproperty real StatusImageCrop::aspectRatio
|
\qmlproperty real StatusImageCrop::aspectRatio
|
||||||
*/
|
*/
|
||||||
|
@ -146,7 +140,7 @@ Item {
|
||||||
|
|
||||||
\sa StatusImageCrop::source
|
\sa StatusImageCrop::source
|
||||||
*/
|
*/
|
||||||
readonly property size sourceSize: mainImage.sourceSize
|
readonly property alias sourceSize: mainImage.sourceSize
|
||||||
/*!
|
/*!
|
||||||
\qmlproperty real StatusImageCrop::scrToImgScale
|
\qmlproperty real StatusImageCrop::scrToImgScale
|
||||||
|
|
||||||
|
@ -218,7 +212,7 @@ Item {
|
||||||
|
|
||||||
function getZoomRect(scale /*real*/) {
|
function getZoomRect(scale /*real*/) {
|
||||||
const oldCenter = root.rectCenter(root.cropRect)
|
const oldCenter = root.rectCenter(root.cropRect)
|
||||||
const inflatedRect = root.inflateRectBy(root.minimumCropRect(), 1/scale)
|
const inflatedRect = root.inflateRectBy(d.minimumCropRect(), 1/scale)
|
||||||
return root.recenterRect(inflatedRect, oldCenter);
|
return root.recenterRect(inflatedRect, oldCenter);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -248,44 +242,34 @@ Item {
|
||||||
return Qt.rect(newCenter.x - target.width/2 , newCenter.y - target.height/2, target.width, target.height)
|
return Qt.rect(newCenter.x - target.width/2 , newCenter.y - target.height/2, target.width, target.height)
|
||||||
}
|
}
|
||||||
|
|
||||||
//> cropRect for minimum zoom: 1.0
|
function fillContentInWindow(contentSize /*size*/, windowSize /*size*/) {
|
||||||
function minimumCropRect() {
|
const contentAR = contentSize.width/contentSize.height
|
||||||
const sourceAR = root.sourceSize.width/root.sourceSize.height
|
const windowAR = windowSize.width/windowSize.height
|
||||||
const widthBound = sourceAR > root.aspectRatio
|
const heightBound = contentAR > windowAR
|
||||||
const minCropSize = widthBound ? Qt.size(root.sourceSize.width, root.sourceSize.width/root.aspectRatio)
|
if(heightBound) {
|
||||||
: Qt.size(root.sourceSize.height * root.aspectRatio, root.sourceSize.height)
|
const wWidth = contentSize.height * windowAR
|
||||||
let res = Qt.rect(widthBound ? 0 : -(root.sourceSize.width - minCropSize.width)/2, // x
|
const horizontalBorder = (contentSize.width - wWidth)/2
|
||||||
widthBound ? -(root.sourceSize.height - minCropSize.height)/2 : 0, // y
|
return Qt.rect(horizontalBorder, 0, wWidth, contentSize.height)
|
||||||
minCropSize.width, minCropSize.height)
|
}
|
||||||
return res
|
else {
|
||||||
|
const wHeight = contentSize.width / windowAR
|
||||||
|
const verticalBorder = (contentSize.height - wHeight)/2
|
||||||
|
return Qt.rect(0, verticalBorder, contentSize.width, wHeight)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
QtObject {
|
QtObject {
|
||||||
id: d
|
id: d
|
||||||
|
|
||||||
property rect cropRect: fillContentInSquaredWindow(root.sourceSize)
|
property rect cropRect
|
||||||
onCropRectChanged: windowRect.requestPaint()
|
onCropRectChanged: windowRect.requestPaint()
|
||||||
|
|
||||||
readonly property real zoomToFill: {
|
readonly property real zoomToFill: {
|
||||||
const rectangle = fillContentInSquaredWindow(root.sourceSize)
|
const rectangle = root.fillContentInWindow(root.sourceSize, d.cropWindowSize)
|
||||||
return d.currentZoom(root.sourceSize, Qt.size(rectangle.width, rectangle.height))
|
return d.currentZoom(root.sourceSize, Qt.size(rectangle.width, rectangle.height))
|
||||||
}
|
}
|
||||||
|
|
||||||
property rect cropWindow
|
property size cropWindowSize: Qt.size(d.cropRect.width, d.cropRect.height)
|
||||||
// Probably called from render thread, run async
|
|
||||||
signal updateCropWindow(rect newRect)
|
|
||||||
onUpdateCropWindow: cropWindow = newRect
|
|
||||||
|
|
||||||
function fillContentInSquaredWindow(c /*size*/) {
|
|
||||||
if(c.width > c.height) {
|
|
||||||
const border = (c.width - c.height)/2
|
|
||||||
return Qt.rect(border, 0, c.height, c.height)
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
const border = (c.height - c.width)/2
|
|
||||||
return Qt.rect(0, border, c.width, c.width)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//> 1.0 is the content represented by w fully inscribed in c
|
//> 1.0 is the content represented by w fully inscribed in c
|
||||||
function currentZoom(c /*size*/, w /*size*/) {
|
function currentZoom(c /*size*/, w /*size*/) {
|
||||||
|
@ -293,10 +277,26 @@ Item {
|
||||||
const hScale = c.height/w.height
|
const hScale = c.height/w.height
|
||||||
return Math.max(wScale, hScale)
|
return Math.max(wScale, hScale)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//> cropRect for minimum zoom: 1.0
|
||||||
|
function minimumCropRect() {
|
||||||
|
const sourceAR = root.sourceSize.width/root.sourceSize.height
|
||||||
|
const widthBound = sourceAR > root.aspectRatio
|
||||||
|
const minCropSize = widthBound ? Qt.size(root.sourceSize.width, root.sourceSize.width/root.aspectRatio)
|
||||||
|
: Qt.size(root.sourceSize.height * root.aspectRatio, root.sourceSize.height)
|
||||||
|
let res = Qt.rect(widthBound ? 0 : -(root.sourceSize.width - minCropSize.width)/2, // x
|
||||||
|
widthBound ? -(root.sourceSize.height - minCropSize.height)/2 : 0, // y
|
||||||
|
minCropSize.width, minCropSize.height)
|
||||||
|
return res
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
onWindowStyleChanged: windowRect.requestPaint()
|
onWindowStyleChanged: windowRect.requestPaint()
|
||||||
onSourceSizeChanged: d.cropRect = d.fillContentInSquaredWindow(sourceSize)
|
onRadiusChanged: windowRect.requestPaint()
|
||||||
|
onSourceSizeChanged: {
|
||||||
|
if(d.cropWindowSize.width > 0 && d.cropWindowSize.height > 0)
|
||||||
|
d.cropRect = root.fillContentInWindow(sourceSize, d.cropWindowSize)
|
||||||
|
}
|
||||||
|
|
||||||
Canvas {
|
Canvas {
|
||||||
id: windowRect
|
id: windowRect
|
||||||
|
@ -330,7 +330,6 @@ Item {
|
||||||
ctx.roundedRect(cW.x, cW.y, cW.width, cW.height, root.radius, root.radius)
|
ctx.roundedRect(cW.x, cW.y, cW.width, cW.height, root.radius, root.radius)
|
||||||
ctx.fill()
|
ctx.fill()
|
||||||
ctx.restore()
|
ctx.restore()
|
||||||
d.updateCropWindow(cW)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue