⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 photoshopreader.cpp

📁 网络泡泡被.net管理
💻 CPP
📖 第 1 页 / 共 4 页
字号:
	item_length = m_name.length();
	outfile << item_length;
	for (i = 0; i < m_name.length() ; i++)
	{
		outfile.sputc( 0 );
		outfile.sputc( m_name[i] );
	}

	item_length = 4;
	id = index;
	outfile.sputn( "8BIMlyid", 8 );
	outfile << item_length;
	outfile << id;

	int extra_field_end = tell(outfile );

	length = extra_field_end - extra_field_start - sizeof(length);
	outfile.pubseekpos( extra_field_start );
	outfile << length;
	outfile.pubseekpos( extra_field_end );
	return true;
}

// ------------------------------------------------------------------------
// photoshop layer
// ------------------------------------------------------------------------
bool t_photoshop_layer::write_channels( std::streambuf& outfile, int channel_block_start,
									    CDxFileProgress* file_progress )
{
	int channel_index;
	int channel_start;
	int channel_end;
	std::vector<long>    channel_lengths;

	for (channel_index = 0; channel_index < m_channels.size(); channel_index++)
	{
		channel_start = tell( outfile );
		if (!m_channels[channel_index]->write( outfile, file_progress ))
			return false;
		channel_end = tell( outfile );
		channel_lengths.push_back( channel_end - channel_start );
	}

	int file_end = tell( outfile );

	outfile.pubseekpos( channel_block_start );
	for (channel_index = 0; channel_index < m_channels.size(); channel_index++)
	{
		t_mac_short id;
		t_mac_long  length;

		id = m_channels[channel_index]->get_id();
		length = channel_lengths[channel_index];
		outfile << id;
		outfile << length;
	}
	outfile.pubseekpos( file_end );
	return true;
}

// --------------------------------------------------------------------------------
// photoshop image
// --------------------------------------------------------------------------------
t_photoshop_image::~t_photoshop_image()
{
}

// --------------------------------------------------------------------------------
// photoshop image
// --------------------------------------------------------------------------------
t_photoshop_layer_ptr t_photoshop_image::get_layer( const char* name )
{
	int i;

	i = m_layers.size();
	while (i--)
		if (strcmp( name, m_layers[i]->get_name().c_str() ) == 0)
			return m_layers[i];
	return 0;
}

// --------------------------------------------------------------------------------
// photoshop image
// --------------------------------------------------------------------------------
bool t_photoshop_image::read_resources( std::streambuf& infile, long length )
{
	infile.pubseekoff( length, std::ios::cur );
	return true;
}

// --------------------------------------------------------------------------------
// photoshop image
// --------------------------------------------------------------------------------
bool t_photoshop_image::read_layers( std::streambuf& infile, CDxFileProgress* file_progress,
									 int bar_size )
{
	t_mac_long            length;
	t_mac_short           layer_count;
	int                   layer_index;
	t_photoshop_layer_ptr layer;

	infile >> length;
	if (length == 0)
		return true;
	infile >> layer_count;

	int layer_max = static_cast<signed short>(layer_count.get());

	layer_max = abs( layer_max );
	for (layer_index = 0; layer_index < layer_max; layer_index++)
	{
		layer = new t_photoshop_layer;

		m_layers.push_back( layer );
		if (!layer->read( infile ))
			return false;
		bar_size += ((layer->get_width() * layer->get_height() + k_file_progress_unit - 1)
			         / k_file_progress_unit) * layer->get_channel_count();
	}
	if (file_progress != 0)
		file_progress->set_max_value( bar_size );
	for (layer_index = 0; layer_index < layer_max; layer_index++)
		if (!m_layers[layer_index]->read_channels( infile, file_progress ))
			return false;
	
	int position = tell(infile);
	if ((position & 1) == 1)
		infile.sbumpc();
	return true;
}

// --------------------------------------------------------------------------------
// photoshop image
// --------------------------------------------------------------------------------
bool t_photoshop_image::read( std::streambuf& infile, CDxFileProgress* file_progress )
{
	t_photoshop_file_header file_header;

	::read( infile, &file_header, sizeof(file_header));
	if (memcmp( file_header.signature, "8BPS", 4 ) != 0)
		return false;
	if (file_header.version != 1)
		return false;

	m_height = file_header.rows;
	m_width = file_header.columns;
	m_color_mode = file_header.color_mode;

	int i;

	for (i = 0; i < sizeof( file_header.reserved ); i++)
		if (file_header.reserved[i] != 0)
			return false;
	if (file_header.channel_count < 1 || file_header.channel_count > 24)
		return false;

	// read color mode information
	t_mac_long length;

	infile >> length;
	if (length != 0)
	{
		if (length != 256 * 3)
			return false;
		BYTE buffer[256];

		::read( infile, buffer, sizeof(buffer));
		for (i = 0; i < 256; i++)
			m_palette[i].red = buffer[i];
		::read( infile, buffer, sizeof(buffer));
		for (i = 0; i < 256; i++)
			m_palette[i].green = buffer[i];
		::read( infile, buffer, sizeof(buffer));
		for (i = 0; i < 256; i++)
			m_palette[i].blue = buffer[i];
	}

	infile >> length;
	if (!read_resources( infile, length ))
		return false;
	
	int bar_size = ((m_width * m_height + k_file_progress_unit - 1) / 
	                k_file_progress_unit ) * file_header.channel_count;

	infile >> length;
	if (length > 0)
	{
		if (!read_layers( infile, file_progress, bar_size ))
			return false;

		// read global layer mask (and discard)
		infile >> length;
		infile.pubseekoff( length, std::ios::cur );
	}
	else
	{
		if (file_progress != 0)
			file_progress->set_max_value( bar_size );
	}

	// read background channels
	return m_background.read_background( infile, file_header.columns, file_header.rows,
										 file_header.channel_count,
		                                 file_header.bits_per_channel, m_color_mode,
										 file_progress );
}

// --------------------------------------------------------------------------------
// photoshop image
// --------------------------------------------------------------------------------
bool t_photoshop_image::write_resources( std::streambuf& outfile )
{
	t_image_resource_header header;
	int                     block_start = tell( outfile );
	t_mac_long              length;

	length = 0;
	outfile << length;
	return true;
}

// --------------------------------------------------------------------------------
// photoshop image
// --------------------------------------------------------------------------------
bool t_photoshop_image::write_layers( std::streambuf& outfile, CDxFileProgress* file_progress )
{
	t_mac_long            length;
	t_mac_short           layer_count;
	int                   layer_index;
	t_photoshop_layer_ptr layer;
	std::vector<int>      channel_block_starts;
	int                   channel_count = m_background.get_channel_count();

	int block_start = tell(outfile );

	outfile << length;
	layer_count = m_layers.size();
	outfile << layer_count;
	channel_block_starts.resize( m_layers.size() );

	for (layer_index = 0; layer_index < m_layers.size(); layer_index++)
	{
		if (!m_layers[layer_index]->write( outfile, &channel_block_starts[layer_index], layer_index + 1 ))
			return false;
		channel_count += m_layers[layer_index]->get_channel_count();
	}
	if (file_progress != 0)
		file_progress->set_max_value( ((m_width * m_height + k_file_progress_unit - 1) 
		                              / k_file_progress_unit ) * channel_count );
	for (layer_index = 0; layer_index < m_layers.size(); layer_index++)
		if (!m_layers[layer_index]->write_channels( outfile, channel_block_starts[layer_index],
			                                        file_progress ))
			return false;

	if ((tell( outfile ) & 1) == 1)
		outfile.sputc( 0 );

	int block_end = tell( outfile );

	outfile.pubseekpos( block_start );
	length = block_end - block_start - sizeof(length);
	outfile << length;
	outfile.pubseekpos( block_end );
	return true;
}

// ------------------------------------------------------------------------
// clear all elements of a channel
// ------------------------------------------------------------------------
void t_photoshop_channel::clear()
{
	memset( m_data.begin(), 0, m_width * m_height );
}

// ------------------------------------------------------------------------
// clear all elements of a layer
// ------------------------------------------------------------------------
void t_photoshop_layer::clear()
{
	int i;

	for (i = 0; i < m_channels.size(); i++)
		m_channels[i]->clear();
}

// ------------------------------------------------------------------------
// create the background layers from the foreground layers
// ------------------------------------------------------------------------
void t_photoshop_image::create_background()
{
	if (m_layers.size() == 0)
		return;

	// clear background
	int i;
	int x, y;
	PIX32 pixel;
	GRECT rect;
	t_photoshop_layer_ptr layer;

	m_background.clear();

	for (i = 0; i < m_layers.size(); i++)
	{
		layer = m_layers[i];
		rect = intersection( layer->get_rect(), m_background.get_rect() );
		for (y = rect.top; y < rect.bottom; y++)
			for (x = rect.left; x < rect.right; x++)
			{
				pixel = layer->get_pixel( x, y );
				if (pixel.alpha > 0)
					m_background.set_pixel( x, y, pixel );
			}
	}
}

// --------------------------------------------------------------------------------
// photoshop image
// --------------------------------------------------------------------------------
bool t_photoshop_image::write( std::streambuf& outfile, CDxFileProgress* file_progress )
{
	t_photoshop_file_header file_header;

	file_header.bits_per_channel = 8;
	file_header.channel_count = m_background.get_channel_count();
	file_header.color_mode = m_color_mode;
	file_header.rows = m_height;
	file_header.columns = m_width;
	file_header.version = 1;
	memcpy( file_header.signature, "8BPS", 4 );
	memset( file_header.reserved, 0, sizeof( file_header.reserved ) );
	::write( outfile, &file_header, sizeof(file_header));

	// read color mode information
	t_mac_long length;

	if ( m_color_mode != k_color_mode_indexed )
	{
		length = 0;
		outfile << length;
	}
	else
	{
		length = 256 * 3;
		outfile << length;

		BYTE buffer[256];
		int     i;

		for (i = 0; i < 256; i++)
			buffer[i] = m_palette[i].red;
		::write( outfile, buffer, sizeof(buffer));
		for (i = 0; i < 256; i++)
			buffer[i] = m_palette[i].green;
		::write( outfile, buffer, sizeof(buffer));
		for (i = 0; i < 256; i++)
			buffer[i] = m_palette[i].blue;
		::write( outfile, buffer, sizeof(buffer));
	}

	write_resources( outfile );

	int layer_start = tell( outfile );

	outfile << length;
	if (m_layers.size() > 0)
	{
		write_layers( outfile, file_progress );

		// write global layer mask
		length = 0;
		outfile << length;
	}
	else
	{
		if (file_progress != 0)
			file_progress->set_max_value( ((m_width * m_height + k_file_progress_unit - 1)
			                              / k_file_progress_unit)
										  * m_background.get_channel_count() );
	}


	int layer_end = tell( outfile );

	outfile.pubseekpos( layer_start );
	length = layer_end - layer_start - sizeof(length);
	outfile << length;
	outfile.pubseekpos( layer_end );

	create_background();
	return m_background.write_background( outfile, file_progress );
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -