Wyświetlanie kontrolek XAML’owych tylko w Debug

Podczas działania naszej aplikacji (a będącej jeszcze w fazie dewelopmentu) często zachodzi potrzeba na wyświetlanie dodatkowych informacji. Przykładowo wyświetlamy różnego rodzaju identyfikatory czy kody wczytanych danych aby śledzić czy edytowany rekord jest tym rekordem, o który nam chodzi. W tym celu używamy różnego rodzaju loggerów, tracerów, outputów, a także najnormalniej w świecie wyrzucamy tą zawartość na interfejs użytkownika. Nie uważam, że jest to dobre podejście, ale czasami tak robimy. Gdy już się decydujemy na ten krok, każdy sobie mówi, że będzie pamiętać o tym kawałku kodu i zakomentuje go lub usunie przed releasem. Zamiast tak mówić, lepiej działać i zabezpieczyć się przed późniejszą kompromitacją.

Na początek najlepiej tak pisać, aby „nasz tajny” kawałek wyświetlał się tylko w Debugu. Wtedy, wysyłając aplikację do klienta, robimy build w konfiguracji Release i po kłopocie. Aby odnieść się z poziomu C# do konfiguracji Debug wystarczy użyć instrukcji #if #else #endif

// load user data
var user = LoadUser(123);

#if DEBUG
MessageBox.Show("UserID: " + user.Id);
#endif

Proste. Instrukcja MessageBox.Show nie wykona się, jeśli kompilacja będzie w konfiguracji Release. A co jeśli chcemy pokazywać/ukrywać kontrolki w Silverlight’cie w XAML’u?

Sterowanie w XAML’u

Jak powszechnie wiadomo w technologii Silverlight od strony interfejsu użytkownika mamy język XAML. Niestety nie przewidzano tam instrukcji #if #else #endif  jak to mamy po stronie C#. Ale można napisać konwerter, którego ciało wykona kawałek kodu C#, a tam już jesteśmy w domu.

W projekcie Silverlight utwórz katalog Converters. W katalogu Converters utwórz nowy plik DebugToVisibilityConverter.cs.

Aby nowa klasa stała się konwerterem musi implementować interfejs IValueConverter z przestrzeni System.Windows.Data. Następnie implementujemy metodę Convert tak, aby odpowiednio zwracała Visibility.Visible lub Visibility.Collapsed:

public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
#if DEBUG
 return Visibility.Visible;
#else
 return Visibility.Collapsed;
#endif
}

Implementację metody ConvertBack można pominąć (zostawiamy domyślnie throw new NotImplementedException). Nasz konwerter będzie sterował widocznością kontrolki w zależności od konfiguracji. Czas przygotować kilka kontrolek. Mój przykład to Grid i kilka TextBlock’ów i TextBox’ów. Najciekawsze są ostatnie 2 kontrolki. ID użytkownika ma być wyświetlane tylko w trybie Debug.

Aby użyć nowego konwertera trzeba go dodać do zasobów strony:

Na koniec przypinamy konwerter do kontrolek, których widocznością chcemy sterować:

DataContext

Uwaga! Aby całość zadziałała, kontrolka, którą chcemy ukrywać/pokazywać musi posiadać jakikolwiek DataContext. Bez tego, kod konwertera w ogóle się nie wykona, ponieważ Silverlight uzna, że nie ma co Bindować i nie trzeba stosować konwertera. Dlatego jeśli twoje kontrolki nie posiadają DataContext’u, można go w prosty sposów ustawić z CodeBehind strony, np:

 
using System.Windows.Controls;
namespace SilverlightXamlInDebug
{
    public partial class MainPage : UserControl
    {
        public MainPage()
        {
            InitializeComponent();

            DataContext = new object(); // set fake data context
        }
    }
}

Podsumowanie

Powyższe rozwiązanie u mnie się sprawdza. Nie programuję w WPF’ie, ale jestem przekonany, że tam również to zadziała. Jeśli macie swoje sprawdzone pomysły to zapraszam do komentowania.

Advertisements

5 thoughts on “Wyświetlanie kontrolek XAML’owych tylko w Debug

  1. Pingback: dotnetomaniak.pl

  2. Jeśli tylko od strony kodu, to jest ‚System.Diagnostics.Debugger.IsAttached’, co świetnie sprawdza się w projektach typu WindowsService.

  3. W tym wpisie chciałem się skupić na możliwościach XAML’a. Bo w samym C# (nieważne czy w code-behind czy serwisie) mamy większe pole manewru (to o czym pisali Łukasz i Paweł). Musze jeszcze sprawdzić ostatnie rozwiązanie.

Możliwość komentowania jest wyłączona.