Форум Flasher.ru

Форум Flasher.ru (http://www.flasher.ru/forum/index.php)
-   ActionScript 1.0/2.0 (http://www.flasher.ru/forum/forumdisplay.php?f=93)
-   -   заменить bitmap.getPixel(x, y) (http://www.flasher.ru/forum/showthread.php?t=105112)

bmg 07.12.2007 18:49

заменить bitmap.getPixel(x, y)
 
ребята подскажите, голова уже опухла.
Где то зациклился, не могу понять как работает: threshold()
Вычитал на форуме что threshold быстрее определяет цвет пикселя чем getPixel.

Сейчас сть картинка bitmap, черно-белая.
Требуется определить цвет каждого пиксела(белый или другой).
сейчас делаю циклы для перебора каждого пиксела:
Код:

bitmap.getPixel(xx, yy);
Помогите разобраться.
Возможно ли с помошью. threshold() выяснить белого ли цвета пиксель?
Как его правильно поставить в цикл, что бы он по пиксельно цвет показывал?

wvxvw 07.12.2007 21:56

это вобщем гвозди от разных стенок... а что в итоге нужно сделать?

bmg 07.12.2007 23:26

Вообще требуется, по пиксельно собрать MovieClip(640x960px).

Что бы передать через XMLSocket дальше(программе на C++).

В MovieClip'е текст и картинки, все черно белое, - они меняются пользователем - то есть динамичные.
и после этого требуется передать информацию о составленном в XML Socket(который работает, успешно).

Как мне определить цвет каждого пикселя в MovieClip?

Я делаю это так:
- создаю пустой bitmap, его запихиваю в контейнер, и потом кладу сверху свой MovieClip(при помощи draw()) - в результате у меня получается bitmap с моим рисунком.
После этого, я определяю в цикле, по пиксельно цвет каждого пиксела(нужно определить белый или другой-приравнивается к черному), при помощи getPixel(x,y), и заношу в переменную result += "0"; //или "1";

Когда картинка 640х960пикселей, то Flash v8, выдает надпись, типа: "скрипт тормознутый, закончить его?". И так 2-3 раза подряд. При этом времени занимает больше минуты.

olexandr 08.12.2007 01:08

разбить функцию определения цветов по onEnterFrame на несколько блоков
делал такое, только логику определения оптимального количества пикселей для одного фрейма сейчас не вспомню...

ну суть такая!

Molecula 08.12.2007 01:26

Код:

var _j=0;
while(_j<256)
{
_red= _bmp.threshold(_bmp, new Rectangle(0, 0, _bmp.width, _bmp._height), new Point(0, 0), ">", 16777216-65536*_j, 0xFF0000, 0xFF0000, false);//red
_green= _bmp.threshold(_bmp, new Rectangle(0, 0, _bmp.width, _bmp.height), new Point(0, 0), ">", 65536-255*_j, 0x00FF00, 0x00FF00, false);//green
_blue= _bmp.threshold(_bmp, new Rectangle(0, 0, _bmp.width, _bmp.height), new Point(0, 0), ">", 255-_j, 0x0000FF, 0x0000FF, false);//blue
_j++;
}

Returns
Number - The number of pixels that were changed.

Итого, мы получаем, сколько у нас Красных, Зеленных, Синих пикселей.
Так, можно построить гистограмму, как в Фотопопе.

Никаких онЕнтерФреймов!
Тут всего лишь 255 операций. Конечно, чем больше битмапдата, тем дольше вычисления.

Для черно-белого изображения, всё гораздо проще.
Вообще такие вещи, конечно лучше делать примерно, как тут - http://sephiroth.it/tutorials/flashP...php_bytearray/

bmg 08.12.2007 01:39

А что мне с этой гистограммой дальше делать?

Требуется получить строку(в байтах или стринг): 0010010100100...
где 0 белый(или прозрачный) цвет, а 1 черный (или отличный от белого)цвет.
Как на основе гистограммы это можно сделать ?

Molecula 08.12.2007 02:52

Цитата:

Вообще требуется, по пиксельно собрать MovieClip(640x960px).
Что бы передать через XMLSocket дальше(программе на C++).
Я не предлагаю, Вам строить гистограмму, я просто показал пример, как с помощью
Код:

threshold
получить значение пикселей определенного цветового диапазона.
Ссылка, которую я дал - есть хорошее начало для решения Вашей задачи.

Цитата:

Требуется получить строку(в байтах или стринг): 0010010100100...
ByteArray
из АС3 просто аж просится сюда, хотя, возможно, кто-то предложит что-то другое.

Для черного и белого:
Код:

_b = _bmp.threshold(_bmp, new Rectangle(0, 0, _bmp.width, _bmp.height), new Point(0, 0),"==", 0xFFFFFF, 0xFFFFFFFF, 0xFFFFFF, false);//b
_w = _bmp.threshold(_bmp, new Rectangle(0, 0, _bmp.width, _bmp.height), new Point(0, 0),"==", 0x000000, 0x00000000, 0xFFFFFF, false);//w

Вообще Ваша затея очень стрёмная и ресурсоемкая.
Вы представляете какой массив передадите?
640 * 960 =614400 этих нулей и едениц.

wvxvw 08.12.2007 06:37

зачем передавать массив, если на выходе получим двоичное число? %)
нужно всего лишь знать количество пикселов и результат их последовательного прибавления и сдвига вправо. (но все равно желательно разбить на части, а то очень большие числа получаются).
т.е. комбинация "10000" соответствует "f" (или 16).
строка из 640 черных пикселов, например, будет равна 4.56244061762219e+192 - не так уж и много как для передачи =)

ЗЫ. и все таки, я думаю, что treshold тут ни чем не поможет. Нужно попиксельно перебрать - значит getPixel(). onEnterFrame - вариант, еще вариант - в паблиш сеттингс изменить макимальное время отведенное на работу скрипта (дефолт - 15 сек).

bmg 08.12.2007 20:55

извините, за тупой вопрос, никогда не работал с onEnterFrame
Можно какой либо пример?

wvxvw 08.12.2007 21:58

Код:

import flash.display.BitmapData;
import flash.geom.Rectangle;
//
var __bmpd:BitmapData = new BitmapData(30, 30, false, 0);
__bmpd.fillRect(new Rectangle(5, 5, 20, 20),0xffffff);
var __mc:MovieClip = _root.createEmptyMovieClip("__mc", 0);
__mc.attachBitmap(__bmpd,0);
var r_arr:Array = [];
var j:Number = 0;
onEnterFrame = function ():Void {
        var i:Number = 0;
        var r_num:Number = 1;
        var base:Number = 1;
        while(i<30){
                r_num+=(base<<(__bmpd.getPixel(i,j)>0?0:1));
                base *=2;
                trace(i+" : "+(r_num ^ base).toString(2));
                i++;
        }
        r_arr.push(r_num ^ base);
        j++;
        if (j>30) {
                trace(r_arr);
                trace(r_arr[0].toString(2));
                trace(r_arr[6].toString(2));
                delete this.onEnterFrame;
        }
};

В примере создается картинка размером 30х30 пикселов и построчно заносится в массив. В результате чего получаем массив из 30 элементов, значение каждого из них можно представить в виде числа не большего, чем 2 в степени 30. На самом деле, я думаю, что такую операцию всю можно запихать в 1 онЕнтерФрейм, и таким образом (по 900 пикселов) записать всю картинку. Таким образом понадобится создать 683 массива (683 раза запустить онЕтерФрейм) при 25 фпс это примерно полминуты %)
Ну, не знаю... в принципе, терпимо %) Нужно еще поэксперементировать с сокетом, и как часто можно реально посылать инфу, возможно, можно все это и быстрее сделать =)


Часовой пояс GMT +4, время: 16:14.

Copyright © 1999-2008 Flasher.ru. All rights reserved.
Работает на vBulletin®. Copyright ©2000 - 2026, Jelsoft Enterprises Ltd. Перевод: zCarot
Администрация сайта не несёт ответственности за любую предоставленную посетителями информацию. Подробнее см. Правила.