[Гайд] Создание собственного расширения файла на основе бинарного файла
Цитата: Roman Anderson [anomal3] от 19.10.2020, 20:25Всем привет ВИНТВИКОЮЗЕРЫ
Статья рассчитана не совсем для новичков, а для тех хоть как то понимает что такое переменные.Сегодня хочу рассказать как создать свой файл, а точнее файл со своим расширением на основе бинарного файла.
Большинство игр и программ написано по такому алгоритму. Создаётся бинарный файл, внутри файла своя структура, и просто меняем на своё расширение.
Такой статьи я не смог найти, и поэтому поделюсь своими приобретёнными знаниями
Создавать будем в WinFormИтак приступим. Для начала придумаем свое расширение. Пусть будет *.galileo
В Классе формы объявим свою структуру.public partial class Form1 : Form { public Form1() { InitializeComponent(); } struct GALILEO { public string Date; // Создание файла public string NameCreator; // Кто создал файл public string _text; //Запишем какой-нибудь текст //======Так же "зашьем" файл внутрь===========// public long ByteSize; //Узнаем количество байт файла (это нам потом пригодится) public string FileExt; //Узнаем расширение файла (тоже пригодится) public byte[] ByteSource; //ну и сами байты файла public GALILEO( string _Date, string _NameCreator, string __text, long _ByteSize, string _FileExt, byte[] _ByteSource) { Date = _Date; Razdel = _Razdel; NameCreator = _NameCreator; _text = __text; ByteSize = _ByteSize; FileExt = _FileExt; ByteSource = _ByteSource; } } //Вот и вся структура бинарного файла }
Дальше на форму повесим кнопку (для того чтобы цеплять файл), и сделаем ей событие.
в событии пишемstring PathAttachFile = ""; //Переменная для храения пути какой файл вшиваем private void button1_Click(object sender, EventArgs e) { OpenFileDialog ofd = new OpenFileDialog(); ofd.Title = "Укажите файл который надо прикрепить"; //ofd.Filter = "MP4 video (*.mp4)|*mp4|Docx files (*.docx)|*.docx|Текстовые файлы (*.txt)|*.txt|Все файлы (*.*)|*.*"; //Фильтр файлов которые будем вшивать можно указать ofd.FileName = "Укажите файл"; ofd.RestoreDirectory = true; var ResultDialog = ofd.ShowDialog(); if(ResultDialog == DialogResult.OK) { PathAttachFile = ofd.FileName; } }Теперь осталось вшить данные. Закинем на форму textBox для того чтобы записать какой-нибудь текст.
И ещё одну кнопку, чтобы обработать запись в бинарный файл.private void button2_Click(object sender, EventArgs e) { try { //Запишем в переменную наш файл. Считаем все данные с него. byte[] byte_AttachFile = File.ReadAllBytes(PathAttachFile); //Пора узнать какое расширение будет у нашего вшиваемого файла //Можно конечно узнать и через FileInfo, но мне так проще string ExtFile = tbAttFilePath.Text.Substring(tbAttFilePath.Text.LastIndexOf(".") + 1); //И теперь открываем поток и начинаем писать. using (BinaryWriter writer = new BinaryWriter(File.Open(/*Укажем как назовём свой файл*/ test.galileo, FileMode.OpenOrCreate))) { //Переопределим значения для структуры, чтобы записать какие то значения GALILEO[] galileo = new GALILEO[1]; galileo[0] = new GALILEO( //Пойдём по-порядку как и создавали структуру файла DateTime.Now.ToString("dd/MM/yy HH:mm"), Environment.UserName, textBox1.Text, byte_AttachFile.Length, ExtFile, byte_AttachFile); ); //Пишем foreach (GALILEO l in galileo) { writer.Write(l.Date); writer.Write(l.NameCreator); writer.Write(l._text); writer.Write(l.ByteSize); writer.Write(l.FileExt); writer.Write(l.ByteSource); } } } catch (Exception ex) { MessageBox.Show(ex.Message); } //Если будет ошибка, отловим finally { MessageBox.Show("файл galileo успешно создан"); } //Если все хорошо, сообщим об этом }и всё. Файл вшит и данные в тоже. Но вот если открыть файл блокнотом, то мы можем увидеть некоторые строковые значения
Вот как пример
Зато файл точно не прочитать. Строковые значения можно легко зашифровать, и тогда точно простой пользователь ничего не увидит.
Теперь нам осталось прочитать файл.Можно создать отдельную форму, можно тут же.
//Я решил в отдельной форме делать private string pathGalileo; private string ExtensionFile = ""; private void Form1_Load(object sender, EventArgs e) { OpenFileDialog ofd = new OpenFileDialog(); ofd.Title = "Укажите файл galileo"; ofd.Filter = "Special galileo Files (*.galileo)|*galileo"; ofd.FileName = "galileo файл"; ofd.RestoreDirectory = true; var ResultDialog = ofd.ShowDialog(); if (ResultDialog == DialogResult.OK) { pathGalileo = ofd.FileName; ReadGALILEOFile(); } } void ReadGALILEOFile() { using (BinaryReader reader = new BinaryReader(File.Open(pathGalileo, FileMode.Open))) { // пока не достигнут конец файла // считываем каждое значение из файла while (reader.PeekChar() > -1) { string Date = reader.ReadString(); string Name= reader.ReadString(); string TEXT = reader.ReadString(); var Size = reader.ReadUInt64(); ExtensionFile = reader.ReadString(); string StrSize = (Size / 1024 / 1024).ToString() + " MB"; File.WriteAllBytes(@"tmp." + ExtensionFile, reader.ReadBytes((int)Size)); DialogResult result = MessageBox.Show($"Дата создания {Date}, Имя создателя {Name} \r\n" + $"Текст {TEXT} Расширение вшитого файла {ExtensionFile} и его размер {StrSize}\r\n\r\n" + "Открыть вшитый файл?" , "Galileo", MessageBoxButtons.YesNo, MessageBoxIcon.Question ); if(result == DialogResult.Yes) { //Тут открываем вшитый файл как угодно, так как он хранится рядом Process.Start(@"tmp." + ExtensionFile); } } } } //И чтобы файлы не копились и не засоряли каталог мы егопросто удалим private void Form1_FormClosing(object sender, FormClosingEventArgs e) { string filename = Application.StartupPath; filename = Path.GetFullPath( Path.Combine(filename, ".\\tmp." + ExtensionFile)); File.Delete(filename); }Не бойтесь экспериментировать, и самое главное не запутаться
Всем привет ВИНТВИКОЮЗЕРЫ
Статья рассчитана не совсем для новичков, а для тех хоть как то понимает что такое переменные.
Сегодня хочу рассказать как создать свой файл, а точнее файл со своим расширением на основе бинарного файла.
Большинство игр и программ написано по такому алгоритму. Создаётся бинарный файл, внутри файла своя структура, и просто меняем на своё расширение.
Такой статьи я не смог найти, и поэтому поделюсь своими приобретёнными знаниями
Создавать будем в WinForm
Итак приступим. Для начала придумаем свое расширение. Пусть будет *.galileo
В Классе формы объявим свою структуру.
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
struct GALILEO
{
public string Date; // Создание файла
public string NameCreator; // Кто создал файл
public string _text; //Запишем какой-нибудь текст
//======Так же "зашьем" файл внутрь===========//
public long ByteSize; //Узнаем количество байт файла (это нам потом пригодится)
public string FileExt; //Узнаем расширение файла (тоже пригодится)
public byte[] ByteSource; //ну и сами байты файла
public GALILEO(
string _Date,
string _NameCreator,
string __text,
long _ByteSize,
string _FileExt,
byte[] _ByteSource)
{
Date = _Date;
Razdel = _Razdel;
NameCreator = _NameCreator;
_text = __text;
ByteSize = _ByteSize;
FileExt = _FileExt;
ByteSource = _ByteSource;
}
} //Вот и вся структура бинарного файла
}
Дальше на форму повесим кнопку (для того чтобы цеплять файл), и сделаем ей событие.
в событии пишем
string PathAttachFile = ""; //Переменная для храения пути какой файл вшиваем
private void button1_Click(object sender, EventArgs e)
{
OpenFileDialog ofd = new OpenFileDialog();
ofd.Title = "Укажите файл который надо прикрепить";
//ofd.Filter = "MP4 video (*.mp4)|*mp4|Docx files (*.docx)|*.docx|Текстовые файлы (*.txt)|*.txt|Все файлы (*.*)|*.*";
//Фильтр файлов которые будем вшивать можно указать
ofd.FileName = "Укажите файл";
ofd.RestoreDirectory = true;
var ResultDialog = ofd.ShowDialog();
if(ResultDialog == DialogResult.OK)
{
PathAttachFile = ofd.FileName;
}
}
Теперь осталось вшить данные. Закинем на форму textBox для того чтобы записать какой-нибудь текст.
И ещё одну кнопку, чтобы обработать запись в бинарный файл.
private void button2_Click(object sender, EventArgs e)
{
try
{
//Запишем в переменную наш файл. Считаем все данные с него.
byte[] byte_AttachFile = File.ReadAllBytes(PathAttachFile);
//Пора узнать какое расширение будет у нашего вшиваемого файла
//Можно конечно узнать и через FileInfo, но мне так проще
string ExtFile = tbAttFilePath.Text.Substring(tbAttFilePath.Text.LastIndexOf(".") + 1);
//И теперь открываем поток и начинаем писать.
using (BinaryWriter writer = new BinaryWriter(File.Open(/*Укажем как назовём свой файл*/ test.galileo, FileMode.OpenOrCreate)))
{
//Переопределим значения для структуры, чтобы записать какие то значения
GALILEO[] galileo = new GALILEO[1];
galileo[0] = new GALILEO( //Пойдём по-порядку как и создавали структуру файла
DateTime.Now.ToString("dd/MM/yy HH:mm"),
Environment.UserName,
textBox1.Text,
byte_AttachFile.Length,
ExtFile,
byte_AttachFile);
);
//Пишем
foreach (GALILEO l in galileo)
{
writer.Write(l.Date);
writer.Write(l.NameCreator);
writer.Write(l._text);
writer.Write(l.ByteSize);
writer.Write(l.FileExt);
writer.Write(l.ByteSource);
}
}
}
catch (Exception ex) { MessageBox.Show(ex.Message); } //Если будет ошибка, отловим
finally { MessageBox.Show("файл galileo успешно создан"); } //Если все хорошо, сообщим об этом
}
и всё. Файл вшит и данные в тоже. Но вот если открыть файл блокнотом, то мы можем увидеть некоторые строковые значения
Вот как пример
Зато файл точно не прочитать. Строковые значения можно легко зашифровать, и тогда точно простой пользователь ничего не увидит.
Теперь нам осталось прочитать файл.
Можно создать отдельную форму, можно тут же.
//Я решил в отдельной форме делать
private string pathGalileo;
private string ExtensionFile = "";
private void Form1_Load(object sender, EventArgs e)
{
OpenFileDialog ofd = new OpenFileDialog();
ofd.Title = "Укажите файл galileo";
ofd.Filter = "Special galileo Files (*.galileo)|*galileo";
ofd.FileName = "galileo файл";
ofd.RestoreDirectory = true;
var ResultDialog = ofd.ShowDialog();
if (ResultDialog == DialogResult.OK)
{
pathGalileo = ofd.FileName;
ReadGALILEOFile();
}
}
void ReadGALILEOFile()
{
using (BinaryReader reader = new BinaryReader(File.Open(pathGalileo, FileMode.Open)))
{
// пока не достигнут конец файла
// считываем каждое значение из файла
while (reader.PeekChar() > -1)
{
string Date = reader.ReadString();
string Name= reader.ReadString();
string TEXT = reader.ReadString();
var Size = reader.ReadUInt64();
ExtensionFile = reader.ReadString();
string StrSize = (Size / 1024 / 1024).ToString() + " MB";
File.WriteAllBytes(@"tmp." + ExtensionFile, reader.ReadBytes((int)Size));
DialogResult result = MessageBox.Show($"Дата создания {Date}, Имя создателя {Name} \r\n" +
$"Текст {TEXT} Расширение вшитого файла {ExtensionFile} и его размер {StrSize}\r\n\r\n" +
"Открыть вшитый файл?" , "Galileo", MessageBoxButtons.YesNo, MessageBoxIcon.Question );
if(result == DialogResult.Yes)
{
//Тут открываем вшитый файл как угодно, так как он хранится рядом
Process.Start(@"tmp." + ExtensionFile);
}
}
}
}
//И чтобы файлы не копились и не засоряли каталог мы егопросто удалим
private void Form1_FormClosing(object sender, FormClosingEventArgs e)
{
string filename = Application.StartupPath;
filename = Path.GetFullPath(
Path.Combine(filename, ".\\tmp." + ExtensionFile));
File.Delete(filename);
}
Не бойтесь экспериментировать, и самое главное не запутаться
