210 lines
7.8 KiB
Ruby
Executable File
210 lines
7.8 KiB
Ruby
Executable File
#
|
|
# File:: script/japanese/data_patch_tcls.rb
|
|
# Description::
|
|
#
|
|
# Author:: David Muir <david.muir@rockstarnorth.com>
|
|
# Date:: 30 May 2013
|
|
#
|
|
|
|
#-----------------------------------------------------------------------------
|
|
# Uses
|
|
#-----------------------------------------------------------------------------
|
|
require 'RSG.Base.dll'
|
|
require 'RSG.Base.Configuration.dll'
|
|
require 'RSG.Base.Windows.dll'
|
|
require 'RSG.Pipeline.Core.dll'
|
|
require 'RSG.Pipeline.Content.dll'
|
|
require 'RSG.Pipeline.Services.dll'
|
|
require 'Ionic.Zip.Partial.dll'
|
|
include RSG::Base::Configuration
|
|
include RSG::Base::Logging
|
|
include RSG::Base::Logging::Universal
|
|
include RSG::Base::OS
|
|
include RSG::Base::Windows
|
|
include RSG::Pipeline::Core
|
|
include RSG::Pipeline::Content
|
|
include RSG::Pipeline::Services
|
|
|
|
require 'mscorlib'
|
|
require 'System.Core'
|
|
require 'System.Xml'
|
|
require 'System.Xml.Linq.dll'
|
|
include System::Collections::Generic
|
|
include System::IO
|
|
include System::Xml::Linq
|
|
using_clr_extensions System::Linq
|
|
|
|
require 'pipeline/monkey/object' # This gives you Object.to_seq from the 101samples.
|
|
require 'pipeline/os/options'
|
|
include Pipeline
|
|
|
|
#-----------------------------------------------------------------------------
|
|
# Constants
|
|
#-----------------------------------------------------------------------------
|
|
AUTHOR = 'RSGEDI Tools'
|
|
EMAIL = 'RSGEDI Tools <*tools@rockstarnorth.com>'
|
|
OPTIONS = [
|
|
LongOption::new( 'textures', LongOption::ArgType.Required, 'i',
|
|
'Directory for textures.' )
|
|
]
|
|
|
|
#-----------------------------------------------------------------------------
|
|
# Functions
|
|
#-----------------------------------------------------------------------------
|
|
|
|
# Process component zip.
|
|
def process_zip( branch, log, ped_basename, zip_filename, output_path )
|
|
|
|
output_path = Path::Combine( output_path, Path::GetFileNameWithoutExtension( zip_filename ) )
|
|
filelist = Zip::GetFileList( zip_filename )
|
|
result = Zip::ExtractAll( zip_filename, output_path, true, nil )
|
|
|
|
textures_path = Path::Combine( "x:\\gta5\\assets_japanese\\characters\\textures", ped_basename )
|
|
texture_files = Directory::GetFiles( textures_path )
|
|
files = texture_files.to_seq
|
|
files = files.Select( lambda { |f| Path::GetFileNameWithoutExtension( f ) } )
|
|
files = files.to_a
|
|
|
|
changed_zip = false
|
|
puts "#{filelist.class} #{texture_files.Length}"
|
|
filelist[1].each do |tcl_filename|
|
|
next unless ( tcl_filename.EndsWith( '.tcl' ) )
|
|
|
|
# Skip if we don't have texture overridden.
|
|
tcl_filename = Path::Combine( output_path, tcl_filename )
|
|
tcl_basename = Path::GetFileNameWithoutExtension( tcl_filename )
|
|
next unless ( files.Contains( tcl_basename ) )
|
|
|
|
log.Message( "\t\tPatching: #{tcl_basename} #{tcl_filename}." )
|
|
changed_zip = true
|
|
|
|
xmldoc = XDocument.Load( tcl_filename )
|
|
parent = xmldoc.Element( XName::Get( 'rage__CTextureConversionSpecification' ) ).Element( XName::Get( 'parent' ) )
|
|
parent.Value = parent.Value.Replace( '${RS_ASSETS}', 'x:/gta5/assets_japanese' )
|
|
xmldoc.Save( tcl_filename )
|
|
end
|
|
|
|
if ( not changed_zip ) then
|
|
log.Message( "Not changing: #{zip_filename}." )
|
|
return (false)
|
|
end
|
|
|
|
# Zip back up.
|
|
files = []
|
|
filelist[1].each do |filename|
|
|
input_filename = Path::Combine( output_path, filename )
|
|
output_filename = filename
|
|
files << RSG::Base::Collections::Pair[System::String, System::String]::new( input_filename, output_filename )
|
|
end
|
|
System::IO::File::Delete( zip_filename )
|
|
Zip::Create( branch, zip_filename, files.to_clr( RSG::Base::Collections::Pair[System::String, System::String] ) )
|
|
|
|
log.Message( "Created: #{zip_filename}." )
|
|
true
|
|
end
|
|
|
|
# Process .ped.zip
|
|
def process_pedzip( branch, log, zip_filename, output_path )
|
|
|
|
output_path = Path::Combine( output_path, Path::GetFileNameWithoutExtension( zip_filename ), 'parts' )
|
|
log.Message( "Extract: #{zip_filename} to #{output_path}." )
|
|
filelist = Zip::GetFileList( zip_filename )
|
|
result = Zip::ExtractAll( zip_filename, output_path, true, nil )
|
|
|
|
ped_basename = Path::GetFileNameWithoutExtension( Path::GetFileNameWithoutExtension( zip_filename ) )
|
|
changed = false
|
|
filelist[1].each do |zip|
|
|
next unless ( zip.EndsWith( '.zip' ) )
|
|
|
|
changed |= process_zip( branch, log, ped_basename, Path::Combine( output_path, zip ), output_path )
|
|
end
|
|
|
|
if ( changed ) then
|
|
log.Message( "Re-create .ped.zip: #{zip_filename}." )
|
|
|
|
# Zip back up.
|
|
files = []
|
|
filelist[1].each do |filename|
|
|
input_filename = Path::Combine( output_path, filename )
|
|
output_filename = filename
|
|
files << RSG::Base::Collections::Pair[System::String, System::String]::new( input_filename, output_filename )
|
|
end
|
|
System::IO::File::Delete( zip_filename )
|
|
Zip::Create( branch, zip_filename, files.to_clr( RSG::Base::Collections::Pair[System::String, System::String] ) )
|
|
|
|
log.Message( "Created: #{zip_filename}." )
|
|
end
|
|
end
|
|
|
|
#-----------------------------------------------------------------------------
|
|
# Entry-Point
|
|
#-----------------------------------------------------------------------------
|
|
if ( __FILE__ == $0 ) then
|
|
|
|
# Initialise log and console output.
|
|
LogFactory.CreateApplicationConsoleLogTarget( )
|
|
g_Log = LogFactory.ApplicationLog
|
|
g_Options = OS::Options::new( OPTIONS )
|
|
begin
|
|
if ( g_Options.is_enabled?( 'help' ) )
|
|
puts "#{__FILE__}"
|
|
puts "Usage:"
|
|
puts g_Options.usage()
|
|
exit( 1 )
|
|
end
|
|
|
|
g_Config = g_Options.command_options.Config
|
|
g_Project = g_Options.command_options.Project
|
|
g_BranchName = g_Options.has_option?( 'branch' ) ? g_Options.get( 'branch' ) : g_Project.DefaultBranchName
|
|
g_Branch = g_Project.Branches[g_BranchName] if ( g_Project.Branches.ContainsKey( g_BranchName ) )
|
|
if ( g_Branch.nil? ) then
|
|
g_Log.Error( "Invalid branch '#{g_BranchName}' for project '#{g_Project.UIName}'." )
|
|
exit( 1 )
|
|
end
|
|
|
|
g_TexturesPath = g_Options.has_option?( 'textures' )
|
|
g_Filenames = []
|
|
g_Options.trailing.each do |filename|
|
|
g_Filenames << System::IO::Path.GetFullPath( filename )
|
|
end
|
|
|
|
g_TempPath = "c:\\temp"
|
|
g_Filenames = g_Filenames.to_clr( System::String )
|
|
g_Filenames.each do |filename|
|
|
g_Log.Message( "Processing: #{filename}" )
|
|
|
|
process_pedzip( g_Branch, g_Log, filename, g_TempPath )
|
|
end
|
|
|
|
rescue SystemExit => ex
|
|
|
|
# Show Universal Log output on errors.
|
|
if ( g_Options.show_popups? and 0 != ex.status ) then
|
|
command = "#{g_Branch.Environment.Subst(ULOG_VIEWER)} #{LogFactory.ProcessLogDirectory}"
|
|
g_Log.Message( "Displaying Universal Logs: #{command}" )
|
|
system( command )
|
|
elsif ( g_Options.show_popups? ) then
|
|
## DHM; not sure this is neccessary?
|
|
## RSG::Pipeline::Services::MessageBox::Show( "Asset build completed successfully." )
|
|
end
|
|
LogFactory.ApplicationShutdown()
|
|
exit( ex.status )
|
|
|
|
rescue Exception => ex
|
|
|
|
g_Log.Exception( ex, "Exception during #{__FILE__}." )
|
|
|
|
puts "Exception during #{__FILE__}: #{ex.message}"
|
|
puts ex.backtrace.join("\n")
|
|
|
|
if ( g_Options.show_popups? ) then
|
|
dlg = RSG::Base::Windows::ExceptionStackTraceDlg::new( ex,
|
|
g_Config.EmailAddress, AUTHOR, EMAIL )
|
|
dlg.ShowDialog( )
|
|
end
|
|
|
|
exit( 1 )
|
|
end
|
|
end
|
|
|