Полноэкранное фоновое изображение с Flex - PullRequest
1 голос
/ 04 февраля 2010

Я хочу загрузить изображение на задний план моего приложения Flex. Однако меня интересует несколько вещей, и у меня есть несколько ограничений.

Я хочу, чтобы это было очень похоже на то, как это делается с CSS. Посмотрите этот пример полноэкранных фоновых изображений с CSS .

Очень важно, чтобы за изображением не было пустого пространства (цвет фона) и чтобы изображение не растягивалось. Это будет означать, что часть изображения будет обрезана. Это абсолютно нормально. На самом деле, первые пять пунктов в маркированном списке на связанной странице выше - это именно то, что мне нужно.

Я новичок в инфраструктуре Flex, но у меня хороший опыт работы с AS3. Так что я могу легко сделать это с помощью ActionScript, используя маску, stage.width / height, событие stage RESIZE и немного Math. Но мне интересно, каким будет «гибкий» способ сделать это?

Я не хочу сужать ответы, но буду ли я создавать свой собственный компонент, который расширяет canvas, который я оставлю позади всего своего другого контента? Или мне установить какое-то свойство приложения? Или что?

Спасибо.

Ответы [ 5 ]

2 голосов
/ 15 июля 2010

Вот пользовательский компонент, который заполнит любой прямоугольник изображением. Оно не будет растягивать изображение, если соотношение сторон прямоугольника не совпадает с изображением, и при этом оно не будет отображать пустое пространство, а скорее будет обрезать края изображения. Изображение будет масштабировано. Всегда хотя бы одно измерение будет заполнять прямоугольник на 100%, но другое измерение будет обрезано.

Это основано на UIComponent Flex, жизненном цикле компонента и Image.

ClippedImage.as

package com.preston.www.view.background.components {
import flash.events.Event;
import flash.geom.Rectangle;

import mx.controls.Image;
import mx.core.UIComponent;

//--------------------------------------
//  Events
//--------------------------------------

[Event(name="complete", type="flash.events.Event")]

public class ClippedImage extends UIComponent {

    //--------------------------------------------------------------------------
    //
    //  Constructor
    //
    //--------------------------------------------------------------------------

    public function ClippedImage() {
        image = new Image();
        image.addEventListener(Event.COMPLETE,image_completeHandler);
        addChild(image);
    }

    //--------------------------------------------------------------------------
    //
    //  Variables
    //
    //--------------------------------------------------------------------------

    private var image:Image;

    //--------------------------------------------------------------------------
    //
    //  Properties
    //
    //--------------------------------------------------------------------------

    //----------------------------------
    //  source
    //----------------------------------

    public function get source():Object {
        return image.source;
    }

    public function set source(value:Object):void {
        image.source = value;
    }

    //--------------------------------------------------------------------------
    //
    //  Overridden methods
    //
    //--------------------------------------------------------------------------

    override protected function updateDisplayList(unscaledWidth:Number, unscaledHeight:Number):void {
        super.updateDisplayList(unscaledWidth, unscaledHeight);

        var imageMeasuredWidth:Number = image.measuredWidth;
        var imageMeasuredHeight:Number = image.measuredHeight;
        var imageAspectRatio:Number = imageMeasuredWidth / imageMeasuredHeight;

        var imageWidth:Number;
        var imageHeight:Number;

        // try setting image according to width first
        imageWidth = unscaledWidth;
        imageHeight = imageWidth / imageAspectRatio;

        // if a gap exists vertically, set image according to height
        if (imageHeight < unscaledHeight) {
            imageHeight = unscaledHeight;
            imageWidth = imageAspectRatio * imageHeight;
        }

        image.setLayoutBoundsSize(imageWidth, imageHeight);

        // set image x and y
        var imagex:Number = (unscaledWidth - imageWidth) / 2;
        var imagey:Number = (unscaledHeight - imageHeight) / 2;

        image.setLayoutBoundsPosition(imagex, imagey);

        scrollRect = new Rectangle(0, 0, unscaledWidth, unscaledHeight);
    }

    //--------------------------------------------------------------------------
    //
    //  Event handlers
    //
    //--------------------------------------------------------------------------

    private function image_completeHandler(event:Event):void {
        dispatchEvent(event);
    }
}
}

Затем в вашем приложении вы просто установите тег mxml для этого компонента следующим образом:

<components:ClippedImage id="background" width="100%" height="100%"
                         source="assets/images/winery.jpg"/>
1 голос
/ 05 февраля 2010

По некоторым причинам вы не можете сделать это особенно легко во Flex.Вы можете использовать CSSSkin от Degrafa (http://www.degrafa.org/), чтобы сделать это, хотя, я уверен.

1 голос
/ 05 февраля 2010

Вероятно, есть один миллион способов снять шкуру с этой кошки. Один подход: в нашем приложении flex у нас есть холст позади нашего основного контейнера, как в

<mx:Canvas id="bgImg" width="1280" height="800" backgroundImage="assets/background.jpg" />
<containers:FlashContainer id="mainContainer">
<!-- HBoxs, VBoxes and loads of other components -->
</containers:FlashContainer>

Если хотите, вы можете привязать значения к ширине и высоте и отключить полосы прокрутки (чтобы они не всплывали, если изображение больше окна. Что-то вроде:

<mx:Canvas id="bgImg" width="{someVariable}" height="{someOtherVariable}" backgroundImage="assets/background.jpg" horizontalScrollPolicy="off" verticalScrollPolicy="off" />

Вы также можете поиграть со свойством styleName в сочетании с таблицей стилей и изменить другие свойства. Как в:

<mx:Style source="/mainStyle.css"/>
<mx:Canvas id="bgImg" styleName="bgStyle" width="{someVariableOrCalculationOrFunctionCall}" height="{someOtherVariableOrCalculationOrFunctionCall}" backgroundImage="assets/background.jpg" horizontalScrollPolicy="off" verticalScrollPolicy="off" />

Где mainStyle.css - это таблица стилей с целью вдоль линий:

.bgStyle
{
    styleName1: styleValue1;
    styleName2: styleValue2;
    styleName3: styleValue3;
}

Простите, я не знаю, какие стили можно задать на макушке, но их легко найти.

В нашем приложении размер окна фиксирован, и нашему фону никогда не нужно изменять размер. Но если бы это было так, я бы либо

1) привязать ширину / высоту холста к простому вычислению или 2) добавить слушателя, который реагирует на изменения размера событий и устанавливает связанные переменные width и height или 3) поэкспериментируйте с CSS на изображении холста и посмотрите, что я могу сделать

Примечание: чтобы создать привязываемую переменную, вы пишете что-то вроде

[Bindable]
var imageWidth:int;

или

Используйте тег <mx:Binding>

Надеюсь, все это поможет или, по крайней мере, укажет вам направление на помощь! -kg

1 голос
/ 04 февраля 2010

Несмотря на то, что это чистое решение as3, оно может направить вас в правильном направлении, но оно масштабирует изображение от его точки 0,0, но не составит труда изменить его в масштабе от центра.Вот код:

stage.align = "TL";
stage.scaleMode = "noScale";
// store original image size
var imgW:Number = img.width;
var imgH:Number = img.height;
// stage dimensions
var sW:Number = stage.stageWidth;
var sH:Number = stage.stageHeight;

resizer(null);
stage.addEventListener(Event.RESIZE, resizer);

private function resizer(e:Event):void
{
    // current stage dimension
    sW = stage.stageWidth;
    sH = stage.stageHeight;
    // check for proportions to make the resize based on right axis
    if ((sW / imgW) > (sH / imgH)) {
        img.width = sW;
        img.height = imgH * (img.width / imgW);
    } else {
        img.height = sH;
        img.width = imgW * (img.height / imgH);
    }
    // here you may want to deal with resize from center
    img.x = 0;
    img.y = 0;
}
0 голосов
/ 15 июля 2010

Вы пробовали

<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml"
    backgroundImage="@Embed(source='something.jpg')"
    backgroundAttachment="fixed" ...

Это должно поместить изображение something.jpg в фон без изменения размера. И эти "фоновые" свойства являются стилями, поэтому вы можете поместить их в css.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...