In WPF UI Ho nodi connessi da percorsi bezier, in questo modo:aggiornamento WPF PathGeometry è _SLOW_
Quando l'utente trascina un nodo attorno, i percorsi di collegamento devono essere aggiornati in reale tempo. Tuttavia, ho notato un rallentamento (specialmente se un nodo è collegato a molti altri, o più nodi vengono trascinati contemporaneamente). Ho fatto il profilo, e il problema principale sembra essere qui:
Questa è la funzione che viene chiamata ogni volta che sia la proprietà di origine o di destinazione è cambiato. La geometria che costituisce il percorso sembra essere rigenerata internamente ogni volta che cambia uno dei punti di controllo. Forse se ci fosse un modo per impedire la rigenerazione della geometria fino a quando tutte le proprietà di dipendenza rilevanti sono state impostate?
EDIT: soluzione del Mart di utilizzare StreamGeometry accelerato in su in modo esponenziale; la funzione è lontana da un collo di bottiglia. Un po 'di riflessione suggerisce che PathGeometry utilizza StreamGeometry internamente e ogni volta che viene modificata una delle proprietà di dipendenza, viene ricalcolato StreamGeometry. Quindi in questo modo si elimina l'intermediario. Il risultato finale è:
private void onRouteChanged()
{
Point src = Source;
Point dst = Destination;
if (!src.X.isValid() || !src.Y.isValid() || !dst.X.isValid() || !dst.Y.isValid())
{
_shouldDraw = false;
return;
}
/*
* The control points are all laid out along midpoint lines, something like this:
*
* --------------------------------
* | | | |
* | SRC | CP1 | |
* | | | |
* --------------------------------
* | | | |
* | | MID | |
* | | | |
* -------------------------------
* | | | |
* | | CP2 | DST |
* | | | |
* --------------------------------
*
* This causes it to be horizontal at the endpoints and vertical
* at the midpoint.
*/
double mx = (src.X + dst.X)/2;
double my = (src.Y + dst.Y)/2;
Point mid = new Point(mx, my);
Point cp1 = new Point(mx, src.Y);
Point cp2 = new Point(mx, dst.Y);
_geometry.Clear();
_shouldDraw = true;
using(StreamGeometryContext ctx = _geometry.Open())
{
ctx.BeginFigure(src, false, false);
ctx.QuadraticBezierTo(cp1, mid, true, false);
ctx.QuadraticBezierTo(cp2, dst, true, false);
}
}
Il codice sorgente completo del progetto è disponibile presso http://zeal.codeplex.com per i curiosi.
Grazie; passare a StreamGeometry sembrava risolvere il problema! –