mercredi 19 avril 2017

Region of Interest (ROI) with Red

Region of Interest (ROI) with Red


In many cases you don't need to process all image when processing complex images. You can define regions of interest (ROI). A ROI is a portion of an image that you want to filter or perform some other operation on. Working on ROI drastically  reduces time of image processing.
Once again, Red Language is very performant and the definition of ROI is particularly simple with draw and clip operator.
In the following example, we just want do simple processing: move a face on an image and get back the selected area to copy to another (smaller) ROI image. However, this example is interesting since it introduces two major VID characteristics of Red language.

Loose

First one is loose which enables dragging of a face using the left mouse button. 

style rect: base glass 202x202 loose draw []

Here, we juste define a 202x202 pixels transparent face ( a base face) that can be moved over the main image and we create an instance of the object with p1 variable.

at winBorder p1: rect

In order to make the GUI clearer we also associate to this face a draw facet which only draws a green 200x200 box on the moving face. This will be the ROI that can be hidden or not.

drawRect: compose [line-width 2 pen green box 0x0 200x200]

Reactive programming

Since version 0.6.0, Red has introduced a very interesting support for reactive programming to help reduce the size and complexity of Red programs. Red’s reactive model relies on data flow and object events to construct a directed graph and propagate changes in objects. You'll find more details and samples in Red documentation.

In this code we define an image container which will automatically react  to the displacement of the p1 rect object.

canvas: base 512x512 img react [....]

Code associated to react method just verifies that the displacement of the ROI remains inside the image and then updates the draw block associated to the roi face which contains the clip operator.  Clip defines a clipping rectangular region defined with two points (start and end) or an arbitrarily shaped region defined by a block of Shape sub-dialect commands. This allows to dynamically copy the selected area to roi face according to the displacement of the mouse. 

Code example

Red [
    Title:   "Clip tests "
    Author:  "Francois Jouen"
    File:    %clipImage.red
    Needs:   'View
]

margins: 10x10
winBorder: 10x50
;use the image you want
img: load %lena.jpg
;image container limits
rLimit: 0x0
lLimit: 512x512
; for the ROI size
rstart: 0x0
rend: rstart + 200
; for the ROI displacement
poffset: negate rstart

; Draw operators we need 
drawBlk: compose [translate (poffset) clip (rstart) (rend) image img]
drawRect: compose [line-width 2 pen green box 0x0 200x200]

; ***************** Test Program ****************
view [
        title "Clip Tests"
        style rect: base glass 202x202 loose draw []
        origin margins space margins
        button 80 "Show Roi" [p1/draw: drawRect roi/draw: drawBlk]
        button 80 "Hide Roi" [p1/draw: [] roi/draw: []]
        button 80 "Quit"     [Quit]
        return 
        canvas: base 512x512 img react [
            if (p1/offset/x > lLimit/x) AND (p1/offset/y > lLimit/y)[
                if (p1/offset/x  < rLimit/x) AND (p1/offset/y  < rLimit/y)[
                    rstart: p1/offset - winBorder
                    rend: rstart + 200
                    poffset: negate rstart
                    sb/text: form rstart        
                    drawBlk/2: poffset 
                    drawBlk/4: rstart
                    drawBlk/5: rend
                ]
            ]
        ]
        roi: base 200x200 white draw []
        return
        sb: field 512
        at winBorder p1: rect
        do [lLimit: canvas/offset rLimit: canvas/size + canvas/offset - p1/size ]
]


and the result






Aucun commentaire:

Enregistrer un commentaire