none
issue with textblock foreground not updating if it is touched / tapped RRS feed

  • Question

  • I have a textblock, whose foreground I set to disabled if a list is null. I populate said list on a background thread and when that thread is done, I put the textblock foreground back to foreground brush. On the textblock tap event, I have my code in an if statement that checks the list item count.

    My issue is that if the textblock is tapped while the background thread is running or the foreground is disabled (whichever way you see it; they are at the same time), it won't update to the foreground brush until tapped. This behavior continues for every update on textblock/background thread unless you make a new instance of the page (navigate back then navigate back in).

    has anyone else had an issue with this? I tried setting the IsHitTestVisible property to false, but that didn't change anything.

    My code is pretty simple. In the method where I start the background thread, I set the foreground to disabled and run the worker. On the worker completed event args, I change it back. This happens on the emulator and my Focus (original).

    Thanks for the feedback.
    Monday, April 30, 2012 11:07 PM

Answers

  • I don't see anything obviously wrong. You could try wrapping the Foreground change in Dispatcher.BeginInvoke.

        Dispatcher.BeginInvoke(() => 
            { 
                KanjiTB.Foreground = this.Resources["PhoneForegroundBrush"as Brush; 
            }); 

    However, your thread completion may already be running in the UI thread and it might not make a difference.


    Richard Woo
    Wednesday, May 2, 2012 8:54 AM

All replies

  • I'll make a wild guess at what you're doing. Is your background thread updating the color through databinding, and in the other cases are you updating it directly? Updating directly would terminate the binding.


    Richard Woo
    Tuesday, May 1, 2012 4:26 AM
  • Thank you for your reply, Mr. Woo. I believe that you have responded to almost every post I've made and I really appreciate it.

    I am not using data binding at all on this one. I've had trouble binding to things set in code behind, although I think I could manage to make a converter and make the list public or perhaps set the binding in code-behind.  What I do is on the navigatedto event, I check my isFirstRun bool and set the foreground to disabled brush if it is true, which allows the user to leave the app, come back and everything has the proper brush. On the run worker completed event is where I change the value back to foreground. When I step through this event, after the line for setting the brush to foreground, I mouse over the foreground property and it says "#FFFFFFFF," but on the emulator/phone, it doesn't update (it still shows the disabled brush).

    Now, when this happens, when I tap on the textblock again, it changes to the foreground brush and brings up the popup that I want. If I change the datacontext to another item and re-run the background worker, which finds related items, the foreground is changed to disabled, like it should be, but not back to the foreground brush.

    The foreground changing functions as expected if the textblock is not tapped before I'm ready for it to be.

    EDIT: I just ran the code again and it seems to be different from how I remember. Changing the foreground back works, even when changing the datacontext, until the textblock is tapped. Then it starts to not change back at all, even though the mouse-over on the foreground property on step over indicates that it is.
    Tuesday, May 1, 2012 2:29 PM
  • I made another discovery. I had, in an event that takes place before this, put in code to change the foreground to disabled brush. That's when the brush was changing. Removing that, and relying solely on the code below, the brush does not change at all. However, I also change the image uri to and from the disabled/enabled versions and that updates as it should. As of now, the textblock does not change at all.

    Here is the source code:

     void UpdateOtherOccurrences() 
            { 
                if (progressBar.IsIndeterminate == false
                    progressBar.IsIndeterminate = true
     
                kanjiTB.Foreground = this.Resources["PhoneDisabledBrush"as Brush; 
                SetImageToDisabled();// sets the image source to the appropriate brush (light or dark theme) 
     
                worker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(worker_OtherOccurrencesCompleted); 
                // run the background worker to get the new list of items 
                worker.DoWork += delegate(object sender1, DoWorkEventArgs dw) 
                { 
                    // get the first 8 occurrences of a match 
                    otherOccurrences = (from d in dictionary.Entries 
                                        where d.Name.Contains(KanjiList[currentIndex].Name) 
                                        select d).Take(8).ToList(); 
                }; 
                worker.RunWorkerAsync(); 
            } 
     
            void worker_OtherOccurrencesCompleted(object sender, RunWorkerCompletedEventArgs e) 
            { 
                // reset the brush to its appropriate values 
                kanjiTB.Foreground = this.Resources["PhoneForegroundBrush"as Brush; 
                progressBar.IsIndeterminate = false
     
                //set the image source 
                if (isLightTheme == Visibility.Collapsed) // using dark theme 
                    bmp.UriSource = (isAvailable == true) ? new Uri("Icons/circledSound.png", UriKind.Relative) : new Uri("Icons/circledSoundPlayDarkThemeDisabled.png", UriKind.Relative); 
                else 
                    bmp.UriSource = (isAvailable == true) ? new Uri("Icons/circledSoundLightTheme.png", UriKind.Relative) : new Uri("Icons/circledSoundLightThemeDisabled.png", UriKind.Relative); 
     
                image.Source = bmp; 
     
                worker.RunWorkerCompleted -= worker_OtherOccurrencesCompleted; 
            } 

    Tuesday, May 1, 2012 2:57 PM
  • I don't see anything obviously wrong. You could try wrapping the Foreground change in Dispatcher.BeginInvoke.

        Dispatcher.BeginInvoke(() => 
            { 
                KanjiTB.Foreground = this.Resources["PhoneForegroundBrush"as Brush; 
            }); 

    However, your thread completion may already be running in the UI thread and it might not make a difference.


    Richard Woo
    Wednesday, May 2, 2012 8:54 AM
  • This is odd. The page that I was referencing is a sort of test layout for a user control, of which I intend to have 3 in a horizontal stackpanel so that I can incorporate a scrolling effect. When implementing this, I had to put some of the event handlers in the parent page, which seems to have solved that problem. I don't know why or how.

    Although now I am stuck with the third instance of the control not showing up at all. smh. haha.

    Thank you very much for your help. If I ever get into this situation again, I'll be sure to try your suggestion. I have a feeling that I'll be needing it soon.
    Thursday, May 3, 2012 7:14 PM