davidpoll.com
Posts Tagged collegamenti relativi
collegamenti ipertestuali relativi alla navigazione Silverlight
Inviato da david.poll in Silverlight il 20 settembre 2009
Se non avete già notato, mi capita di come la funzione di navigazione in Silverlight un bel po '(mi chiedo perché?
). In my altri post sulla navigazione , ho trascorso un certo tempo esplorare come potrai navigare all'interno di pagine in insiemi diversi da dell'assemblea ricorso principale e di come queste assemblee possono essere caricati on-demand (concessi, si utilizza alcune soluzioni alternative, ma si siamo dove vogliamo andare!).
Questo è tutto bene e buono, but presenta un problema fastidioso che l'impatto della manutenibilità di code such. In particolare, è forces every collegamento ipertestuale all'interno di ciascuna delle assemblee external per sapere come fare riferimento al suo assembly di nome (questa è simile al problema con URL assoluti in collegamenti ipertestuali alle pagine web - i link diventano strettamente accoppiati alla pagina per la quale sono stati creati, e non possono essere copiati in altri progetti).
Tecnicamente, quasi tutti gli URI utilizzato dal quadro di navigazione oggi sono gli URI relativi (a meno che UriMappings sono usati per trasformare quelle in assoluto quelle relative), ma sono relative application-and mai Page-relative. Questo significa che se si ha una pagina at " / Views/Page1.xaml "e desidera creare il collegamento a un'altra pagina a" / Views/Page2.xaml «dal di dentro Page1, si deve fare riferimento l'intero percorso (" / Views/Page2.xaml ") piuttosto che solo il percorso relativo alla pagina (ad esempio "Page2.xaml" o "./Page2.xaml").
In questo post, vedremo at un modo per consentire la navigazione Page-within tuo parente Pagine Silverlight. The approach I will useremo approfittare della interfaccia INavigate aggiunta in Silverlight 3 and control il HyperlinkButton che utilizza questa interfaccia per effettuare la navigazione quando cliccato.
L'interfaccia INavigate assomiglia a questo:
public interface INavigate ( / / Metodi source); Naviga bool (Uri fonte); )
Si tratta di una semplice interfaccia con uno scopo molto semplice: consentire a un componente di fornire un modo per gestire la navigazione a un URI. Al momento, l'unico componente integrato in Silverlight che ha effettivamente vantaggio di esso è il controllo HyperlinkButton. Usiamo questo controllo molto spesso in Navigazione applicazioni abilitate, in quanto ci permette di indirizzare uno particolare controllo Frame per passare a una pagina da Uri. In the progetto Silverlight Navigation modello Applicazione, vedrai XAML like questo:
: Frame x : Name =" ContentFrame " Style ="{ StaticResource ContentFrameStyle }" <Navigazione: Telaio x: Name = "ContentFrame" style = "(StaticResource ContentFrameStyle)" Navigated ="ContentFrame_Navigated" NavigationFailed ="ContentFrame_NavigationFailed"> Source = "/ home" navigato = "ContentFrame_Navigated" NavigationFailed = "ContentFrame_NavigationFailed"> : Frame > </ Navigazione: Frame>
x : Name ="Link2" Style ="{ StaticResource LinkStyle }" NavigateUri ="/About" TargetName ="ContentFrame " Content ="about"/> <HyperlinkButton x: Name = "Link2" style = "(StaticResource LinkStyle)" NavigateUri = "/ A proposito di" TargetName = "ContentFrame" content = "su" />
Tutto questo funziona perché il controllo Frame implementa INavigate. In altre parole, non c'è nessuna magia là - lo si può utilizzare anche! Ecco il modo in cui HyperlinkButton funziona quando si sta cercando di indirizzare un INavigate (circa
):
- Per ogni genitore FrameworkElement risalendo l'albero visuale dal HyperlinkButton ...
- Verificare se il FrameworkElement è un INavigate e che il suo nome corrisponde TargetName (ignorato se TargetName è null o vuoto)
- Se è così, chiamata INavigate.Navigate () sul FrameworkElement
- In caso contrario, ricorsivamente ricerca di un INavigate che è propriamente chiamato all'interno di ciascuno dei figli della FrameworkElement
- Se non propriamente chiamato INavigate è stato trovato, continuare a muoversi l'albero visuale
- Verificare se il FrameworkElement è un INavigate e che il suo nome corrisponde TargetName (ignorato se TargetName è null o vuoto)
In altre parole, il HyperlinkButton cercherà la sua strada su e giù per l'albero di visuale (tecnicamente fare una ricerca pre-ordine in ampiezza da ciascun genitore del HyperlinkButton, facendo strada l'albero visuale) per un adeguato INavigate chiamare.
Allora, cosa fa tutta questa roba INavigate significa per me?
Con tale dettaglio tecnico fuori del modo, la domanda che si pone è: come possiamo usare questa opzione per consentire la navigazione Page-parente? Beh, la navigazione a causa di un frame all'interno di pagine di lavori oggi è perché il controllo Frame implementa INavigate, e la HyperlinkButton si sta facendo strada l'albero visuale finché non trova ciò.
Per i nostri scopi, questo è grande, perché significa che possiamo intercettare la chiamata a INavigate.Navigate () implementando l'interfaccia in qualche luogo fra la HyperlinkButton e la cornice. C'è un posto comodo per questo, dal momento che le applicazioni che utilizzano Page / Frame e HyperlinkButtons all'interno di tali pagine sono un albero visuale come questo:
- Applicazione
- Disposizione
- Telaio
- Pagina
- HyperlinkButton
- Altri controlli
- Pagina
- Altri controlli
- Telaio
- Disposizione
Quello che sto suggerendo è che la pagina si naviga per attuare INavigate e girare pagina, parente di Uri in applicazioni relative Uri prima di consegnare loro fuori del NavigationService (o la cornice) per eseguire di fatto la navigazione.
Sono andato avanti e ampliato la mia libreria DynamicNavigation fare DynamicPage attuare INavigate di fare ciò che vogliamo, ma si potrebbe fare lo stesso su qualsiasi sottoclasse di Page (compresi tutti una delle pagine se non si vuole una classe base comune) . Ecco il mio semplice implementazione (con un interruttore per disattivare questa funzione DynamicPages):
{ return ( bool )GetValue(RelativeLinksProperty); } set { SetValue(RelativeLinksProperty, value ); } } public static readonly DependencyProperty RelativeLinksProperty = DependencyProperty .Register( "RelativeLinks" , typeof ( bool ), typeof ( DynamicPage ), new PropertyMetadata ( true )); private static readonly Uri basePlaceHolderUri = new Uri ( "none:///" , UriKind .Absolute); #region INavigate Members public bool Navigate( Uri navigateUri) { string original = navigateUri.OriginalString; if (RelativeLinks && !navigateUri.IsAbsoluteUri && !original.StartsWith( "/" )) { Uri result; if (NavigationService.CurrentSource.IsAbsoluteUri) { result = new Uri (NavigationService.CurrentSource, navigateUri); } else { Uri baseUri = new Uri (basePlaceHolderUri, NavigationService.CurrentSource); result = new Uri ( "/" + basePlaceHolderUri.MakeRelativeUri( new Uri (baseUri, navigateUri)).OriginalString, UriKind .Relative); } return NavigationService.Navigate(result); } else { return NavigationService.Navigate(navigateUri); } } #endregion pubblico RelativeLinks bool (get (return (bool) GetValue (RelativeLinksProperty);) set (SetValue (RelativeLinksProperty, valore);)) public static readonly DependencyProperty RelativeLinksProperty = DependencyProperty. Register ("RelativeLinks", typeof (bool), typeof (DynamicPage) , nuovo PropertyMetadata (true)); private readonly static Uri basePlaceHolderUri = new Uri (":///" nessuno, UriKind. assoluto); # regione INavigate membri pubblici bool Navigate (Uri navigateUri) (stringa = navigateUri.OriginalString originale, se (RelativeLinks & &! navigateUri.IsAbsoluteUri & &! original.StartsWith ("/")) (risultato Uri, se (NavigationService.CurrentSource.IsAbsoluteUri) (risultato = new Uri (NavigationService.CurrentSource, navigateUri);) else (baseUri Uri = new Uri (basePlaceHolderUri, NavigationService.CurrentSource); risultato = new Uri ("/" + basePlaceHolderUri.MakeRelativeUri (nuovo Uri (baseUri, navigateUri)). OriginalString, UriKind. Relative);) ritorno NavigationService.Navigate (risultato);) else ( ritorno NavigationService.Navigate (navigateUri);)) # endregion
Ora, all'interno the pagina, si can utilizzare Page-URI relativo's on HyperlinkButtons. All devi fare avoid is setting uno TargetName (sia attraverso uno style o direttamente sul HyperlinkButton), e la pagina handle la navigation!
Page-URI relativo può assumere varie forme. Presumendo che la pagina che stai attualmente è "/ MyLibrary," component/Views/Main/Page1.xaml, le seguenti trasformazioni si verifichi (come esempio):
- "Page2.xaml" -> "/ MyLibrary; component/Views/Main/Page2.xaml"
- "./Page2.xaml" -> "/ MyLibrary; component/Views/Main/Page2.xaml"
- "../Page3.xaml" -> "/ MyLibrary; component/Views/Page3.xaml"
- "../Secondary/Page3.xaml" -> "/ MyLibrary; component/Views/Secondary/Page3.xaml"
- "../../ BasePage.xaml "->" / MyLibrary; componente / BasePage.xaml "
- "SubMain/Page4.xaml" -> "/ MyLibrary; component/Views/Main/SubMain/Page4.xaml"
- "SubMain/Page4.xaml? A = b = c & d" -> "/ MyLibrary; component/Views/Main/SubMain/Page4.xaml? A = b = c & d"
- "/ MyLibrary; component/Views/Main/Page5.xaml" -> "/ MyLibrary; component/Views/Main/Page5.xaml" (nessun cambiamento)
Cool! Posso vederlo in azione?
Certo!
Come sempre, si può giocare con una applicazione in esecuzione che fa questo qui:
Clicca sul link in fondo a questa pagina, per una navigazione peform relativo che si dovrebbe prendere in un viaggio tra un numero di pagine - che navigare utilizzando la navigazione relativo.
Per riferimento, qui è la struttura dei file per l'applicazione di esempio.

Allora, qual è il tuo punto?
Bene, per riassumere - in grado di fare aumenti di navigazione pagina relativa alla portabilità delle pagine. E 'particolarmente utile se lo si utilizza in combinazione con UriMapping. Con la tecnica di cui sopra, la "parente-ness" si riferisce per l'utente- di fronte Uri. Ciò significa che è possibile creare UriMappings al fine di creare una struttura "virtuale di file e tutti i link relativi dovrebbe continuare a lavorare (e di quelli nuovi potrebbe essere possibile!). Dategli un colpo e fatemi sapere cosa pensate! sto continuando a sperimentare con navigazione, sempre alla ricerca di cose che potrebbero migliorare l'esperienza di quando si lavora con esso.
Basta! 'Dammi la merce!
Pazienza! Non hai davvero che ti avrei lasciato appeso, vero? Ecco qua:
- DynamicNavigation librerie (vedi altri miei post per un'introduzione a ciò che offre e come utilizzarlo - 1 , 2 )
- Esempio di Fonte
Smettila di parlare a voi stessi!
Okay. ![]()
Dinamica di navigazione , di navigazione , link relativi , Silverlight , Silverlight 3
Post recenti
- Per XAML, con amore (un esperimento con la serializzazione XAML in Silverlight)
- Assunzione di Microsoft Silverlight 4 La domanda oltre il browser (TechEd WEB313)
- Comune di navigazione dell'interfaccia utente e autorizzazione-driven Sitemaps
- I campioni aggiornato e il codice nei commenti
- Un "Autenticazione rinfrescante" / Autorizzazione esperienza con Silverlight 4
- Rendere più facile la stampa in Silverlight 4
- Silverlight 4 rilasciato!
- Nuovo nella Silverlight 4 RC: XAML Funzionalità
Tag
. NET RIA Services attività di controllo Autorizzazione Blend BusyIndicator CollectionView ContentLoader controlli di associazione dati di navigazione Dynamic Fun Konami Code registrazione MIX '10 di navigazione Off-Topic Out-of-browser PDC PDC09 Personal Stampa Progetti Collegamenti relativi server Silverlight Silverlight 3 Silverlight 3 Beta 4 Silverlight Silverlight 4 Beta di Silverlight 4 RC di Silverlight e oltre (lastra) Silverlight Toolkit Sitemap TechEd TechEd 2010 Nord America Trusted Applications convalida Visual Studio 2010 RIA Services WCF XAML XamlSerializerTwitter: @ depoll
- @ JeffHandley consideri globalizzato. ;) 13 agosto 2010 08:30
- rburger @ E 'un incredibile coro - vale la pena dare un'occhiata se sono nelle vicinanze 6 ago 2010 04:54
- @ Rburger Sono stati campioni del momento internazionale dopo i tempi (erano sconvolti lo scorso anno - prima volta in 30 anni non hanno vinto) 6 agosto 2010 04:53
Silverlight Altri post sul blog - Windows Client Developer Roundup 039 per 2010/08/30 30 agosto 2010
- Caricamento di un file XML statico per il vostro Windows Phone / Silverlight App 27 agosto, 2010
- Post temporaneo utilizzato per il tema di rilevamento (9ce8ce41-59b5-4f6e-b7e6-b485f01bc218 - 3bfe001a-32de-4114-a6b4-4005b770f6d7) 27 Ago 2010
Disclaimer
Il contenuto di questo sito rappresenta la mia opinione personale e pensieri al momento del distacco, e non rispecchiano quelli del mio datore di lavoro in alcun modo.











