Модераторы: korob2001, ginnie
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Паковщик на основе распаковщика, Нужна помощь 
:(
    Опции темы
Ducheved
  Дата 5.2.2010, 17:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 2
Регистрация: 5.2.2010

Репутация: нет
Всего: нет



Здравствуйте, появлилась очень большая надобность сделать упаковщик фаила AI, на основе распаковщика, является ли это возможным? 
Я нуб в Perl, большая просьба. Кто может помочь, помогите  smile 

Код

#!perl -w
#
#Node Compressed
#---------+++++++++++-----------
#8 8 7|1 8 8 6|2 8 8 5|3 8 8 4|4
#0 1 2   3 4 5   6 7 8   9 a b
#######################################################################
package main;
use strict;
use IO::File;
use Carp;
use POSIX;

my $fn = "level.ai";
my $fh = IO::File->new($fn, 'r') or croak "$fn: $!\n!";
binmode $fh;

my $data;
$fh->read($data, 0x38) or die;
my (
        $version,
        $vertex_count,
        $cell_size,
        $factor_y,
        @box,
) = unpack("VVfff6", $data);

printf "version=%d\n", $version;
printf "vertex_count=%d\n", $vertex_count;
printf "cell_size=%g\n", $cell_size;
printf "factor_y=%g\n", $factor_y;
printf "diff_y=%g\n", $box[4] - $box[1];
printf "box=(%g,%g,%g) - (%g,%g,%g)\n", @box;


my $row_length = floor(($box[5] - $box[2])/$cell_size + 1.501);
my $column_length = floor(($box[3] - $box[0])/$cell_size + 1.501);

printf "row x column = %d x %d\n", $column_length, $row_length;

die unless ($version == 8 || $version == 9 || $version == 10);

sub get_neighbours {
        my $data = shift;

        my ($r0) = unpack('V', $data);
        my ($r1) = unpack('V', substr($data, 2));
        my ($r2) = unpack('V', substr($data, 5));
        my ($r3) = unpack('V', substr($data, 8));

        my $n0 = $r0 & 0x7fffff;
        my $n1 = ($r1 >> 7) & 0x7fffff;
        my $n2 = ($r2 >> 6) & 0x7fffff;
        my $n3 = ($r3 >> 5) & 0x7fffff;

        return ($n0, $n1, $n2, $n3);
}

my @uv_adjustment;
sub get_normal {
        my $plane = shift;
        my ($i, $u, $v);
        my ($x, $y, $z);

        $u = ($plane >> 7) & 0x3f;
        $v = $plane & 0x7f;
        if ($u + $v >= 0x7f) {
                $u = 0x7f - $u;
                $v = 0x7f - $v;
        }
        $i = $plane & 0x1fff;
        $x = $uv_adjustment[$i] * $u;
        $y = $uv_adjustment[$i] * $v;
        $z = $uv_adjustment[$i] * (126-$u-$v);
        $x = -$x if $plane & 0x8000;
        $y = -$y if $plane & 0x4000;
        $z = -$z if $plane & 0x2000;
        return ($x, $y, $z);
}

sub prepare_uv_adjustment {
        my ($i, $u, $v);
        for (my $i = 0; $i < 0x2000; $i++) {
                $u = $i >> 7;
                $v = $i & 0x7f;
                if ($u + $v >= 0x7f) {
                        $u = 0x7f - $u;
                        $v = 0x7f - $v;
                }
                $uv_adjustment[$i] = 1.0/sqrt($u*$u + $v*$v + (126-$u-$v)*(126-$u-$v));
        }
}

prepare_uv_adjustment();

my @vertices = {};
my @matrix;
for (my $i = 0; $i < $vertex_count; $i++) {
        my ($data, $cover, $low_cover, $plane, $packed_xz_lo, $packed_xz_hi, $packed_y);
        if ($version == 10) {
                $fh->read($data, 0x17) or die;
                (
                        $data,
                        $cover,
                        $low_cover,
                        $plane,
                        $packed_xz_lo, $packed_xz_hi,
                        $packed_y,
                ) = unpack("a12vvvvCv", $data);
        } else {
                $fh->read($data, 0x15) or die;
                (
                        $data,
                        $cover,
                        $plane,
                        $packed_xz_lo, $packed_xz_hi,
                        $packed_y,
                ) = unpack("a12vvvCv", $data);
                $low_cover = $cover;
        }
        my $packed_xz = unpack('V', pack('vCC', $packed_xz_lo, $packed_xz_hi, 0));

# game X -> picture Y
# game Z -> picture X
my $gx = floor($packed_xz / $row_length);
my $gy = floor($packed_xz % $row_length);
if (defined $matrix[$gy][$gx]) {
        $matrix[$gy][$gx]++;
} else {
        $matrix[$gy][$gx] = 1;
}

        my $x = $box[0] + $cell_size * floor($packed_xz / $row_length);
        my $y = $box[1] + $factor_y * $packed_y / 65535.0;
        my $z = $box[2] + $cell_size * floor($packed_xz % $row_length);
        my @c = ($cover & 0xf, ($cover >> 4) & 0xf, ($cover >> 8) & 0xf, ($cover >> 12) & 0xf);
        my @lc = ($low_cover & 0xf, ($low_cover >> 4) & 0xf, ($low_cover >> 8) & 0xf, ($low_cover >> 12) & 0xf);
        my @n = get_neighbours($data);
        my @d = get_normal($plane);
        if (0) {
                my $qx = $x/0.7 + 0.5;
                my $qy = ($y - $box[1])/($box[4] - $box[1])*65535.0;
                my $qz = $z/0.7 + 0.5;
                my $x2 = floor($qx)*0.7;
                my $y2 = floor($qy)*($box[4] - $box[1])/65535.0 + $box[1];
                my $z2 = floor($qz)*0.7;
                printf "%f %f %f        -> %d %u %d        -> %f %f %f\n", $x, $y, $z, $qx, $qy, $qz, $x2, $y2, $z2;
                my $dx = abs($x2 - $x);
                my $dy = abs($y2 - $y);
                my $dz = abs($z2 - $z);
                die unless ($dx < 0.0001 && $dy < 0.001 && $dz < 0.0001);
        }
#printf "%6.6x %4.4x\n", $packed_xz, $packed_y;
        printf "%10d (%3d x %3d x %f): %6.6x (%x/%x), %6.6x (%x/%x), %6.6x (%x/%x), %6.6x (%x/%x); light: %d, normal: (%.3f, %.3f, %.3f)\n",
                        $i, $gx, $gy, $y,
                        $n[0], $c[0], $lc[0],
                        $n[1], $c[1], $lc[1],
                        $n[2], $c[2], $lc[2],
                        $n[3], $c[3], $lc[3],
                        unpack('C', substr($data, 11)) >> 4, get_normal($plane);
#        printf "cover=%4.4x x=%g y=%g z=%g\n", $cover, $x, $y, $z;
#        printf "light=%2.2x x=%g y=%g z=%g\n", $light, $x, $y, $z;
}
exit;

$fn = "out.bmp";
my $bmp_fh = IO::File->new($fn, 'w+') or croak "$fn: $!\n!";
binmode $fh;

my $w = $column_length;
my $h = $row_length;
my $rl = ($w*3 + 3) & ~3;
my $pad = $rl - $w*3;
$data = pack("vVvvV VVVvvV6",
        0x4d42,                # bfType
        $h*$rl,                # bfSize
        0,                # bfReserved1
        0,                # bfReserved2
        0x36,                # bfOffBits

        0x28,                # biSize
        $w,                # biWidth
        $h,                # biHeight
        1,                # biPlanes
        24,                # biBitCount
        0,                # biCompression
        0,                # biSizeImage,
        0xb12,                # biXPelsPerMeter,
        0xb12,                # biYPelsPerMeter,
        0,                # biClrUsed,
        0,                # biClrImportant,
);
$bmp_fh->write($data, 0x36);

use constant colors => {
        0 => [255,255,255],
        1 => [255,0,0],
        2 => [128,0,0],
        3 => [0,255,0],
        4 => [0,128,0],
        5 => [0,0,255],
        6 => [0,0,128],

        7 => [0,0,128],
        8 => [0,0,128],
        9 => [0,0,128],
};

#for (my $i = $h - 1; $i >= 0; $i--) {
for (my $i = 0; $i < $h; $i++) {
        for (my $j = 0; $j < $w; $j++) {
                my $floors = 0;
                if (defined $matrix[$i][$j]) {
                        $floors = $matrix[$i][$j];
                }
                $data = pack("CCC", @{colors->{$floors}});
                $bmp_fh->write($data, 3);
        }
        $pad != 0 and $bmp_fh->write(pack("C$pad", 0), $pad);
}


Данная функция запускается батником 

dump_ai.pl {level.ai}  ; >3487_level.txt
pause

и на выходе мы получаем фаил level.txt
в нем мне надо удалить несколько строк и обратно ввернуть в level.ai

Это сообщение отредактировал(а) Ducheved - 5.2.2010, 17:48
PM MAIL   Вверх
Ducheved
  Дата 8.2.2010, 19:15 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 2
Регистрация: 5.2.2010

Репутация: нет
Всего: нет



Может мне опишет кто нибудь процесс?  smile 
PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "Perl"
korob2001
sharq
  • В этом разделе обсуждаются общие вопросы по языку Perl
  • Если ваш вопрос относится к системному программированию, задавайте его здесь
  • Если ваш вопрос относится к CGI программированию, задавайте его здесь
  • Интерпретатор Perl можно скачать здесь ActiveState, O'REILLY, The source for Perl
  • Справочное руководство "Установка perl-модулей", можно скачать здесь


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, korob2001, sharq.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Perl: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.1399 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.