> Forums > Windows

Fotos aus GTA V auf dem PC laden, ohne Social Club

aleX Do., 16. April, 2015 um 22:44 #1



Viele Fragen sich sicher wie man die Fotos die man in GTA V mit dem Handy macht und in die Galerie speichert auf den PC bekommt ohne den Umweg über Social Club.

Am einfachsten geht dies mit dem Open Source Tool "Photomatic". Ein nur 9KB kleines Programm welches nur aus einer EXE Datei besteht. Einfach ausführen und es erkennt dann wo GTA V gespeichert ist und speichert die Bilder unter:

[code:1]C:\Users\<user>\Documents\Rockstar Games\GTA V\Profiles\<profile>\[/code:1]

... ab.

Hier der Reddit Post zum Programm:
https://www.reddit.com/r/GrandTheftAutoV/comments/32s622/photomatic_a_tool_to_extract_snapmatic_photos/

Quelltext:
https://bitbucket.org/WillKirkby/photomatic/src/master/


Download findet ihr hier angehängt, oder im Reddit Post.

aleX Do., 16. April, 2015 um 22:46 #2

Hier der Quellcode:

[code:1]using System;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Text.RegularExpressions;

namespace Photomatic
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Photomatic v{0}", Assembly.GetExecutingAssembly().GetName().Version.ToString());

string folderPath = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments), @"Rockstar GamesGTA VProfiles");

Console.WriteLine("Scanning for images in {0}", folderPath);
foreach (var fi in Directory.GetFiles(folderPath, "PGTA5*", SearchOption.AllDirectories).Select(a => new FileInfo(a)).Where(a => a.Name.StartsWith("PGTA5") && a.Extension == ""))
{
Console.Write("Loading {0}... ", fi.Name);

try
{
GtaPhoto photo = new GtaPhoto(fi.FullName);
Console.WriteLine("{0} {1}", photo.m_name, photo.m_title);

string fileName = fi.Name;

var match = Regex.Match(photo.m_json, ""creat":(\d+),");
if (match.Success)
{
long ts = long.Parse(match.Groups[1].Value);
DateTime utc = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc).AddSeconds(ts);
fileName = string.Format("{0:yyyy-MM-dd HH-mm-ss} {1}", utc, fi.Name);
}

string outPath = Path.Combine(fi.DirectoryName, fileName);
photo.SaveJpeg(outPath + ".jpg");

if (args.Contains("-info"))
{
photo.SaveInfo(outPath + ".txt");
}
}
catch
{
Console.WriteLine("Unexpected error.");
}
}
Console.WriteLine("All done! Press Enter to exit.");

Console.ReadLine();
}
}

class GtaPhoto
{
const uint kUnknown1 = 0x01000000;
const uint kJpegMagic = 0x4745504A;
const uint kJsonMagic = 0x4E4F534A;
const uint kTitlMagic = 0x4C544954;
const uint kDescMagic = 0x43534544;
const uint kJendMagic = 0x444E454A;
const int kBaseOffset = 0x108;

public string m_name;
public uint m_checksum;
public byte[] m_jpegData;
public string m_json;
public string m_title;
public string m_desc;


public GtaPhoto(string p_filepath)
{
using (BinaryReader br = new BinaryReader(File.OpenRead(p_filepath)))
{
uint unknown1 = br.ReadUInt32(); Debug.Assert(unknown1 == kUnknown1);
m_name = br.ReadNullPaddedUCS2(0x100);

m_checksum = br.ReadUInt32();
// --- offset base is here at 0x108 ---
uint offsetJEND = br.ReadUInt32(); // plus 0x108 - points to exact end of file, not the JEND marker
uint offsetJSON = br.ReadUInt32(); // plus 0x108
uint offsetTITL = br.ReadUInt32(); // plus 0x108
uint offsetDESC = br.ReadUInt32(); // plus 0x108

uint jpegMagic = br.ReadUInt32(); Debug.Assert(jpegMagic == kJpegMagic);
uint jpegBuffer = br.ReadUInt32(); // buffer is always 0x80000 (512 KiB)
uint jpegLength = br.ReadUInt32();
m_jpegData = br.ReadBytes((int)jpegLength);
br.ReadBytes((int)(jpegBuffer - jpegLength));

Debug.Assert(br.BaseStream.Position == kBaseOffset + offsetJSON);
uint jsonMagic = br.ReadUInt32(); Debug.Assert(jsonMagic == kJsonMagic);
uint jsonLength = br.ReadUInt32();
m_json = br.ReadNullPaddedASCII((int)jsonLength);

Debug.Assert(br.BaseStream.Position == kBaseOffset + offsetTITL);
uint titlMagic = br.ReadUInt32(); Debug.Assert(titlMagic == kTitlMagic);
uint titlLength = br.ReadUInt32();
m_title = br.ReadNullPaddedASCII((int)titlLength); // 0x28 max

Debug.Assert(br.BaseStream.Position == kBaseOffset + offsetDESC);
uint descMagic = br.ReadUInt32(); Debug.Assert(descMagic == kDescMagic);
uint descLength = br.ReadUInt32();
m_desc = br.ReadNullPaddedASCII((int)descLength); // unknown max - seems to be unused anyways

uint jendMagic = br.ReadUInt32(); Debug.Assert(jendMagic == kJendMagic);
Debug.Assert(br.BaseStream.Position == kBaseOffset + offsetJEND);
}
}

public void SaveJpeg(string p_filepath)
{
File.WriteAllBytes(p_filepath, m_jpegData);
}

public void SaveInfo(string p_filepath)
{
using (StreamWriter sw = new StreamWriter(p_filepath))
{
sw.WriteLine("TITL: {0}", m_title);
sw.WriteLine("DESC: {0}", m_desc);
sw.WriteLine("JSON: {0}", m_json);
}
}
}

static class Extensions
{
public static string ReadNullPaddedASCII(this BinaryReader self, int bytes)
{
byte[] data = self.ReadBytes(bytes);
StringBuilder buffer = new StringBuilder();
byte val;
for (int i = 0; i < data.Length; ++i)
{
if ((val = data[i]) == 0) break;
buffer.Append((char)val);
}
return buffer.ToString();
}

public static string ReadNullPaddedUCS2(this BinaryReader self, int bytes)
{
byte[] data = self.ReadBytes(bytes);
StringBuilder buffer = new StringBuilder();
ushort val;
for (int i = 0; i < data.Length; i += 2)
{
if ((val = BitConverter.ToUInt16(data, i)) == 0) break;
buffer.Append((char)val);
}
return buffer.ToString();
}
}
}[/code:1]



> Forums > Windows

Top