Tag Archives: Silverlight

Almás gomb Silverlightban

Nagy fába vágtam a fejszém, amikor szerettem volna valami igazán szépet alkotni Silverlightban, ugyanis a dizájnhoz egyáltalán nem értek. Valahonnan viszont rémlett, hogy az Expression Design tud Photoshopból importálni és XAML-be exportálni, így letöltöttem egy pofás iPhone stílusú gombot a netről .psd formátumban és megpróbáltam .xaml-lé alakítani. Nem sikerült 😦

Szerencsétlen Expression Designnak volt pofája PNG fájlként kimenteni, majd a XAML-be egy Image taget tenni. Noooooormális?

Így nem volt más hátra, nekem kellett rajzolnom. Szerencsére Buck Wilson oldalán találtam egy Photoshop tutorialt, csak ugyanazt kellett Expressionben végigkattintgatnom.

Kezdjük egy keret nélküli, lekerekített négyzettel:

    <Rectangle x:Name="background" Width="180" Height="180" 
RadiusX
="30" RadiusY="30" Fill="#FF0677D5" StrokeThickness="0" />

iPhone_background

Az alsó színátmenethez a háttérre rákerült egy ugyanekkora négyzet, átlátszóba tűnő színátmenettel:

    <Rectangle x:Name="underglow" Width="180" Height="180" 
Stroke
="#FF000000" RadiusX="30" RadiusY="30" StrokeThickness="0"> <Rectangle.Fill> <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0"> <GradientStop Color="#00FFFFFF" Offset="0.7"/> <GradientStop Color="#B2FFFFFF" Offset="1"/> </LinearGradientBrush> </Rectangle.Fill> </Rectangle>

iPhone_underglowA felső részhez lemásoltam a négyzetet Blendben, majd rárajzoltam egy elliszist és vettem a két objektum metszetét az Intersect menüpont segítségével. Így lett egy alulról íves, felülről lekerekített Path objektumom, amit színátmenettel tudtam kitölteni:

    <Path x:Name="topglare" Height="93.5" Margin="10,10,10,96" 
Stretch
="Fill" Stroke="#FF000000" StrokeThickness="0" Data="..."> <Path.Fill> <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0"> <GradientStop Color="#B2FFFFFF"/> <GradientStop Color="#4CFFFFFF" Offset="1"/> </LinearGradientBrush> </Path.Fill> </Path>iPhone_topglare

Sokat kísérleteztem a szép árnyékkal, végül több körvonallal sikerült megoldani:

    <Canvas x:Name="shadow" Margin="6, 7, 0, 0">
        <Border CornerRadius="30" Canvas.Left="4" Canvas.Top="4" Width="180" Height="180" 
BorderThickness
="1" BorderBrush="Black" Opacity="0.50" /> <Border CornerRadius="31" Canvas.Left="3" Canvas.Top="3" Width="182" Height="182"
BorderThickness
="1" BorderBrush="Black" Opacity="0.40" /> <Border CornerRadius="32" Canvas.Left="2" Canvas.Top="2" Width="184" Height="184"
BorderThickness
="1" BorderBrush="Black" Opacity="0.20" /> <Border CornerRadius="33" Canvas.Left="1" Canvas.Top="1" Width="186" Height="186"
BorderThickness
="1" BorderBrush="Black" Opacity="0.10" /> </Canvas>iPhone_shadow

Ezzel a gomb lényegében elkészült, már csak egy nyilat akartam rárajzolni. Ehhez rajzoltam egy négyzetet, elforgattam 45 fokkal, hogy a sarkán álljon, majd elmetszettem egy négyzettel. Így lett egy csúcsán álló háromszögem, amit csak hozzá kellett ragasztanom egy téglalaphoz és kész is lett a nyilat leíró Path:

    <Path x:Name="arrow" Fill="#FFFFFFFF" Stretch="Fill" Stroke="#FF0677D5" StrokeThickness="4" 
Data
="..." Height="94.641" Margin="0,25.479,-8.949,79.521"
RenderTransformOrigin
="0.251,0.202"
d
:LayoutOverrides="Height" Width="95" HorizontalAlignment="Right"> <Path.RenderTransform> <TransformGroup> <RotateTransform Angle="45"/> <TranslateTransform X="-43.27" Y="23.665"/> </TransformGroup> </Path.RenderTransform> </Path> iPhone_arrow

A nyíl vastag körvonalat kapott (StrokeThickness=”4”) és olyan körvonal színt, mint a háttér. Ha más színű gombot szeretnék, csak a #FF0677D5 színt kell másikra cserélni.

A tapasztalatom az, hogy ha az ember tudja, mit akar rajzolni, egészen jól lehet az Expression Blendben boldogulni. A generált Path objektumokat viszont fehér ember biztosan nem fogja kódból módosítani Visual Studioban.

Akinek épp ilyen gombra van szüksége, letöltheti a teljes XAML fájlt.

Advertisements

Kommunikáció ASP.NET és Silverlight között

Mostanában divat azon vitatkozni, hogy az ASP.NET vagy a Silverlight-e a jövő webfejlesztő technológiája. Különösen az utóbbi hívei között vannak olyanok, akik szeretik azt hinni, hogy kis kedvencük minden helyzetben tökéletes választás. Szerintem a két technológiát együtt fogjuk használni a jövőben: amit nem lehet vagy nem célszerű a böngészőben megoldani, ott fogunk a böngésző bővítményhez folyamodni. Ehhez persze nélkülözhetetlen, hogy a két világ tudjon egymással kommunikálni.

Silverlight alkalmazás inicializálása ASP.NET-ből

Egy Silverlightos alkalmazásnak induláskor adatokat adhatunk át az initParams paraméterben. Egyetlen stringben, vesszővel elválasztva kell felsorolnunk az átadandó kulcs-érték párokat.

HTML:

    <object data="data:application/x-silverlight-2," ...>
        <param name="source" value="ClientBin/SilverlightApplet.xap"/>
        <param name="initParams" value="p1=Első paraméter,p2=Második paraméter" />
        ...
    </object>

ASP.NET-ben a beágyazó asp:Silverlight vezérlő InitParameters tulajdonságát kell használnunk akár code behindból, akár ASPX markupból:

    <asp:Silverlight ID="slPlugin" runat="server" Source="~/ClientBin/SilverlightApplet.xap"
        MinimumVersion="2.0.31005.0" Width="100%" Height="100%"
        InitParameters="p1=Első paraméter,p2=Második paraméter" />

Az így átadott paraméterek Silverlightban az App.xaml.cs fájlban lévő Application_Startup metódus StartupEventArgs e paraméterében érkeznek meg egy szótár típusú változóban. Ha nem csak itt akarjuk elérni, akkor szerintem érdemes kitenni statikus változóba:

    // Silverlight: 
public partial class App : Application { internal static IDictionary<string, string> InitParams; private void Application_Startup( object sender, StartupEventArgs e ) { App.InitParams = e.InitParams; this.RootVisual = new Page(); }
}

Ez persze bárhonnan elérhető a Silverlight alkalmazáson belül:

    // Silverlight: A bemenő paramétereket vesszővel kell elválasztani, különben KeyNotFoundException jön.
    this.lblInitParams.Text = String.Format( CultureInfo.InvariantCulture, 
        "Param1={0}, Param2={1}", App.InitParams[ "p1" ], App.InitParams[ "p2" ] );

Érték átadása a weboldalról

Az ASP.NET és a Silverlight együttélésének a kulcsa a Silverlight HTML Bridge nevű komponense, aminek segítségével felügyelt kódból érhetjük el a böngészőben futó oldalt, illetve a felügyelt kódunk bizonyos részeit tehetjük böngészőből elérhetővé. Ahhoz, hogy a weboldalról adatot tudjunk átadni egy Silverlight alkalmazásnak, egy felügyelt metódust kell publikálnunk, melyet majd JavaScriptből hívunk meg. A kiválasztott metódus elé a [ScriptableMember] attribútumot kell biggyesztenünk. Ha a metódust más néven akarjuk szkriptből meghívni, használhatjuk az attribútum ScriptAlias tulajdonságát. Ha egy osztály összes metódusát publikálni szeretnénk, akkor az osztály elé tehetjük a [ScriptableType] attribútumot.

    // Silverlight
    // [ScriptableType]
    public partial class Page : UserControl
    {
        public Page()
        {
            InitializeComponent();
            HtmlPage.RegisterScriptableObject( "MyScriptableType", this );
        }

        [ScriptableMember]
        public string SayHello( string name )
        {
            this.lblMessageIn.Text = name;
            return "Szia " + name;
        }
}

A következő lépés a HtmlPage.RegisterScriptableObject meghívása. Az első paraméterben tetszőleges sztringet megadhatunk, ilyen néven lesz elérhető a második paraméterben megadott objektumunk JavaScriptből.

A példában egy HTML szövegdoboz értékét adjuk át gombnyomásra a fenti SayHello metódusnak, ami az slPlugin azonosítójú asp:Silverlight vezérlőben fut:

    <!-- ASPX -->
<asp:ScriptManager runat="server" />

    <input type="text" id="txtName" />
    <input type="button" value="Küldés" onclick="sendToSilverlight()" />
    <script type="text/javascript" language="javascript">
        function sendToSilverlight()
        {
            var slPlugin = $get( '<%= this.slPlugin.ClientID %>' );
            var txtName = $get( 'txtName' );
            var result = slPlugin.Content.MyScriptableType.SayHello( txtName.value );
            alert( 'Válasz: ' + result );
        }
    </script>

A JavaScript írásakor ne várjunk az IntelliSensre, nem lesz.

Érték átadása a weboldalnak

Silverlightból adhatunk át adatokat a weboldalnak, a HTML Bridge segítségével ugyanis gyakorlatilag a teljes DOM-ot kezelhetjük felügyelt kódból. (Na ezt kellene valakinek megírnia egy kicsit típusosabban ASP.NET-ben…) Arra kell csak figyelni, hogy a Silverlight pluginon vagy az őt tartalmazó div elemen ne legyen display:none vagy visibility:hidden. Szépen is néznénk ki, ha láthatatlan vezérlők rángathatnák a weboldalunkat 🙂

Íme az ASPX oldalunknak az a része, amely fogadni fogja az adatot a Silverlight alkalmazástól:

    Fogadott: <span id="lblName">(még nem jött semmi)</span>

Silverlight oldalon faragtam egy mini űrlapot:

    <StackPanel Orientation="Horizontal">
        <TextBlock Text="Küldendő üzenet: " FontWeight="Bold" VerticalAlignment="Center" />
        <TextBox x:Name="txtMessageOut" Width="100" />
        <Button x:Name="btnSend" Content="Küldés" Click="btnSend_Click" />
    </StackPanel>

A lényeg persze a gomb eseménykezelője:

    // Silverlight 
private void btnSend_Click( object sender, RoutedEventArgs e ) { HtmlDocument doc = HtmlPage.Document; HtmlElement lblName = doc.GetElementById( "lblName" ); lblName.SetAttribute( "innerHTML", this.txtMessageOut.Text ); }

Weboldal esemény kezelése Silverlightban

Arra is van lehetőségünk, hogy felügyelt kódban kezeljük egy HTML DOM objektum valamely eseményét, ráadásul ehhez nem kell JavaScriptet írni. Készíthetünk például egy combo boxot a weblapunkra:

    <!-- HTML / ASPX -->
    <select id="selWelcome">
        <option>Szia</option>
        <option>Helló</option>
        <optiondv</option>
    </select>

A select objektumnak van egy changed eseménye, amire feliratkozhatunk Silverlightból:

    // Silverlight: feliratkozás weblap esem?nyre
    HtmlDocument doc = HtmlPage.Document;
    HtmlElement selWelcome = doc.GetElementById( "selWelcome" );
    selWelcome.AttachEvent( "onchange", new EventHandler<HtmlEventArgs>( this.OnWelcomeChanged ) );

Sajnos itt sem lesz IntelliSense az eseménykezelő megírásához, ezért jó tudni, hogy létezik egy HtmlEventArgs paraméter típus:

    private void OnWelcomeChanged( object sender, HtmlEventArgs e )
    {
        HtmlElement selWelcome = sender as HtmlElement;

        string selection = String.Empty;
        foreach( HtmlElement option in selWelcome.Children )
        {
            object selectedProperty = option.GetProperty( "selected" );

            if( selectedProperty != null )
            {
                if( selectedProperty.ToString().Equals( "true", StringComparison.OrdinalIgnoreCase ) )
                {
                    selection = option.GetProperty( "innerHTML" ).ToString();
                }
            }
        }
        MessageBox.Show( "Ezt választottad az oldalon: " + selection );
    }

A fenti kódból talán látszik, hogy a HTML Bridge az összes HTML elemet egyetlen HtmlElement osztályra képezi le. Ez persze nem rossz, de most éppen kicsit nehézkes megkeresni a kiválasztott gyermekelemet. Persze bevethetünk egy kis LINQ-et 🙂

    string selection = ( from HtmlElement option in selWelcome.Children
                         let o = option.GetProperty( "selected" )
                         where
                           p != null &&
                           p.ToString().Equals( "true", StringComparison.OrdinalIgnoreCase )
                         select option.GetProperty( "innerHTML" ).ToString()
).First();

A felhasznált osztályok a System.Windows.Browser névtérben találhatóak. Érdemes ott körülnézni, van ott még más hasznos típus is…

A cikkhez tartozó forráskód letölthető: HtmlBridgeSampleSolution.zip (549 kB)

Javaval települ a Silverlight, ez már a vég?

Épp Javat telepítek a böngészőbe és nem hiszek a szememnek: jön vele a Silverlight! Pontosabban telepíthetjük vele az MSN Toolbart, aminek pedig az az érdekessége, hogy teljesen Silverlight alapú, azaz amikor az MSN Toolbart telepítem, települ a Silverlight is.

Java Setup: MSN Toolbar

Az MSN Toolbar egész felhasználói felülete valójában XAML, a böngésző shell pedig kontrollként hosztolja a Silverlightot. Magyarul akár az MSN Toolbart, akár a JRE-t telepíti valaki a gépére, lesz a gépén Silverlight 2 is. Ez a tény valahogy kimaradt a press release-ből 🙂 Gondolom a Sun annyira nem rajongott az ötletért, ezért az ily módon települő Silverlightot csak az MSN Toolbar tudja használni, tehát ha kellene a böngésző plugin is, akkor a felhasználónak külön kell telepítenie a Silverlightot (ismét) 😦

Egyébként, csak hogy egy kicsit a jövőbe nézzünk, hamarosan az összes Live kliens alkalmazás is alapértelmezés szerint telepíteni fogja a Silverlight 2-t (persze out-out lesz). Scott novemberben még azt írta, hogy az interneten most minden negyedik gépen van Silverlight, de úgy látom nagyon dolgoznak rajta, hogy ez az arány jobb legyen 🙂

Technorati Tags: ,,,