четверг, 27 декабря 2007 г.

startDrag() область перемещения.

Если нужно заставить Display Object таскаться мышкой не по всей области плеера, а только по горизонтали (или вертикали)

var rec:Rectangle = new Rectangle(x, 0, width, 0);
this.startDrag(false, rec);

Фотошоп на Flex-е

Просто нет слов...
В полном улете
splashup.com

среда, 26 декабря 2007 г.

Video. Camera. NetStream. Настройка

Посмотрим, что же изменилось в тройке по работе с вебкамерой?

Создаю два файла в ТоталКомандере (Shift+F4) try_Camera_and_NetConnection.fla, затем Alt+F4 затем навожу рамку выбора на уже созданный файл, снова Shift+F4, нужно только в поле ввода имени файла автоматически подставляется имя выбранного файла, поэтому чтобы создать файл с таким же именем, но расширением .as нужно исправить только расширение.
Есть два пустых файла: try_Camera_and_NetConnection.fla и Try_Camera_and_NetConnection.as. Жму на первый запускается Flash CS3, второй перетаскиваю во FlashDevelop. Во флэше пишу в поле Document Class: Try_Camera_and_NetConnection. Все. Можно писать код.

Наверняка не самый "прямой" способ -), но, надеюсь, и не самый корявый. Делайте скидку на то что многие флешеры не программисты изначально.

В файле .as пишу шапку. Множно конечно сгенерить ее, но пока мне доставляет удовольствие писать все ручками (используя подсказки редактора - кайф!). Еще заметил, что как только начинаю копипастить, то появляются ошибки которые долго искать. Для себя решил что буду писать все руками, пусть это медленне, но экономится много времени на меньшем количестве ошибок. Да и чувство какое-то от такого кода другое... большего контроля, что ли.

Итак шапка:

package {
public class Try_Camera_and_NetConnection extends Sprite {
import flash.display.Sprite;
public function Try_Camera_and_NetConnection() {

}
}
}


Создаю объект Camera:

package {
import flash.display.Sprite;
import flash.media.Camera;
public class Try_Camera_and_NetConnection extends Sprite {

private var cam:Camera;

public function Try_Camera_and_NetConnection() {
this.cam = new Camera.getCamera();
}
}
}

Ага, непривычно, раньше было просто Camera.get();

Добавлю два экзэмпляра класса Video. В одном будет видео с камеры, в другом поток с Red5 сервера.

private var cameraVideo:Video;
private var inVideo:Video;
...
this.cameraVideo = new Video(160,120);
addChild(cameraVideo);


* * *

Принцип понятен, опустим несколько шагов. Вот результат:

package {
import flash.display.Sprite;
import flash.events.Event;
import flash.events.EventDispatcher;
import flash.events.MouseEvent;
import flash.events.NetStatusEvent;
import flash.events.SecurityErrorEvent;
import flash.media.Camera;
import flash.media.Video;
import flash.net.NetConnection;
import flash.net.NetStream;
import flash.text.TextField;
import flash.text.TextFieldAutoSize;


public class Try_Camera_and_NetConnection extends Sprite {

private var nc:NetConnection;
private var txt:TextField;
private var cameraVideo:Video;
private var inVideo:Video;
private var cam:Camera;

private var outNS:NetStream;
private var inNS:NetStream;

function Try_Camera_and_NetConnection() {
this.nc = new NetConnection();
this.nc.connect("rtmp://127.0.0.1:1935/SOSample");
this.nc.addEventListener(NetStatusEvent.NET_STATUS, onStatus);

txt = new TextField();
txt.autoSize = TextFieldAutoSize.CENTER;
txt.x = 100;
txt.y = 100;
addChild(txt);

this.cam = Camera.getCamera();

cam.setQuality(6000, 90);
cam.setMode(320, 240, 15);

this.cameraVideo = new Video(160,120);
addChild(cameraVideo);
cameraVideo.attachCamera(cam);

}

private function onStatus(e:NetStatusEvent) {
trace(e.info.code);
txt.text = e.info.code;
this.outNS = new NetStream(this.nc);
this.outNS.attachCamera(cam);
this.outNS.publish("first", "live");

this.inNS = new NetStream(nc);
this.inNS.play("first");

this.inVideo = new Video(32,240);
addChild(inVideo);
inVideo.x = 320;
inVideo.attachNetStream(inNS);
inVideo.width = 150;
inVideo.height = 150;
}
}
}

Для того чтобы запустить сервер достаточно скачать установить и запустить щелкнув по ярлычку.

Итак, что же получилось? Два видеоокна. В одном видео с камеры, в другом видео с камеры упакованное в видеопоток отпраленное на сервер и снова назад клиенту.

У класса Camera есть два важных метода:

Camera.setMode();
Camera.setQuality();


Продолжение см часть 2. TODO

вторник, 25 декабря 2007 г.

Война со смайлами в чате. Часть II

Немного поднаторев в текстфиелдных вопросах снова берусь за смайлики.
Приятный сюрприз, если использовать свойство htmlText и гарнитуру, размер и цвет задавать тегами, то глюка описанного ранее не происходит.
Ура, все хорошо, жизнь прекрасна.

Начинаю тестить с большими кусками текста, после какого-то n-нного раза (n все время разное) при смене размера и/или гарнитуры шрифта плеер падает. Падают все имеющиеся девятые плееры у меня на компе. Причем браюзер падает вместе с плагином. Раааз и вместо флэша или мозиллы только окошко: "Обнаружена ошибка. Приложение будет закрыто"
Даже если у меня код кривой флеш не должен падать!
Должен ругаться!

Будем копать дальше.

Война со смайлами в чате. Часть I

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

На картинках видно, что при выделении куска текста меняется гарнитура и размер текста.

понедельник, 24 декабря 2007 г.

Заработал дебаггер в CS3

После установки Flash Pro CS3 дебаггер работал наполовину: код пошагово дебажит, а плеер не запускается.
Помогла установка flash player debug version

Хронология развития компании Adobe

http://www.adobe.com/aboutadobe/history/timeline/index.html
... Фотошоп планировался как плагин к иллюстратору...

Неумный компилятор

Уже не первый раз вводит меня (и не только -))в ступор от полного не понимания флешовый компилятор своими сообщениями об ошибках.
Пишу

new SomeClass();

Компилятор ругается:
ReferenceError: Error #1065: Variable SomeClass is not defined.

Ну и ну! SomeClass значит теперь в переменные у нас записан. А я всегда считал, что с ключевым словом new только имя класcа можно употреблять. Можно конечно возражать, что имя класса это переменная ссылающаяся на объект класса Class, но сообщения об ошибках для того и нужны чтобы быстро коротко и ясно описать проблему. А код ошибки это для стандартизации и подробного описания возможных причин.

Так что такой Error расцениваю как преднамеренное введение в заблуждение.
Доходчивее должен быть смысл изложен.
-)

Аттач мувика из либы по его linkage ID

В AS3 нет такого понятия как linkage ID. Линкейдж устанавливает связь графического объекта с классом. Если такого класса нет, то флэш создаст пустой класс с именем символа при компиляции.

Начинаю я переходить на тройку с AS2 и почти сразу сталкиваюсь с проблемой: Как приаттачить мувик если есть его имя (а фактически имя класса мувика) в виде строки?

Покумекав и поспрашав получился такой солюшн

public static function getSymbolClone(symbolName:String):*
{
return duplicate(symbolName);
function duplicate (className:String):*
{
var currentClass:Class = Class(getDefinitionByName(className));
return new currentClass();
}
}



Со временем AS3 начинает потихоньку вправлять мозги своей строгостью и ООПностью
(по сравнению с раздолбайской двойкой) и необходимость в таких извращения просто отпадает.

воскресенье, 23 декабря 2007 г.

Event Flow

В AS3 вводится новый подход для работы с событиями. "Поток событий" (event flow)
определен только для видимых объектов, находящихся в display list.
У потока выделяют три стадии. Данный код демонстрирует 3 стадию (bubbling)


package {
import flash.display.Sprite;
import flash.events.MouseEvent;
import flash.display.StageScaleMode;
import flash.display.StageAlign;

public class Test extends Sprite {

private var _rectangle:Sprite;
private var _circle:Sprite;
public function Test() {

stage.scaleMode = StageScaleMode.NO_SCALE;
stage.align = StageAlign.TOP_LEFT;

_rectangle = new Sprite();
_rectangle.graphics.lineStyle(0, 0, 0);
_rectangle.graphics.beginFill(0x0000FF, 1);
_rectangle.graphics.drawRect(0, 0, 100, 50);
_rectangle.graphics.endFill();
addChild(_rectangle);

_circle = new Sprite();
_circle.graphics.lineStyle(0, 0, 0);
_circle.graphics.beginFill(0x0000FF, 1);
_circle.graphics.drawCircle(0, 0, 50);
_circle.graphics.endFill();
_circle.x = 100;
_circle.y = 100;
addChild(_circle);

addEventListener(MouseEvent.CLICK, onClick);

}

public function onClick(event:MouseEvent):void {
event.target.x = Math.random() * 400;
event.target.y = Math.random() * 400;
}
}
}