I need a help with a component descendent from TListBox

hidrau
hidrau used Ask the Experts™
on
Hello Friends

For my project I am using this component

http://www.tmssoftware.com/site/advsmoothlistbox.asp

The advsmoothlistbox is very interessting and nice for what I need to do.

But I am having some trouble to reach what I want to do. Well, let me explain

so you can understand and help me.

This project is for students

I have a small text and 10 questions. My task is a routine for each question that has 4 options where only one will be chosen, only one is the suitable answer.

On a form I have a scrollbox where I create in run time 10 advsmoothlistbox, each advsmoothlistbox  has a header where is the question and 4 itens where of them is the correct.  The component has this option for header and itens.

The student will choose one item and click on, when it is done that, the component turn on the item selected.

After having all itens of each advsmoothlistbox selected, I want to correct the selection.

If the student selected the correct alternative, the  item must be in blue color to show him that its answer was right.

If the answer is not right, the correct answer must be displayed in blue color and its answer must be in red color.

My difficult is being how to manipulate the color, so I need an example to do that. I think that all the code must be in onItemDraw. But you can tell me if there is the suitable place to do.

Well, a small  example with the component advsmoothlistbox  that you can download it to try is very welcome, so this way I can see how to reach the goal and inplamentate my code.

thanks
Alexandre
Comment
Watch Question

Do more with

Expert Office
EXPERT OFFICE® is a registered trademark of EXPERTS EXCHANGE®
Ferruccio AccalaiSenior developer, analyst and customer assistance

Commented:
Well, here's just my suggestion.

FIrst of all you have to know for any advsmoothlistbox (from now called advlb) wich is the correct answer, so you can store the itemindex of the correct answer into the tag value.

Then , if you want that the user selects just one option without let it change it after,  just set the advlb as enabled = false, so he cannot change his choice.

Finally, after any selection in any advlb, you can do the results check by a loop.

Do not use the ItemDraw event to do this, as it's fired during any advlb redrawing starting from creation. Just run a loop at the end of the selections.

Now a little bit of code

After the selection, to stop any other selection into the advlb
you can link this procedure to any advlb on your form

procedure TForm1.AdvSmoothListBox1ItemSelected(Sender: TObject; itemindex: Integer);
begin
  TAdvSmoothListBox(Sender).Enabled := false;
end;

Open in new window

(remember to re-enable them on a new starting test)

Now the results check.
I've used a simple tbutton, but you can decide to do it when the last advlb is selected

You said that the advlb's are dropped into a scrollbox, so we will do a loop into it, and when an advlb is found we will do a check for its items.

procedure TForm1.Button1Click(Sender: TObject);
var
  i, x: Integer;
begin
  with ScrollBox1 do
  begin
    for x := controlcount - 1 downto 0 do
      if Controls[x] is TAdvSmoothListBox then
      begin
        with TAdvSmoothListBox(ScrollBox1.Controls[x]) do
        begin
          for i := 0 to Items.Count - 1 do
          begin
            if Items[i].selected then
            begin
              if i <> tag then
                Items[i].CaptionFont.Color := clred
              else
                Items[i].CaptionFont.Color := clblue
            end
            else if i = tag then
              Items[i].CaptionFont.Color := clblue;
          end;
        end;
      end;
  end;
end;

Open in new window


There are other string properties that can be stored and changed. If you have dowloaded the whole TMS Smooth Controls you will find very useful the Demo Directory that contains a lot of demo, included one for this ListBox component under C:\Users\Public\Documents\tmssoftware\TMS Smooth Controls Demos\Listbox)

Hope that this my comment could be a good point of start for you

Author

Commented:
Hi Ferruccio68,

I understood perfectly what you gave me.

You give another point of view, I didn't think about item[x].CaptionFont.color

I had thought changing the color of brush of the item. But your way it is totally suitable :)

Just one question, would it be complicated change the brush color of the item?

Thanks
Senior developer, analyst and customer assistance
Commented:
No, it isn't, but you will lost all the nice graphics for the items

An example on how it can be done in the previous code using onItemDraw in addition

procedure TForm1.AdvSmoothListBox1ItemDraw(Sender: TObject; Canvas: TCanvas; itemindex: Integer; itemrect: TRect;
  var defaultdraw: Boolean);
begin
 with TAdvSmoothListBoxItem(Sender) do
  begin
    if (CaptionFont.Color = clred) or (CaptionFont.Color = clblue) then
    begin
      defaultdraw := false;
      Canvas.Brush.Color := CaptionFont.Color;
      Canvas.Font := CaptionFont;
      Canvas.Font.Color := clblack;
      Canvas.FillRect(itemRect);
      Canvas.TextOut(itemRect.Left+6, (itemRect.top+(itemRect.Bottom-itemRect.top - Canvas.TextHeight(caption)) div 2),
        caption);
    end
    else
      defaultdraw := true;
  end;
end;

Open in new window

Microsoft Azure 2017

Azure has a changed a lot since it was originally introduce by adding new services and features. Do you know everything you need to about Azure? This course will teach you about the Azure App Service, monitoring and application insights, DevOps, and Team Services.

Author

Commented:
one more time, thanks very much friend for your help

Author

Commented:
Ferruccio68,

Have you seen this event AdvSmoothListBox1ItemCustomizeFill ?

Maybe this event  can give a better fill with color for correct and incorrect answer, what do you think? If you want, I can open another thread with this complement. well, I think it is fair

Author

Commented:
I got it :)))

procedure TFEditorQuestOP.ListMatrizItemCustomizeFill(Sender: TObject;
  Item: TAdvSmoothListBoxItem; AFill, ADisabledFill,
  ASelectedFill: TGDIPFill);
begin
  with TAdvSmoothListBoxItem(Sender) do begin
    if (CaptionFont.Color = clred) Then Begin
      AFill.Color   := clRed;
      AFill.ColorTo := clWhite;
      AFill.ColorMirror := clWhite;
      AFill.ColorMirrorTo := clRed;
    end;

    if (CaptionFont.Color = clblue) Then Begin
        AFill.Color := clBlue;
        AFill.ColorTo := clWhite;
        AFill.ColorMirror := clWhite;
        AFill.ColorMirrorTo := clblue;

    end;
  End
end;

Open in new window

Do more with

Expert Office
Submit tech questions to Ask the Experts™ at any time to receive solutions, advice, and new ideas from leading industry professionals.

Start 7-Day Free Trial