2009-04-13 11 views
2

Ich habe ein sehr großes Bild, das ich gerne für Sprite-Techniken verwenden würde (à la css image sprites).Wie funktioniert Silverlight Image Clipping?

Ich habe den Code unten bekam:

<Image x:Name="testImage" Width="24" Height="12" Source="../Resources/Images/sprites.png"> 
    <Image.Clip> 
     <RectangleGeometry Rect="258,10632,24,12" /> 
    </Image.Clip> 
</Image> 

Diese Clips die Bildquelle an der relativen Position 258, 10632 in dem Quellbild in 24x12.

Das Problem ist, dass das beschnittene Bild im testImage bei 0,0 angezeigt werden soll, während es bei 258, 10632 angezeigt wird. Es verwendet die Geometrie als Schnittführung, aber auch als Layouthilfe.

Hat jemand eine Idee, wie das gemacht werden sollte? wenn überhaupt.

Fazit: Es scheint derzeit keine gute Möglichkeit, dies zu tun, Graeme Lösung scheint dies zu erreichen, mit Silverlight 2.0 in der Nähe zu sein.

Das gesagt, wenn jemand eine bessere Möglichkeit weiß, dies zu tun, bitte antworten Sie mit einer Antwort.

Antwort

3

Es stellt sich heraus, dass dies getan werden kann.

<Rectangle x:Name="myRect" Width="28" Height="12" /> 

ImageBrush imageBrush = new ImageBrush(); 
imageBrush.ImageSource = //Load in image source 
imageBrush.Stretch = Stretch.None; 
imageBrush.AlignmentX = AlignmentX.Left; 
imageBrush.AlignmentY = AlignmentY.Top; 

TranslateTransform offsetTransform = new TranslateTransform(); 
offsetTransform.X = -258; 
offsetTransform.Y = -10632; 

imageBrush.Transform = offsetTransform; 
1

Angenommen, Sie sind auf einer Leinwand

<Image x:Name="testImage" Width="24" Height="12" Canvas.Left="-258" Canvas.Top="-10632" Source="../Resources/Images/sprites.png"> 
<Image.Clip> 
    <RectangleGeometry Rect="258,10632,24,12" /> 
</Image.Clip> 

Mit WPF Sie eine CroppedBitmap verwenden würde, aber leider nicht in Silverlight nicht existiert.

< Bearbeiten>

Mit weiteren Experimenten wurde eine Lösung ohne eine Leinwand mit:

<Image x:Name="testImage" Width="24" Height="12" Source="../Resources/Images/sprites.png"> 
    <Image.Clip> 
     <RectangleGeometry Rect="258,10632,24,12" /> 
    </Image.Clip> 
    <Image.RenderTransform> 
     <TranslateTransform X="-258" Y="10632"/> 
    </Image.RenderTransform> 
</Image> 

Es ist nur etwas sauberere die gleiche Sache wie die Leinwand zu tun.

+0

Ich mag, wo Sie hier gehen, aber die Bildbreite bis 24 versteckt der Inhalt zu ändern.Ändern der Breite bei allen Änderungen, welches Bit des Originalbildes angezeigt wird. –

+0

Ich könnte die Breite und Höhe als die ursprüngliche Breite = "800" Höhe = "18928" lassen aber ist das der richtige Weg, es zu tun? –

+0

Das Problem ist, dass Silverlight das, was Sie versuchen, noch nicht unterstützt. CroppedBitmap ist der richtige Weg, aber leider nur in WPF vorhanden. Also, es sei denn, Sie öffnen Reflektor und implementieren es selbst, Sie sind mit der Einschränkung der Bild –

1

Warum das alles zu tun, ist der ganze Sinn von CSS Image Sprites, indem eine Anfrage an Stelle von vielen Downloadzeit zu verbessern. Aber Sie können dasselbe erreichen, indem Sie alle Ihre Bilder in ein xap (oder das xap) setzen und sie in einer Anfrage herunterladen.

+0

Das Problem, das ich wahrnehme, ist mehr das Laden einer Vielzahl von Bildern, anstatt ein einziges Bild zu verwenden, das * hoffentlich * Silverlight intern die Leistung von. Optimieren wird. –

+1

Ich würde wetten, dass Sie tatsächlich eine höhere Speichernutzung und schlechtere Leistung dabei bekommen. Es sei denn, Sie haben tatsächlich einen nachgewiesenen Engpass UND Messungen, die diese "Optimierung" zeigen, können die Dinge verbessern (was in beiden Fällen wie Nein klingt), dann verschwenden Sie Ihre Zeit UND verringern die Qualität von was auch immer Sie arbeiten. –

1

Das ist völlig machbar - die Lösung negativen Margen anstatt Transformationen zu verwenden. Legen Sie einfach einen negativen Rand oben und links fest, um den Offset des Clips oben/links aufzufressen (in Ihrem Beispiel 258.10632). Negative Ränder werden auch rechts und unten benötigt, um den Rest des Quellbildes aufzufressen; die Formel für den rechten Rand ist:

-1 * (width_of_source - x_coord_of_clip - width_of_clip_region)