Katoch
Katoch

Reputation: 2777

QML how to clip image & extract images from single image

I am having a image which contains numbers in following order :--
0 1 2 3 4 5 6 7 8 9 ... i have to show meter reading .. so now how to create sub image of individual numbers from this image so that i can display each number separately .. means to say i want to extract images of number from this image so that i can display them separately on Meter reading .. please suggest.

Full image size is 108x16 .

I tried using column then using the repeater i replicated the image, but how to change x,y of image inside the repeater so that image inside the repeater is clipped .. so that i extract the numbers from image.. ?

I created column's of the images... using repeater.. but not able to clip the real image.. so that X,Y coordinate changes... and each column contains Digit from the image.

Window {
    visible: true
    width: 400
    height: 300
    color: "grey"

    Item {
        id: container
        anchors.centerIn: parent
        width: 12
        height: 16
        clip: true
        property int position: 0
        Column {
            id: image
            y: -container.position * 16
            Repeater {
                model: 10
                delegate: Rectangle {
                    width: 12
                    height: 16
                    Image {
                        anchors.fill: parent
                        source: "files/REE Demo images/odo_font_orange.png"
                    }
                }
            }
        }
    }

    Timer {
        interval: 1000
        repeat: true
        running: true
        onTriggered: {
            if(container.position == 9)
                container.position = 0;
            else
                container.position ++
        }
    }

Upvotes: 0

Views: 1491

Answers (2)

Soheil Armin
Soheil Armin

Reputation: 2795

You may want to use Sprite and SpriteSequence. Obviously, you have to set running to true so that you can manually set your desired frame(number) by using jumpTo method.

As your image is not 120 pixels wide, it means that your sprites are not the same size. But I recommend you to choose 12 pixels width frames within your original image. SpriteSequence will resize your sprite to its own size if it has a different size. It means that you have to manually set frameX of each Sprite object to get a good visual appearance.

 SpriteSequence {
        id: digit
        width: 12
        height: 16
        interpolate: false
        goalSprite: ""
        running: true
        property var sourceImage: 'files/REE Demo images/odo_font_orange.png'
        Sprite{
            name: "1"
            source: digit.sourceImage
            frameCount: 1
            frameWidth: 12
            frameHeight: 16
            frameX: 0
            frameY: 0
        }
        Sprite{
            name: "2"
            source: digit.sourceImage
            frameCount: 1
            frameWidth: 12
            frameHeight: 16
            frameX: 12
            frameY: 0
        }
        //other digits with their topleft and width/height 
        //in original image should be repeated with their own name

       function setNumber(n){
          digit.jumpTo(n);
       }

}

Upvotes: 1

folibis
folibis

Reputation: 12864

You should place your image inside a container with clip:true and play with x/y of the content item, for example:

import QtQuick 2.12
import QtQuick.Window 2.12

Window {
    visible: true
    width: 400
    height: 300

    Item {
        id: container
        anchors.centerIn: parent
        width: 30
        height: 30
        clip: true
        property int position: 0
        Column {
            id: image
            y: -container.position * 30
            Repeater {
                model: 10
                delegate: Rectangle {
                    width: 30
                    height: 30
                    Text {
                        anchors.fill: parent
                        verticalAlignment: Text.AlignVCenter
                        horizontalAlignment: Text.AlignHCenter
                        text: index
                        font.pixelSize: 20
                        color: "orange"
                    }
                }
            }
        }
    }

    Timer {
        interval: 1000
        repeat: true
        running: true
        onTriggered: {
            if(container.position == 9)
                container.position = 0;
            else
                container.position ++
        }
    }
}

here I replace Image with Column item to just illustrate the idea. You maybe want to add some move animation etc.

Updated: taking you image into account:

import QtQuick 2.12
import QtQuick.Window 2.12

Window {
    visible: true
    width: 400
    height: 300

    Item {
        id: container
        anchors.centerIn: parent
        width: 12
        height: 16
        clip: true
        property int position: 1
        Image {
            id: image
            x: -container.position * 12
            source: "https://i.sstatic.net/jnbEZ.png"
        }
    }
    Timer {
        interval: 1000
        repeat: true
        running: true
        onTriggered: {
            if(container.position == 9)
                container.position = 0;
            else
                container.position ++
        }
    }

}

but since your images are not aligned right the result is a bit rough. You need 10 cells with the same size each one.

Upvotes: 0

Related Questions