Показать сообщение отдельно
Старый 26.12.2013, 19:47
Ioangum вне форума Посмотреть профиль Отправить личное сообщение для Ioangum Найти все сообщения от Ioangum
  № 9  
Ответить с цитированием
Ioangum

Регистрация: Aug 2013
Адрес: Москва
Сообщений: 59
Может, я что-то не так делаю, но всё равно не то. Вот код основного класса Main:
Код AS3:
package  
{
	import flash.display.Sprite;
	import flash.geom.Point;
 
 
	public class Main extends Sprite
	{
		public var s:Space;
		public var stars:Vector.<Sprite> = new Vector.<Sprite>;
		private var s0: Star;
 
		private var pre_x:Number=0;
		private var pre_y:Number=0;
 
		public function Main() 
		{
			fillSky(1000, 800);
			s = new Space(500 - 700, 400 - 500); //Располагаем посередине. 700x500 - размер swf
			pre_x = s.x;
			pre_y = s.y;
			addChild(s);
		}
 
		private function fillSky(W:int, H:int) {
			//i - слой, j - звезда в слое
			//i=0 - слой, самый ближний к наблюдателю
			//j - звезда, размер выбирается рандомно в пределах слоя (внутри есть свойство dist = дальность {0..100})
			var sloy:Sprite;
			for (var i:int = 0; i < 10; i++) {
				sloy = new Sprite();
				for (var j:int = 0; j < 25; j++) {
					s0 = new Star(Math.random() * W, Math.random() * H, Math.random() * 10+i*10);
					sloy.addChild(s0);
				}
				stars.push(sloy);
				addChildAt(sloy,0);
			}
		}
 
		public function moveSky():void {
 
			//рассчитываем насколько сдвинулся Space
			var dx:Number = s.x-pre_x;
			var dy:Number = s.y - pre_y;
 
			//запоминаем положение Space для вычисления разницы
			pre_x = s.x;
			pre_y = s.y;
 
			//сдвигаем каждый слой соответственно его глубине
			for (var i:int = 0; i < stars.length; i++) {
				stars[i].x += dx / (10 - i +2); //по идее надо делать 10-i, но тогда при i=9 ,будет dx/1, что соответствует слою Space. А нужно сделать всё-таки чуть сзади
				stars[i].y += dy / (10 - i +2);
			}
 
		}
 
		public function scalePoint(target:Sprite, scaleX:Number, scaleY:Number, point:Point):void{
			var dXS:Number = (target.x - point.x) / target.scaleX;
			var dYS:Number = (target.y - point.y) / target.scaleY;
 
			target.scaleX = scaleX;
			target.scaleY = scaleY;
 
			target.x = point.x + dXS * target.scaleX;
			target.y = point.y + dYS * target.scaleY;
		}
 
		public function scaleSky(bigger:Boolean):void {
			var p:Point;
			for (var i:int = 0; i < stars.length; i++) {
				p = new Point(stage.stageWidth/2, stage.stageHeight/2);
				p = globalToLocal(p);
				scalePoint(stars[i], s.scaleX * (1 - 1 / (10 - i +2)), s.scaleY * (1 - 1 / (10 - i +2)), p);
			}
		}
 
	}
 
}
В классе Space ничего особенного: его можно таскать и увеличивать. Ну и всё. Но на всякий пожарный вот он:
Код AS3:
package  
{
	import flash.display.Sprite;
	import flash.events.Event;
	import flash.events.MouseEvent;
	import flash.geom.Point;
	import flash.geom.Rectangle;
 
	public class Space extends Sprite
	{
		public const GEN_W:int = 700; //horizontal size of swf file
		public const GEN_H:int = 500; //vertical size of swf file 
		public var WW:Number = 1000; //данные о начальной высоте спейса
		public var HH:Number = 800; //данные о начальной ширине спейса
		public var scale_f:Number = 1;
 
		private var droped:Boolean = false;
 
		public function Space(XX:int, YY:int) 
		{
			x = XX;
			y = YY;
 
			graphics.beginFill(0x000000,0.5);
			graphics.drawRect(0, 0, 1000, 800);
			graphics.endFill();
 
			graphics.beginFill(0x00FF00);
			graphics.drawCircle(400, 300, 100);
			graphics.endFill();
 
			graphics.beginFill(0x00FF00);
			graphics.drawCircle(200, 700, 50);
			graphics.endFill();
 
			addEventListener(MouseEvent.MOUSE_DOWN, onMDown);
			addEventListener(MouseEvent.MOUSE_UP, onMUp);
			addEventListener(MouseEvent.MOUSE_WHEEL, sScale);
			addEventListener(Event.ENTER_FRAME, EF);
		}
 
		private function onMDown(e:MouseEvent) {
			var dx:Number = WW-stage.stageWidth; 
				var dy:Number = HH-stage.stageHeight; 
				var dragRect:Rectangle = new Rectangle(-dx,-dy, dx,dy);
				startDrag(false, dragRect);
				droped = true;
		}
 
		private function onMUp(e:MouseEvent) {
			stopDrag();
			droped = false;
		}
 
		//изменение масштаба карты
		private function sScale(e:MouseEvent):void {
			var sc:Number = 0.95;
			var p = new Point(GEN_W/2, GEN_H/2);
			p = globalToLocal(p);
			if ((e.delta < 0) && (WW*sc>=GEN_W) && (HH*sc>=GEN_H)) {
				width *= sc;
				height *= sc;
				WW *= sc;
				HH *= sc;
 
				scale_f *= sc;
				(parent as Main).scaleSky(false);
			}
			else if ((e.delta > 0) && (scale_f<5)) {
				width /= sc;
				height /= sc;
				WW /= sc;
				HH /= sc;
 
				scale_f /= sc;
				(parent as Main).scaleSky(true);
			}
 
			p = localToGlobal(p);
			x += GEN_W/2 - p.x;
			y += GEN_H / 2 -p.y;
 
			if (x > 0) x = 0;
			if (y > 0) y = 0;
			if (x + WW < GEN_W) x = GEN_W - WW;
			if (y + HH < GEN_H) y = GEN_H - HH;
		}
 
		private function EF(e:Event) {
			if (droped) (parent as Main).moveSky();
		}
 
	}
 
}
Ну и класс Star - обычный шейп:
Код AS3:
package  
{
	import flash.display.Shape;
 
	public class Star extends Shape
	{
		public var dist:Number = 0; //0..100
		public var x0:int = 0;
		public var y0:int = 0;
 
		public function Star(X:Number, Y:Number, D: Number = 0)
		{
			dist = D;
			x0 = X;
			y0 = Y;
			x = X;
			y = Y;
			graphics.beginFill(0xFFFFFF);
			graphics.drawCircle(0, 0,D/100+0.01);
			graphics.endFill();
		}
 
	}
 
}
Вложения
Тип файла: swf Параллакс.swf (2.4 Кб, 96 просмотров)