Mailing List Archive: 49091 messages
  • Home
  • Script library
  • AltME Archive
  • Mailing list
  • Articles Index
  • Site search
 

drawing images on text face after displayed = "highlighting text"

 [1/14] from: fergus4:bellatlantic at: 1-Oct-2008 2:45


Is there a way to append an image object (a box for example) to a face that has already been displayed. I'm looking to get simple highlight functionality in an app in which a string is scanned for in a series of text faces. I've been able to highlight the search word in each face but if I click in any of the text faces the face looses the highlight effect sort of like loosing focus on normal highlighting. I would like the highlight to remain until no longer needed What I got working: rebol [] pad: 20x30 window: layout [ bx: box red 0x0 panel: panel [ text 400 "Here is a simple example how to use DRAW dialect for into alpha channel of the image. I think with the function make-alpha (bellow in the example) you can draw almost any kind of transparent shape though it is not the fastest method....IMO the possibility to use DRAW pens for alpha channel should be done at Rebol's native level" t: text 400 "Here is a simple example how to use DRAW dialect for e-alpha (bellow in the example) you can draw almost any kind of transparent shape though it is not the fastest method....IMO the possiinto alpha channel of the image. I think with the function make-alpha (bellow in the example) you can draw almost any kind of transparent shape though it is not the fastest method....IMO the possibility to use DRAW pens for alpha channel should be done at Rebol's native level" text 500 "can draw almost any kind of transparent shape though it is not the fastest method....IMO the possibility to use DRAW pens for alpha channel should be done at Rebol's naHere is a simple example how to use DRAW dialect for into alpha channel of the image. I think with the function make-alpha (bellow in the example) you can draw almost any kind of transparent shape though it is not the fastest method....IMO the possibility to use DRAW pens for alpha channel should be done at Rebol's native level"] button "Highlight" [foreach face panel/pane [if face/style = 'text [ system/view/focal-face: face system/view/highlight-start: find face/text "into alpha channel of the image" system/view/highlight-end: find/tail face/text "into alpha channel of the image" show face ]]] button "Paint" [foreach face panel/pane [if face/style = 'text [ keyword: "transparent" xy: caret-to-offset face find face/text keyword bx/offset: face/offset + pad + xy bx/size: as-pair (5.9 * length? keyword) 15 show face ]]] ] view window -Alan Macleod

 [2/14] from: anton::wilddsl::net::au at: 1-Oct-2008 18:17


Hi Alan, The problem is, VID only provides one highlight-start and highlight-end, and one caret, shared amongst all faces. ('Highlights' are separate from the concept of 'selection', but VID calls the current text selection a 'highlight'). Therefore, you need to patch VID and the focus system so that it does highlighting *optionally*, not automatically, and write a custom text style which chooses not to exercise that option. :) I expect each of your custom text faces should allow multiple highlights, so create a 'highlights' facet block, and store each pair of highlight-start/highlight-end in there. To implement it, you need to maintain several 'highlight faces', one for each highlight in the highlights facet. (These highlight faces are like your red box.) The highlight faces go into the PANE block of your custom text style face. See example code at bottom. Your "Paint" button uses an interesting technique to draw the same box multiple times at multiple locations. I don't recommend this technique, because you never know when the next redraw will clear it. You should better implement multiple boxes in your custom text style's pane block. There are more problems to solve, like accurately finding the position of some text in all cases (ie. doing a better job than CARET-TO-OFFSET does) and maybe opting out of the automatic system caret placement on focus. I've solved some of these problems already. I have several modular VID patches, which allows customised AREA and FIELD style replacements to draw their own highlight and caret. It should be relatively easy (for me, anyway!) to add multiple highlighting to these styles. http://anton.wildit.net.au/rebol/patch/caret-to-offset-patch.r http://anton.wildit.net.au/rebol/patch/focus-system-patch.r http://anton.wildit.net.au/rebol/patch/ctx-text-caret-highlight-patch.r do http://anton.wildit.net.au/rebol/gui/demo-area.r do http://anton.wildit.net.au/rebol/gui/demo-field.r do http://anton.wildit.net.au/rebol/gui/demo-edit-panel.r do http://anton.wildit.net.au/rebol/gui/demo-edit-panels.r ... so the answer to your question is: "yes". Regards, Anton. Alan Macleod wrote:
> Is there a way to append an image object (a box for example) to a face that > has already been displayed. I'm looking to get simple highlight
<<quoted lines omitted: 5>>
> I would like the highlight to remain until no longer needed > -Alan Macleod
rebol [] stylize/master [ my-text: text with [ highlights: [] ; custom facet init: [ pane: copy [] ] add-highlight: func [start end][ append append highlights start end refresh-highlights show self ] highlight-box: make-face/spec 'box [ size: 50x18 effect: [merge multiply yellow] ; translucent ] refresh-highlights: has [n][ n: 0 foreach [start end] highlights [ n: n + 1 if n > length? pane [ append pane make highlight-box [] ] pane/:n/offset: 30x22 * (n - 1) ; (use CARET-TO-OFFSET here etc.) ] clear skip pane n ; remove old highlights ] feel: make feel [ redraw: func [face action position][ ;face/refresh-highlights ] ] ] ] view layout [ my-text: my-text 400x300 {Hello how are you going^/Just wonderful thankyou.} btn "Add highlight" [my-text/add-highlight 10 20] ]

 [3/14] from: henrikmk:gma:il at: 1-Oct-2008 12:30


On Wed, Oct 1, 2008 at 10:17 AM, Anton Rolls <anton-wilddsl.net.au> wrote: Anton, how do you solve marking up multiple lines? I'm building something similar with boxes, but have yet to find out how to figure out where text is broken into multiple lines for display, so I can detect start of line and end of line. -- Regards, Henrik Mikael Kristensen

 [4/14] from: fergus4:bellatlantic at: 1-Oct-2008 8:14


Henrik, I was going to map the start and endpoints using caret_to_offset on find text and find/tail text. And knowing the text field width paint multiple boxes to fit the shape. Not pretty but I think good enough for what I want. Or is the function that highlight_start and highlight-end uses available or is it hidden too deep (not mezzazine) Anton, or Henrik, Is it possible to use the draw dialect to "paint" these highlights? The way a simple paint program pains into an area?

 [5/14] from: henrikmk:g:mail at: 1-Oct-2008 14:26


On Wed, Oct 1, 2008 at 2:14 PM, Alan Macleod <fergus4-bellatlantic.net> wrote:
> Henrik, > > I was going to map the start and endpoints using caret_to_offset on find > text and find/tail text. And knowing the text field width paint multiple > boxes to fit the shape. Not pretty but I think good enough for what I want.
I use almost the same method.
> Or is the function that highlight_start and highlight-end uses available or > is it hidden too deep (not mezzazine) > > Anton, or Henrik, > > Is it possible to use the draw dialect to "paint" these highlights? The way > a simple paint program pains into an area?
You can probably do that with the SHAPE command in DRAW. To ensure accurate painting, I would use SIZE-TEXT as it can accurately detemine the width and height of the area you need to paint per row. My implementation uses plain boxes and then SIZE-TEXT to calculate the size of one highlight box. It works for all font sizes I've tested so far. My only problem right now is detecting the start and end point of multi-line text as I want a more accurate depiction of the selected text. To detect multiple line highlights: If the Y position of caret-to-offset is not identical for start and end position, then you are using multiple lines. -- Regards, Henrik Mikael Kristensen

 [6/14] from: fergus4:bellatlantic at: 1-Oct-2008 8:41


Henrik, How do you use size-text to find the size for a row or highlighted section? I can only find the size of the entire text face.

 [7/14] from: henrikmk:gma:il at: 1-Oct-2008 15:02


On Wed, Oct 1, 2008 at 2:41 PM, Alan Macleod <fergus4-bellatlantic.net> wrote:
> Henrik, > > How do you use size-text to find the size for a row or highlighted section? > I can only find the size of the entire text face.
You shouldn't use size-text on the original face. Something like: size-text make t [size: 2000x50 text: highlighted-text] Explanation: You make a copy of the original text face for measurement purposes, and then let it only contain the highlighted text. (I guess View needs to render the text internally to return the size of it.) You then need the exact same text attributes (font and para) for it to measure the size correctly. You also need a rather big size in order for the text in the new face to flow correctly to avoid unintended linebreaks as we want the text to match the original. -- Regards, Henrik Mikael Kristensen

 [8/14] from: fergus4:bellatlantic at: 1-Oct-2008 11:47


I tried some similar things to get the highlighted text in a temp face but could not get it to work... Thanks again.. -Alan Macleod

 [9/14] from: henrikmk:g:mail at: 1-Oct-2008 17:54


On Wed, Oct 1, 2008 at 5:47 PM, Alan Macleod <fergus4-bellatlantic.net> wrote:
> I tried some similar things to get the highlighted text in a temp face but > could not get it to work...
My code so far (stolen from your original code submission): rebol [] pad: 20x30 set-highlight: func [ "Sets the highlight boxes in the given text face" face [object!] strings [block!] "Block of one or multiple string pairs describing the highlight start and end points" /no-show /local access ] [ if all [ access: get in face 'access in access 'set-face* ] [ access/set-highlight* face strings ] if not no-show [show face] face ] get-highlight: func [face [object!]] [ ; unimplemented ] window: layout [ style hl-text text with [ pane: make block! [] hl: none ; a single highlight face hl-face: make face [ color: 255.0.0 edge: none para: make para [origin: 0 margin: 0] effect: [gradient 0x1 255.128.0 255.0.0] ; just to make it look a little cooler ] ; the pane which stores all highlight faces hl-pane: make face [color: none pane: make block! []] ; the position in pane for the highlight pane as used by set-highlight* hl-pane-block: none make-hl-face: func [face str pos sz] [ append face/hl-pane-block make face/hl-face [offset: pos - 2 size: sz text: str] ] split-lines: make block! [] access: make access [ set-highlight*: func [face [object!] strings [block!] /local pos end-pos split-lines str sz done] [ face/hl: strings clear face/hl-pane-block ; create highlight boxes foreach [start end] face/hl [ ; paint a box for each highlight by finding the position on where to paint it using caret-to-offset to get the position. ; is the highlight split over multiple lines? ; the end-pos can't be used here, we need to do the split thing before calculating positions str: copy/part start end sz: size-text make face/hl-face [size: 2000x50 text: str] pos: caret-to-offset face start end-pos: caret-to-offset face end either pos/y <> end-pos/y [ ; multiple lines ; ---------- The code in this block is not working correctly ------------ ; paint one box per line for multiple line highlights ; that means that each line must paint right from start or beginning of line to either the end of highlight or end of line ; generate split-lines list of all indexes required for painting the lines clear split-lines line-pos: start ; we should be able to use the line list, but something is not right here. ; the line list is not set, but it would be manipulated by something, so we should figure out what that is until [ ; calculate start of line or none sol: ; calculate end of line or none eol: case [ ; start of line to end of line all [sol eol] [repend split-lines [sol eol] false] ; start of text to end of line all [none? sol eol] [repend split-lines [start eol] false] ; start of line to end of text all [sol none? eol] [repend split-lines [sol end] true] ] ] foreach [start end] split-lines [ str: copy/part start end sz: size-text make face/hl-face [size: 2000x50 text: str] pos: caret-to-offset face start make-hl-face face str pos sz ] ][ make-hl-face face str pos probe sz ] ] show face ] ] append init [ ; prepare the highlight face to have the right font hl-face/font: make font [offset: 0x0 color: white] unless all [block? pane none? pane] [pane: make block! []] ; position the hl-pane hl-pane/color: none hl-pane/size: size ; perhaps size optimize it later hl-pane/offset: offset append pane hl-pane ; prepare hl-pane-block hl-pane-block: get in last pane 'pane ] ] bx: box red 0x0 panel: panel [ tt: hl-text 500 font-size 12 {Here is a simple example how to use DRAW dialect for into alpha channel of the image. I think with the function make-alpha (bellow in the example) you can draw almost any kind of transparent shape though it is not the fastest method....IMO the possibility to use DRAW pens for alpha channel should be done at Rebol's native level} t: text 400 {Here is a simple example how to use DRAW dialect for e-alpha (bellow in the example) you can draw almost any kind of transparent shape though it is not the fastest method....IMO the possiinto alpha channel of the image. I think with the function make-alpha (bellow in the example) you can draw almost any kind of transparent shape though it is not the fastest method....IMO the possibility to use DRAW pens for alpha channel should be done at Rebol's native level} text 500 {can draw almost any kind of transparent shape though it is not the fastest method....IMO the possibility to use DRAW pens for alpha channel should be done at Rebol's naHere is a simple example how to use DRAW dialect for into alpha channel of the image. I think with the function make-alpha (bellow in the example) you can draw almost any kind of transparent shape though it is not the fastest method....IMO the possibility to use DRAW pens for alpha channel should be done at Rebol's native level}] button "Highlight" [foreach face panel/pane [if face/style = 'text [ system/view/focal-face: face system/view/highlight-start: find face/text "into alpha channel of the image" system/view/highlight-end: find/tail face/text "into alpha channel of the image" show face ]]] button "Paint" [foreach face panel/pane [if face/style = 'text [ keyword: "transparent" xy: caret-to-offset face find face/text keyword bx/offset: face/offset + pad + xy bx/size: as-pair (5.9 * length? keyword) 15 show face ]]] button "Box highlight" [ set-highlight tt reduce [ ; one start and end highlight component per line find tt/text "IMO" skip find tt/text "IMO" 10 find tt/text "native" skip find tt/text "native" 4 ] ] ] view window -- Regards, Henrik Mikael Kristensen

 [10/14] from: fergus4:bellatlantic at: 1-Oct-2008 12:23


Looks nice. I can't get it to do multiple faces though. I'll work on it. Thanks. -Alan

 [11/14] from: anton:wilddsl:au at: 2-Oct-2008 2:36


Hi Henrik, In my edit-panel style, I stored the text data as lines (a block of strings), not a single string, so I didn't have this problem. face/line-list used to be a block of offsets to each line, but, while the facet still exists, it is set to none by the View system, probably natively. So it's a mystery to me. Regards, Anton. Henrik Mikael Kristensen wrote:

 [12/14] from: anton:wilddsl:au at: 2-Oct-2008 2:37


Hi Alan, Alan Macleod wrote:
> Henrik, > > I was going to map the start and endpoints using caret_to_offset on find > text and find/tail text. And knowing the text field width paint multiple > boxes to fit the shape. Not pretty but I think good enough for what I want. > > Or is the function that highlight_start and highlight-end uses available or > is it hidden too deep (not mezzazine)
Hidden too deep I think. But can be worked around, I think.
> Anton, or Henrik, > > Is it possible to use the draw dialect to "paint" these highlights? The way > a simple paint program pains into an area?
Yes, it is.
> How do you use size-text to find the size for a row or highlighted
section?
> I can only find the size of the entire text face.
You can't do it in place. I've obtained this by use of workarounds which you can see working pretty well in demo-caret-to-offset-patch.r and test-caret-to-offset-patch.r See my lengthy investigations in these files. http://anton.wildit.net.au/rebol/doc/field-text-draw.r http://anton.wildit.net.au/rebol/view/draw/smooth-font-scaling.r http://anton.wildit.net.au/rebol/patch/demo-caret-to-offset-patch.r http://anton.wildit.net.au/rebol/patch/test-caret-to-offset-patch.r Especially those last two files. Regards, Anton.

 [13/14] from: henrikmk:gmai:l at: 1-Oct-2008 19:26


On Wed, Oct 1, 2008 at 6:36 PM, Anton Rolls <anton-wilddsl.net.au> wrote:
> Hi Henrik, > In my edit-panel style, I stored the text data as lines
<<quoted lines omitted: 3>>
> but, while the facet still exists, it is set to none by > the View system, probably natively. So it's a mystery to me.
Thanks for the reply, Anton. I was wondering about line-list myself and how useless it is for this case. Now I don't need to waste any more hours on that. :-) -- Regards, Henrik Mikael Kristensen

 [14/14] from: carl:cybercraft at: 1-Oct-2008 21:35


A quick response... One simple way to have an image appear after the layout has been shown would be to include it in the original layout and change its offset to -100x-100 (or whatever's required to stop it being visible) before the layout is shown. Then when you want to show the image just change its offset again - and the image too, if required. Hope that's useful, and within the ballpark of what you're wanting to do... -- Carl Read. On Wednesday, 1-October-2008 at 2:45:35 Alan Macleod wrote,

Notes
  • Quoted lines have been omitted from some messages.
    View the message alone to see the lines that have been omitted