PDA

Просмотр полной версии : Формула расчета х-координаты перемещения элементов горизонтального меню


Kuruki
29.05.2009, 18:03
Привет!
Сделал менюшку, в которой элементы передвигаются горизонтально относительно мыши
import mx.transitions.easing.Regular;
import gs.*;

var imagesAmount:Number = 30; // Кол-во картинок
var imageWidth:Number = 145; // Ширина картинки

var spaceWidth:Number = 10; // Ширина пробела

this.createEmptyMovieClip("nav_mc", this.getNextHighestDepth());
this.nav_mc._y = 6;

for (var counter:Number = 1; counter <= imagesAmount; counter++)
{
this.nav_mc.attachMovie("image", "image" + counter, this.nav_mc.getNextHighestDepth());
this.nav_mc["image" + counter]._x = (counter - 1) * (imageWidth + spaceWidth);
this.nav_mc["image" + counter]._txt.text = counter;
}

this.onMouseMove = moveNav;

function moveNav():Void
{
// Макс _х. При котором становится виден последний элемент
var xMax:Number = -(this.nav_mc._width - Stage.width);

// Коэффициент.
// Когда мышка в правом углу (к = 1) полностью виден последний элемент
// Когда в левом углу (к = 0) полностью виден первый элемент
var k:Number = _root._xmouse / Stage.width;

var nextX:Number = xMax * k;

TweenMax.to(this.nav_mc, 1, {_x: nextX, ease: Regular.easeOut});
updateAfterEvent();
}
Все работает правильно, но есть неудобство: чтобы полностью увидеть первый или последний элементы, нужно переместить мышь до конца влево или вправо соответственно. Я хочу сделать немного поменьше "ход" мыши, скажем на 20 пикселей справа и слева, но при этом, чтобы на координате 20 и Stage.width-20 был уже полностью виден первый или последний элемент соответственно, и еще при этом независимо от кол-ва элементов, в чем вся сложность.

Пробовал прибавлять 20 увеличивать и уменьшать на 20 координату элементов, когда мышь соответственно левее/правее центра, но такой вариант не устраивает, т.к. когда мышь проходит центр будет наблюдаться резкий скачок элементов.
Пробовал делать отступы у nav_mc справа и слева, но не могу рассчитать ширину этого отступа, т.к. он зависит от кол-ва картинок.
Как его рассчитать или есть другие варианты?

Волгоградец
29.05.2009, 19:01
Попробуй так, если я правильно понял:
var xMax:Number = -(this.nav_mc._width - (Stage.width - 200));
var k:Number = + _root._xmouse / Stage.width;
var nextX:Number = xMax * k + 100;
Еще надо условие поставить, а то сильно выдвигаются менюшки.

Kuruki
29.05.2009, 19:22
Как раз с условием и будут проблемы, т.к. ход мыши зависит от ширины клипа и при различных количествах картинок, _xmouse, при котором полностью будет виден первый/последний элемент, будет разный

UPD: попробую еще вот так объяснить чего я хочу: чтобы независимо от кол-ва картинок на _xmouse, равном 20 был полностью виден первый элемент и при _xmouse, равном stagewidth-20 был полностью видим последний

Волгоградец
29.05.2009, 19:33
Ага, я ересь написал, каюсь.
Вот так работает:
var xMax:Number = -(this.nav_mc._width - (Stage.width));

var k:Number = _root._xmouse / Stage.width / 0.94 - 0.03;

var nextX:Number = xMax * k;
if(nextX > 0){
nextX = 0;
}else if(nextX < xMax){
nextX = xMax
}

Kuruki
29.05.2009, 20:00
Нее, всеравно отступы разные получаются. При 6 картинках его вообще практически нет. Тут в ручную не подберешь, все от ширины клипа зависит

UPD Вот, сделал!import mx.transitions.easing.Regular;
import gs.*;

var imagesAmount:Number = 30; // Кол-во картинок
var imageWidth:Number = 145; // Ширина картинки

var spacesAmount:Number = imagesAmount - 1; // Количество пробелов между картинками
var spaceWidth:Number = 10; // Ширина одного пробела

var clipWidth:Number = imagesAmount * imageWidth + spacesAmount * spaceWidth;

var rate:Number = clipWidth / Stage.width; // На такое расстояние смещается клип при передвижении мыши на 1 пикс

var offset:Number = 20 * rate; // Считаем расстояние, на которое нужно увеличить клип справа и слева
// правда отступ получится при этом не ровно 20, т.к. ширину клипа мы считали без него
// но зато при любой ширине клипа он будет одинаковым!

this.createEmptyMovieClip("nav_mc", this.getNextHighestDepth());
this.nav_mc._y = 6;

for (var counter:Number = 1; counter <= imagesAmount; counter++)
{
this.nav_mc.attachMovie("image", "image" + counter, this.nav_mc.getNextHighestDepth());
this.nav_mc["image" + counter]._x = offset + (counter - 1) * (imageWidth + spaceWidth);
this.nav_mc["image" + counter]._txt.text = counter;
}
// это чтобы считывалась нужная нам ширина
this.nav_mc.lineTo(1, 0);
this.nav_mc.moveTo(this.nav_mc._width + offset, 0);
this.nav_mc.lineTo(this.nav_mc._width + offset - 1, 0);

this.nav_mc._x = 18 - offset;

this.onMouseMove = moveNav;

function moveNav():Void
{
// Макс _х. При котором становится виден последний элемент
var xMax:Number = -(this.nav_mc._width - Stage.width);

// Коэффициент.
// Когда мышка в правом углу (к = 1) полностью виден последний элемент
// Когда в левом углу (к = 0) полностью виден первый элемент
var k:Number = _root._xmouse / Stage.width;

var nextX:Number = xMax * k;

if(_root._xmouse > 18 && _root._xmouse < Stage.width - 18)
{
TweenMax.to(this.nav_mc, 1, {_x: nextX, ease: Regular.easeOut});
updateAfterEvent();
}
}