Use of colors in multiline listbox

  1. 8 weeks ago

    Rob V

    Feb 9 the Netherlands
    Edited 8 weeks ago

    I am using multiline in my listbox and I am using several colors, depending of the type of event I am receiving.

    When I do not touch the listbox everything goes well and you see multiline multicolored events. However, when I scroll the mouse or use keydown then all colors disappear and all the text in all rows are getting the last color which was used.

    Is there a way to keep the colors per event. The color is chosen by the eventname in the celltag, so per row the eventname is always available.

    I use an earlier described solution on this forum for multiline rows in my listbox

    Note: I do the same with a single line listbox and there I do not have this problem, every row keeps its color. I think this is multiline related.

    I found my problem, I was changing color in the celltag, but because I only use one cell I should use rowtag to hold the color.

    I changed celltag to rowtag in my code and the multiline text in my listbox does not change of color anymore, but keeps always the color I assigned to it.

    Thank you very much for your responses.

  2. Emile S

    Feb 9 Europe (France, Strasbourg)

    Where are-you changing the colors ?

  3. Jeff T

    Feb 9 Pre-Release Testers Midlands of England, Europe

    The color is chosen by the eventname in the celltag, so per row the eventname is always available.

    Not really sure what you mean here, but let us assume that
    EVENTNAME is text, that there are maybe 3 values, and each has a unique color

    Ignoring the effect of changing color when a row is SELECTED, the
    CellBackgroundPaint event just needs a select case

    dim thecol as color
    if row < me.listcount then
    Select case me.rowtag(row)
    case "EVENT1"
    thecol = &cff0000
    
    case "EVENT2"
    thecol = &c00FF00
    
    case "EVENT3"
    thecol = &c0000FF
    
    case else
    thecol = &cFFFFFF
    end select
    g.forecolor = thecol
    g.fillrect 0,0,g.width, g.height
    
    end if

    Multiline shouldnt make any difference

  4. Rob V

    Feb 9 the Netherlands

    Thank you for your answer, Jeff, but also with your solution (for the background color, I use only colored text on a black background) does show the same. When scrolling the listbox the background will be black. Just as the text.

    @Emile, I do this in the CellTextPaint of the listbox

  5. Beatrix W

    Feb 9 Pre-Release Testers, Third Party Store Europe (Germany)

    Show us your code. An example would be best. I use custom colours, too, in listboxes and have never seen such an effect.

  6. Rob V

    Feb 9 the Netherlands
    Edited 8 weeks ago

    Ok, this is the code I have in the cellTextPaint:

      Dim arr() As String = Split(Me.Cell(row, column), EndOfLine) 
      Dim CellTagCapture as string
      Dim bcolor as Color
      
      
      If Row > -1 And Row < Me.ListCount Then
        CellTagCapture = me.CellTag(row,0)
        CellTagCapture = me.RowTag(row)
        CellTagCapture = me.ColumnTag(column)
        if me.CellTag(row,0)="me" then
          me.CellAlignment(Me.LastIndex,0) = me.AlignRight
          bColor = dcBlue
        elseif me.CellTag(row,0)="human" then
          me.CellAlignment(me.LastIndex,0) = me.AlignRight
          bColor = LBlue
        end if
        
        
        me.CellTag(row,column)=me.cell(row,column)
        For i As Integer = 0 To ubound(arr)
          g.foreColor=bColor
          g.DrawString(arr(i), x, y - g.TextHeight + i * g.TextHeight)
        Next
        Return True
      end if
      

    The return true was a trial to keep the colors

  7. Rob V

    Feb 9 the Netherlands

    @Beatrix W , I have this only with multiline listboxes, not with singleline listboxes

  8. Jeff T

    Feb 9 Pre-Release Testers Midlands of England, Europe

    In this code you are testing for "me" and for "human"
    if the celltag is not one of those, bColor will not be set, and will remain as black or whatever color is was set to last.

    if me.CellTag(row,0)="me" then
          me.CellAlignment(Me.LastIndex,0) = me.AlignRight
          bColor = dcBlue
        elseif me.CellTag(row,0)="human" then
          me.CellAlignment(me.LastIndex,0) = me.AlignRight
          bColor = LBlue
        end if


    try this instead:

    select case me.CellTag(row,0)
    
    case "me"
          me.CellAlignment(Me.LastIndex,0) = me.AlignRight
          bColor = dcBlue
    case "human"
          me.CellAlignment(me.LastIndex,0) = me.AlignRight
          bColor = LBlue
    case else
          me.CellAlignment(me.LastIndex,0) = me.AlignRight
          bColor = &cff0000  //red
        end select

    And then, you actually change the contents of the celltag inside the loop.. so next time it refreshes it may not even have the same tag second time around?

       
        me.CellTag(row,column)=me.cell(row,column)
  9. Greg O

    Feb 9 Xojo Inc scout.galaxy.barn

    I suggest not changing cellAlignment in the paint event. It will cause a refresh under certain circumstances. That’s something you should do when the data is added to the listbox.

  10. Jeff T

    Feb 9 Pre-Release Testers Midlands of England, Europe

    Also, the alignment is being set for the LAST ADDED row, regardless of which row you are painting.

    me.CellAlignment(Me.LastIndex,0)
    I would have expected it to be me.CellAlignment(row,0)

    You can fudge this by drawing the text yourself (thats why it is CellTextPaint), but surely it is best to set it once at the time you add the row.

  11. Emile S

    Feb 9 Europe (France, Strasbourg)

    Have-you read ListBox.CellBackgroundPaint ?

  12. Rob V

    Feb 9 the Netherlands
    Edited 8 weeks ago

    The alignment goes well now, thanks Greg. No clue why I put it there, in other apps it was also outside the celltextpaint.

    Yes, Emile, but it is not about the background color, that one is always black to make it readable. It is all about the CellTextPaint color and I am afraid it is this part in the code which does give the problem:

    In CellTextPaint:

    Dim arr() As String = Split(Me.Cell(row, column), EndOfLine) 
    
        For i As Integer = 0 To ubound(arr)
          g.foreColor=bColor
          g.DrawString(arr(i), x, y - g.TextHeight + i * g.TextHeight)
        Next

    What was done, we split up long text into a max length per line and after every maxlenth one put an EndOfLine. The above code will split the line on the EndOfLine markers and draw it on the next line.

    For instance here is the code which is working fine for single line events:
    in CellTextPaint:

      If Row > -1 And Row < Me.ListCount Then
        if me.CellTag(row,2)="eq" then
          If val(Me.CellTag(row,1)) < 3 then
            DisColor1=white
          elseif  val(Me.CellTag(row,1)) >= 3 and  val(Me.CellTag(row,1)) < 4 then
            DisColor1 = LYellow
          elseif  val(Me.CellTag(row,1)) >= 4 and  val(Me.CellTag(row,1))<5 then
            DisColor1 = dGreen
          elseif val(Me.CellTag(row,1))  >= 5 and  val(Me.CellTag(row,1))<6 then
            DisColor1 = Yellow
          elseif  val(Me.CellTag(row,1))  >= 6 and  val(Me.CellTag(row,1)) <7 then
            DisColor1 = Orange
          elseif  val(Me.CellTag(row,1)) >= 7 and  val(Me.CellTag(row,1))<8 then
            DisColor1 = Red
          elseif  val(Me.CellTag(row,1)) >= 8 then
            DisColor1 = Purple
          end if
        elseif me.CellTag(row,2)="ts" or me.CellTag(row,2)="hu" or me.CellTag(row,2)="fl" then
          Discolor1=LBlue
        elseif me.CellTag(row,2)="ls" then
          Discolor1 = LRed
        elseif me.CellTag(row,2)="fi" or me.CellTag(row,2)="li" then
          DisColor1=dRed
        elseif me.CellTag(row,2)="vu" then
          DisColor1=LOrange
        Else
          Discolor1 = LGrey
        End If
        g.foreColor=Discolor1
      end if

    Moving up/down with the mouse over the text, using the mouse wheel to roll up/down the list does not affect the colors, each event does keep the color I assigned to it (in the if statement)

  13. Rob V

    Feb 9 the Netherlands

    @Jeff T : your select statement will only show the last command (human) and response (me) in the listbox. All earlier command/responses will appear in red

  14. Tim P

    Feb 9 Pre-Release Testers, Xojo Pro Rochester, NY

    @Rob V @Jeff T : your select statement will only show the last command (human) and response (me) in the listbox. All earlier command/responses will appear in red

    If you'd like a full working implementation, why not post the project? We can only help with bits of code and make assumptions over the forum. If you were to provide us with a project that operates and shows the error, it would significantly simplify the process of helping you find out what's going wrong.

    From the code bits you've posted, I fear it's more than just one issue.

  15. Jeff T

    Feb 9 Pre-Release Testers Midlands of England, Europe

    @Jeff T : your select statement will only show the last command (human) and response (me) in the listbox. All earlier command/responses will appear in red

    Thats the point. I wanted uncaught values to show up and cause some thinking.

  16. Rob V

    Feb 9 the Netherlands

    @Tim P The only part which gives me the problem is the multiline part which I put down the code above. All other code I put here for the single line, maybe it deserves not a price for clean coding, but I am busy to rewrite it. This single line part works as a champ for 4-5 years. I wrote that short after I stepped over to Xojo. Now I am more experienced with Xojo I am rewriting parts.

  17. Jeff T

    Feb 9 Pre-Release Testers Midlands of England, Europe

    Off topic.. Am I the only one who finds

    if
    elseif
    elseif

    almost impossible to follow?

    val(Me.CellTag(row,1)) >= 3 and val(Me.CellTag(row,1)) < 4 etc.

    Hugely simplified using a Select case

    Select Me.CellTag(row,1)
    case "3"
    
    case "4"
    
    case "5","6"
    end select
    
    select case me.CellTag(row,2)
    case "ts" ,"hu" ,"fl"
     Discolor1=LBlue
    case "ls" 
          Discolor1 = LRed
    case "fi","li"
          DisColor1=dRed
    case "vu"
          DisColor1=LOrange
     case   Else
          Discolor1 = LGrey
    end select
  18. 7 weeks ago

    Rob V

    Feb 14 Answer the Netherlands

    I found my problem, I was changing color in the celltag, but because I only use one cell I should use rowtag to hold the color.

    I changed celltag to rowtag in my code and the multiline text in my listbox does not change of color anymore, but keeps always the color I assigned to it.

    Thank you very much for your responses.

or Sign Up to reply!