-
ACHTUNG - NEUES BLOG
Ab sofort steht unter http://devtyr.norberteder.com mein neues Blog zur Verfügung. Dieses Blog wird nicht weiter betreut, bleibt aber erhalten. Neue Eintr%auml;ge erfolgen nur mehr im neuen Blog. Kommentare werden ebenfalls nicht mehr behandelt. Wer weiterhin meinen Einträgen und Aktivitäten folgen möchte, möge bitte RSS-Feeds, Verlinkungen etc. an die neue Location anpassen.
|
Artikel: Steuerelemente für jeden Zweck
30.06.08 - .NET, WPF Beitrag von Norbert Eder| | In der aktuellen Ausgabe der visual studio one wurde mein Artikel Steuerelemente für jeden Zweck veröffentlicht.
Die Idee der Steuerelemente ist ja nicht neu. Relativ neu hingegen ist die Möglichkeit, grafische Elemente komplett von der eigentlichen Logik zu trennen – zumindest gilt dies für Microsoft-basierte Technologien.Mit der Windows Presentation Foundation wird den Entwicklern genau dies in die Hand gelegt. Sie als Entwickler und auch Ihr Kunde können davon profitieren. Dieser Artikel zeigt Ihnen, wie Sie dynamische WPF-Steuerelemente selber bauen können.
Link: visual studio one
| | | 3 Kommentare
- 903 mal angesehen
| 0 Trackbacks
| Permalink | Trackback-URL |
Diablo III - Offizielle Website online
28.06.08 - Internet Beitrag von Norbert Eder| | Unter http://eu.blizzard.com/diablo3/ steht ab sofort die offizielle Website von Diablo III zur Verfügung. Als Spieler der alten Versionen freue ich mich natürlich besonders, dass es zu einer neuen Version inkl. neuer Grafikengine kommen wird.
Mich wundert ja zusätzlich, dass daran bereits seit 4 Jahren entwickelt wurde und bis zur offiziellen Ankündigung ja kaum etwas davon zu hören war - ausser ein paar Gerüchten.
Dann hoffe ich, dass das Teil bald verfügbar sein wird.
| | | 2 Kommentare
- 804 mal angesehen
| 2 Trackbacks
| Permalink | Trackback-URL |
UniformGrid - das einfache Grid
24.06.08 - .NET, WPF Beitrag von Norbert Eder| | Im Namespace System.Windows.Controls.Primitives verbirgt sich ein Grid namens UniformGrid. Dabei handelt es sich um ein wirklich sehr einfaches Grid, welches (wie der Name schon sagt) im Endeffekt nicht mehr tut, als alle enthaltenen Elemente in gleicher Größe darzustellen. Dabei wandert jedes Kindelement in eine eigene Zelle.
Sehen wir uns gleichein Beispiel an:
<UniformGrid>
<Button Content="Button 1"/>
<Button Content="Button 2"/>
<Button Content="Button 3"/>
<Button Content="Button 4"/>
</UniformGrid>
Definiert wird ein UniformGrid mit insgesamt vier Buttons als Kindelemente. Und so sieht's aus:
Wird nun ein weiterer Button hinzugefügt, ändert sich das UniformGrid wie folgt:
Wie also zu sehen ist, werden die notwendigen Spalten und Reihen automatisch berechnet. Diese können aber mit den Attributen Columns und Rows beeinflusst werden:
<UniformGrid Columns="2" Rows="3">
<Button Content="Button 1"/>
<Button Content="Button 2"/>
<Button Content="Button 3"/>
<Button Content="Button 4"/>
<Button Content="Button 5"/>
</UniformGrid>
Definiert sind zwei Spalten und drei Reihen. Hier das Ergebnis:
Aber aufgepasst: angezeigt wird nur, was auch tatsächlich auf die vorhandene Fläche passt:
<UniformGrid Columns="2" Rows="2">
<Button Content="Button 1"/>
<Button Content="Button 2"/>
<Button Content="Button 3"/>
<Button Content="Button 4"/>
<Button Content="Button 5"/>
</UniformGrid>
Definiert sind zwei Spalten und zwei Reihen, vorhanden sind jedoch fünf Elemente. Das wird daraus:
Viel Spaß beim Probieren.
| | | 2 Kommentare
- 1715 mal angesehen
| 0 Trackbacks
| Permalink | Trackback-URL |
Was hat Firefox 3 mit Nirvana zu tun?
24.06.08 - Internet Beitrag von Norbert Eder| | Gemeint ist hier nicht Nirvana als Band, sondern vielmehr Nirwana als Austritt aus dem Kreislauf des Leidens.
Aber was hat das nun mit Firefox 3 zu tun? Grundsätzlich ja ein Browser, den ich dann doch des Öfteren benutze, da ich auf einem Rechner IE7 nicht installieren kann, da sonst ein bestimmtes Produkt nicht laufen würde und da hin und wieder Webgeschichten mit mehreren Browsern getestet werden müssen.
Nun allerdings seit Firefox 3 bin ich mir nicht mehr so sicher, ob ich ihn auch wirklich weiterhin benutzen möchte. Ich tippe mal auf: "Nein, ich will nicht". Warum? Weil sich Firefox 3 gerade bei Multimedia-Inhalten von seinem Leid selbständig erlöst und einfach alle Schotten dicht macht. Bumm, zack und weg. Ständig.
Ab sofort kann sich das Teil im Nirwana vertschüssen, so oft es will. Da stört es mich nicht weiter. *Winke*
| | | 9 Kommentare
- 895 mal angesehen
| 0 Trackbacks
| Permalink | Trackback-URL |
Was ist Community?
23.06.08 - Internet, Community Beitrag von Norbert Eder| | Eine Community ist eigentlich nicht nur ein Blog bei dem sich einige Personen angemeldet haben. Eine Community ist nicht nur ein Forum mit zahlreichen Usern, die sich über unterschiedlichste Themen unterhalten. Eine Community ist wesentlich mehr.
Eine Community zeichnet sich dadurch aus, dass
- sich Menschen gegenseitig bei Problemen helfen
- gemeinsam Ideen umgesetzt werden
- gemeinsam Wissen verteilt und somit die gemeinsame Community gestärkt wird
- die einzelnen Community-Betreiber zusammen halten um gemeinsam stark zu werden
- einzelne Community-Betreiber sich an Abgemachtes halten um wirklich gemeinsam für die Community da sein zu können
- jeder die Möglichkeit besitzt seine Stärken auszuspielen
Und natürlich könnte man noch weitere Punkte hinzufügen. Schade ist nur, dass sich einige absolut nicht daran halten und lieber ihren ganz persönlichen Weg beschreiten. Dagegen ist auch nichts einzusetzen.
Traurig finde ich jedoch, dass es immer jemanden geben muss, der gegen gemeinsam definierte Spielregeln verstößt und das auch noch für gut befindet. Für mich ist Derartiges nicht mit dem Community-Gedanken zu vereinbaren.
Anscheinend sind Regeln da, um gebrochen zu werden. Gestern Beschlossenes gilt heute nicht mehr ohne auch nur einen Laut von sich zu geben. Und das dort, wo eigentlich am gleichen Strang gezogen werden sollte.
Das hat keinen Wert. Weder auf persönlicher Ebene, noch in Bezug auf die Community. Wenn es unbedingt so sein muss, make it so, aber ohne mich.
| | | 11 Kommentare
- 913 mal angesehen
| 0 Trackbacks
| Permalink | Trackback-URL |
WPF: Offene Fenster im Überblick behalten
22.06.08 - .NET, WPF Beitrag von Norbert Eder| | Wir kennen es wohl alle: Das "Window"-Menü mit allen offenen Fenstern derselben Applikation. Vor allem in den Office-Produkten war dies immer wieder zu finden. Doch wie kann dies unter WPF implementiert werden? Dieser Artikel zeigt wie's geht. Und so kann das Endresultat aussehen (es ist zwar nicht hübsch, aber es funktioniert):
Zu Beginn stellt sich natürlich dir Frage ob es da nicht schon etwas Fertiges gibt. Ja. Gibt es. Unter Application.Current.Windows findet sich die aktuelle Auflistung aller geöffneten Fenster. Einziger Nachteil: Diese stecken in einer eigenen WindowCollection, welche lediglich ICollection und IEnumerable implementiert. Damit jedoch Data Binding möglich ist, wäre eine ObservableCollection notwendig.
Damit es uns Entwicklern nicht fad wird, müssen wir daher selbst in die Tasten klopfen und unser eigenes System entwickeln, wollen wir doch Data Binding verwenden!
Zuerst benötigen wir eine simple Datenklasse, welche Informationen für uns hält und auch später wieder zugänglich macht:
public class WindowInformation
{
private Window _window;
public WindowInformation(Window window)
{
_window = window;
}
public Window Window
{
get { return _window; }
}
public int WindowHashCode
{
get { return _window.GetHashCode(); }
}
public String Title
{
get { return _window.Title; }
}
public ImageSource Icon
{
get { return _window.Icon; }
}
}
Die Datenklasse fungiert in diesem Fall lediglich als Wrapper-Klasse, könnte aber ohne großen Aufwand um weitere Informationen angereichert werden.
Damit nun Data Binding verwendet werden kann, benötigen wir eine - wie schon angesprochen - ObserableCollection:
public class WindowInformationCollection :
ObservableCollection<WindowInformation>
{
}
Nun wird eine Manager-Klasse benötigt, welche die Liste der geöffneten Fenster hält und zusätzliche Funktionen wie Entfernen eines Fensters oder das Zurückgeben eines speziellen Fensters zur Verfügung stellt. Dieser Manager wurde mit dem Singleton-Pattern umgesetzt, damit sichergestellt ist, dass nur eine Instanz davon pro gestarteter Anwendungsinstanz vorhanden ist.
public class WindowManager
{
private static WindowManager _manager;
private WindowInformationCollection _openWindows =
new WindowInformationCollection();
private WindowManager() { }
public static WindowManager GetInstance
{
get
{
if (_manager == null)
_manager = new WindowManager();
return _manager;
}
}
public WindowInformationCollection OpenWindows
{
get { return _openWindows; }
}
public Window GetOpenWindow(int hashCode)
{
foreach (WindowInformation wi in _openWindows)
{
if (wi.WindowHashCode == hashCode)
{
return wi.Window;
}
}
return null;
}
public bool RemoveOpenWindow(int hashCode)
{
WindowInformation windowToRemove = null;
foreach (WindowInformation wi in _openWindows)
{
if (wi.WindowHashCode == hashCode)
{
windowToRemove = wi;
break;
}
}
if (windowToRemove != null)
{
_openWindows.Remove(windowToRemove);
return true;
}
return false;
}
}
Zu guter Letzt wird noch ein Handler implementiert, der schlussendlich in das Window-Element des XAMLs eingebunden werden kann und somit ein Fenster in das System einbindet:
public class WindowInformationHandler
{
public static readonly DependencyProperty
IsHandledProperty =
DependencyProperty.RegisterAttached("IsHandled",
typeof(bool), typeof(WindowInformationHandler),
new FrameworkPropertyMetadata((bool)false,
new PropertyChangedCallback(OnIsHandledChanged)));
private static void OnIsHandledChanged(
DependencyObject dObj,
DependencyPropertyChangedEventArgs e)
{
Window openWindow = dObj as Window;
if (openWindow != null)
{
openWindow.Loaded +=
new RoutedEventHandler(WindowLoaded);
openWindow.Closed +=
new EventHandler(WindowClosed);
}
}
public static bool GetIsManaged(DependencyObject dObj)
{
return (bool)dObj.GetValue(IsHandledProperty);
}
public static void SetIsManaged(
DependencyObject dObj,
bool value)
{
dObj.SetValue(IsHandledProperty, value);
}
private static void WindowClosed(
object sender, EventArgs e)
{
Window closedWindow = sender as Window;
if (closedWindow != null)
{
WindowManager.GetInstance.RemoveOpenWindow(
closedWindow.GetHashCode()
);
openWindow.Loaded -=
new RoutedEventHandler(WindowLoaded);
openWindow.Closed -=
new EventHandler(WindowClosed);
}
}
private static void WindowLoaded(
object sender, RoutedEventArgs e)
{
Window openWindow = sender as Window;
if (openWindow != null)
{
WindowInformation winInfo =
new WindowInformation(openWindow);
WindowManager.GetInstance.OpenWindows.Add(winInfo);
}
}
}
Wird die Eigenschaft IsHandled auf true gesetzt, werden zwei Events (Loaded und Closed) registriert. Auf diese wird in weiterer Folge reagiert, um das Fenster nach erfolgtem Laden in die Liste der geöffneten Fenster aufzunehmen bzw. davon auch wieder zu entfernen.
In XAML wird dies folgendermaßen in das Window-Element eingebunden:
local:WindowInformationHandler.IsManaged="true"
Damit ist dieses System fertig und kann angewandt werden.
Das XAML-Markup für oben gezeigten Screenshot sieht so aus:
Und hier noch der Inhalt aus dem Code Behind:
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
mnuWindows.ItemsSource =
WindowManager.GetInstance.OpenWindows;
}
private void NewWindow(object sender,
RoutedEventArgs e)
{
MainWindow window = new MainWindow();
window.Title = String.Format("Open Window {0}",
Application.Current.Windows.Count);
window.Show();
}
private void ShowWindow(object sender,
RoutedEventArgs e)
{
MenuItem mi = sender as MenuItem;
if (mi != null)
{
WindowInformation wi = mi.DataContext
as WindowInformation;
if (wi != null)
{
wi.Window.Focus();
}
}
}
}
Voilá!
| | | 1 Kommentar
- 1363 mal angesehen
| 0 Trackbacks
| Permalink | Trackback-URL |
Konvertierung von C# nach VB.NET und wieder zurück
20.06.08 - .NET, Allerlei Beitrag von Norbert Eder
WPF: Layout-System und Performance
18.06.08 - WPF Beitrag von Norbert Eder| | Müssen viele Elemente erstellt und dargestellt werden, kann die Performance schon mal sehr schnell in den Keller gehen. Dabei müssen die darzustellenden Elemente keineswegs komplex sein. Vielmehr reichen oft kleine Fallen, die vermieden werden wollen.
Oftmals führt das Verwenden eines falschen Panels zu einem Performance-Problem. Meist ist es so, dass genau das Panel verwendet wird, welches die gewünschte Aufgabe mit dem geringsten Aufwand (für uns als Entwickler) erfüllt. So wird also beispielsweise ein StackPanel verwendet, sollen Elemente untereinander platziert werden - und zwar in der Reihenfolge, wie sie hinzugefügt wurden. Werden ein paar wenige Elemente hinzugefügt, ist keine Auswirkung zu spüren. Sind es hunderte oder gar tausende, dann wird dieser Vorgang spürbar langsamer.
Hierfür verantwortlich ist die unterschiedliche Funktionalität der Panels. Während ein Canvas relativ dumm ist und Elemente basierend auf einer Positionsangabe platziert, ist diese Logik in einem StackPanel oder einem DockPanel wesentlich komplexer.
Layout System
Vom Layout-System werden pro Kindelement zwei Schritte durchgeführt:
Jedes dieser Kindelemente besitzt seine eigene Implementierung von Measure und Arrange, damit die an das Element gestellten Anforderungen bezüglich des Layout-Verhaltens erfüllt werden können.
Ablauf Layouting
- Ein Kindelement (UIElement) beginnt den Layoutprozess durch das Erfassen der Basiseigenschaften
- Dann werden die Eigenschaften bezüglich Höhe, Breite, Randstärke ausgewertet
- Ausführung von Panel-spezifischer Logik (siehe Orientation-Eigenschaft des StackPanels)
- Der Inhalt wird ausgerichtet bzw. positioniert, nachdem die Größe etc. aller Kindelemente bemessen wurde.
- Die Liste der Kindelemente wird am Bildschirm ausgegeben
Wann wird es haarig?
Beim Eintreten bestimmter Aktionen, wird der gesamte Layout-Prozess erneut durchlaufen. Folgende Aktionen sind dafür maßgeblich:
- Hinzufügen eines neuen Kindelementes
- Ausführung der Methode UpdateLayout eines Kindelementes
- Zuweisung von LayoutTransform eines Kindelementes
- Bei Änderung einer Dependency Property mit Auswirkung auf Measure und Arrange (gesetzt über die Metadaten)
Fazit
Durch das Wissen wie das Layout-System funktioniert und wann es erneut durchlaufen werden muss, lässt sich feststellen, in welchen Fällen worauf verzichtet werden sollte. So kann es beispielsweise effizienter sein, eine ListBox anstatt eines StackPanels zu verwenden (durch das Definieren von Templates kann das auch schön aussehen), oder vielleicht doch einen Canvas.
Ist man sich nicht sicher, ob die geplante Variante die beste Performance bietet, bietet sich auch an, vor der konkreten Implementierung dann eventuell doch eine kleine Beispielanwendung zu schreiben. Auch eingesetzte Profiler sind hilfreich.
Siehe auch: WPF: Performance messen und verbessern
| | | Kommentar hinzufügen
| 0 Trackbacks
| Permalink | Trackback-URL |
Ein Wortspiel gefällig?
17.06.08 - Blog-Intern Beitrag von Norbert Eder| | Heute habe ich mir aus Spaß die letzten Einträge meines Blogs via wordle.net grafisch darstellen lassen. Eigentlich eine recht nette Sache. Hier das Ergebnis:
Damit hätten sich auch schon ein paar passende Keywords zusammen getan ;-)
| | | 1 Kommentar
- 770 mal angesehen
| 1 Trackbacks
| Permalink | Trackback-URL |
.NET Blog - Refresh
10.06.08 - Blog-Intern Beitrag von Norbert Eder Zurück Weiter
|
|
|
|
|
|
|