support storing comments in PropertyList, add preliminary support for reading Master Boot Record (MBR) disk images
This commit is contained in:
parent
d8dd8d993e
commit
1a793c3f38
@ -0,0 +1,21 @@
|
||||
<?xml version="1.0" encoding="UTF-8" ?>
|
||||
<UniversalEditor Version="5.0">
|
||||
<Editors>
|
||||
<Editor ID="{1a47fee2-eb61-4ce8-a297-4d6988b1680c}" TypeName="UniversalEditor.Editors.PartitionedFileSystem.PartitionedFileSystemEditor" Title="Partitioned File System Editor">
|
||||
<Contexts>
|
||||
<Context ID="{7a21bf07-b17d-4c2f-9ac5-9760ab0aec33}" Name="Tree View - File System Editor" />
|
||||
</Contexts>
|
||||
<Commands>
|
||||
<Command ID="PartitionedFileSystemEditor_tvPartitions_ContextMenu_CopyTo" Title="_Copy To..." />
|
||||
|
||||
<Command ID="PartitionedFileSystemEditor_tvPartitions_ContextMenu_Unselected" Title="PartitionedFileSystemEditor tvPartitions ContextMenu Unselected">
|
||||
<Items>
|
||||
<CommandReference CommandID="PartitionedFileSystemEditor_tvPartitions_ContextMenu_CopyTo" />
|
||||
<Separator />
|
||||
<CommandReference CommandID="FileProperties" />
|
||||
</Items>
|
||||
</Command>
|
||||
</Commands>
|
||||
</Editor>
|
||||
</Editors>
|
||||
</UniversalEditor>
|
||||
@ -0,0 +1,198 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.40.0 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.24"/>
|
||||
<object class="GtkTreeStore" id="tmPartitions">
|
||||
<columns>
|
||||
<!-- column-name colPartitionDevice -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colPartitionName -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colPartitionFileSystem -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colPartitionMountPoint -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colPartitionLabel -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colPartitionSize -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colPartitionSizeUsed -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colPartitionSizeUnused -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colPartitionFlags -->
|
||||
<column type="gchararray"/>
|
||||
</columns>
|
||||
</object>
|
||||
<object class="GtkWindow">
|
||||
<property name="can-focus">False</property>
|
||||
<child>
|
||||
<object class="GtkBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">False</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<child>
|
||||
<object class="GtkDrawingArea" id="cnvPartitions">
|
||||
<property name="name">MBS.Framework.UserInterface.CustomControl</property>
|
||||
<property name="height-request">96</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">False</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkScrolledWindow">
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
<property name="shadow-type">in</property>
|
||||
<child>
|
||||
<object class="GtkTreeView" id="tvPartitions">
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
<property name="model">tmPartitions</property>
|
||||
<child internal-child="selection">
|
||||
<object class="GtkTreeSelection"/>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcPartitionDevice">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Device</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">0</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcPartitionName">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Name</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">1</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcPartitionFileSystem">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">File System</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">2</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcPartitionMountPoint">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Mount Point</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">3</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcPartitionLabel">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Label</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">4</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcPartitionSize">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Size</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">5</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcPartitionSizeUsed">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Used</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">6</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcPartitionSizeUnused">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Unused</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">7</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcPartitionFlags">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Flags</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">8</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
||||
@ -11,11 +11,14 @@
|
||||
<Commands>
|
||||
<Command ID="PropertyListContextMenu_New_Property" Title="_Property" />
|
||||
<Command ID="PropertyListContextMenu_New_Group" Title="_Group" />
|
||||
<Command ID="PropertyListContextMenu_New_Comment" Title="_Comment" />
|
||||
|
||||
<Command ID="PropertyListContextMenu_New" Title="_New">
|
||||
<Items>
|
||||
<CommandReference CommandID="PropertyListContextMenu_New_Property" />
|
||||
<CommandReference CommandID="PropertyListContextMenu_New_Group" />
|
||||
<Separator />
|
||||
<CommandReference CommandID="PropertyListContextMenu_New_Comment" />
|
||||
</Items>
|
||||
</Command>
|
||||
|
||||
|
||||
@ -390,6 +390,8 @@
|
||||
<Content Include="Editors\Roland\VDrumKit\TD20\Sounds\Tom\TR808.uexml" />
|
||||
<Content Include="Editors\Roland\VDrumKit\TD20\Sounds\Tom\TR909.uexml" />
|
||||
<Content Include="Editors\Multimedia\Font\Bitmap\BitmapFontEditor.glade" />
|
||||
<Content Include="Editors\PartitionedFileSystem\PartitionedFileSystemEditor.glade" />
|
||||
<Content Include="Editors\PartitionedFileSystem\Commands.uexml" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Content Include="Configuration\Application.upl" />
|
||||
@ -454,6 +456,7 @@
|
||||
<Folder Include="Editors\Roland\VDrumKit\TD12\" />
|
||||
<Folder Include="Editors\Roland\VDrumKit\TD17\" />
|
||||
<Folder Include="Editors\Roland\VDrumKit\TD20EXP\" />
|
||||
<Folder Include="Editors\PartitionedFileSystem\" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Content Include="Templates\Project\Concertroid\Images\Concert.xcf" />
|
||||
|
||||
20
Libraries/UniversalEditor.Essential/Associations/MBR.uexml
Normal file
20
Libraries/UniversalEditor.Essential/Associations/MBR.uexml
Normal file
@ -0,0 +1,20 @@
|
||||
<?xml version="1.0" encoding="utf-8" ?>
|
||||
<UniversalEditor Version="4.0">
|
||||
<Associations>
|
||||
<Association>
|
||||
<Filters>
|
||||
<Filter Title="Master Boot Record (MBR) partitioned file system" HintComparison="FilterOnly">
|
||||
<FileNameFilters>
|
||||
<FileNameFilter>*.mbr</FileNameFilter>
|
||||
</FileNameFilters>
|
||||
</Filter>
|
||||
</Filters>
|
||||
<ObjectModels>
|
||||
<ObjectModel TypeName="UniversalEditor.ObjectModels.PartitionedFileSystem.PartitionedFileSystemObjectModel" />
|
||||
</ObjectModels>
|
||||
<DataFormats>
|
||||
<DataFormat TypeName="UniversalEditor.DataFormats.PartitionedFileSystem.MBR.MBRDataFormat" />
|
||||
</DataFormats>
|
||||
</Association>
|
||||
</Associations>
|
||||
</UniversalEditor>
|
||||
@ -0,0 +1,179 @@
|
||||
//
|
||||
// MBRDataFormat.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
using UniversalEditor.IO;
|
||||
using UniversalEditor.ObjectModels.PartitionedFileSystem;
|
||||
|
||||
namespace UniversalEditor.DataFormats.PartitionedFileSystem.MBR
|
||||
{
|
||||
public class MBRDataFormat : DataFormat
|
||||
{
|
||||
private static DataFormatReference _dfr = null;
|
||||
protected override DataFormatReference MakeReferenceInternal()
|
||||
{
|
||||
if (_dfr == null)
|
||||
{
|
||||
_dfr = base.MakeReferenceInternal();
|
||||
_dfr.Capabilities.Add(typeof(PartitionedFileSystemObjectModel), DataFormatCapabilities.All);
|
||||
}
|
||||
return _dfr;
|
||||
}
|
||||
|
||||
protected override void LoadInternal(ref ObjectModel objectModel)
|
||||
{
|
||||
PartitionedFileSystemObjectModel disk = objectModel as PartitionedFileSystemObjectModel;
|
||||
if (disk == null)
|
||||
throw new ObjectModelNotSupportedException();
|
||||
|
||||
disk.PartitionDataRequest += Disk_PartitionDataRequest;
|
||||
|
||||
Reader r = Accessor.Reader;
|
||||
|
||||
ushort newldrRecordSize = r.ReadUInt16();
|
||||
string newldr = r.ReadFixedLengthString(6);
|
||||
if (newldr.Equals("NEWLDR"))
|
||||
{
|
||||
// this is a NEWLDR MBR
|
||||
}
|
||||
else
|
||||
{
|
||||
// this is not a NEWLDR MBR
|
||||
r.Accessor.Seek(-8, SeekOrigin.Current);
|
||||
}
|
||||
|
||||
byte[] bootstrapCodeAreaPart1 = r.ReadBytes(218);
|
||||
ushort diskTimestampUnknown = r.ReadUInt16();
|
||||
byte originalPhysicalDrive = r.ReadByte();
|
||||
byte diskTimestampSeconds = r.ReadByte();
|
||||
byte diskTimestampMinutes = r.ReadByte();
|
||||
byte diskTimestampHours = r.ReadByte();
|
||||
|
||||
// wiki says also 222,but palimpsest writes 216
|
||||
byte[] bootstrapCodeAreaPart2 = r.ReadBytes(216);
|
||||
|
||||
// Disk signature (optional; UEFI, Linux, Windows NT family and other OSes)
|
||||
uint diskSignature = r.ReadUInt32();
|
||||
ushort copyProtectionFlag = r.ReadUInt16();
|
||||
if (copyProtectionFlag == 0x5A5A)
|
||||
{
|
||||
// lol
|
||||
}
|
||||
|
||||
MBRPartitionEntry partentry1 = ReadMBRPartitionEntry(r);
|
||||
if (partentry1.PartitionType != MBRPartitionType.None)
|
||||
{
|
||||
AddPartition(disk, partentry1);
|
||||
}
|
||||
MBRPartitionEntry partentry2 = ReadMBRPartitionEntry(r);
|
||||
if (partentry2.PartitionType != MBRPartitionType.None)
|
||||
{
|
||||
AddPartition(disk, partentry2);
|
||||
}
|
||||
MBRPartitionEntry partentry3 = ReadMBRPartitionEntry(r);
|
||||
if (partentry3.PartitionType != MBRPartitionType.None)
|
||||
{
|
||||
AddPartition(disk, partentry3);
|
||||
}
|
||||
MBRPartitionEntry partentry4 = ReadMBRPartitionEntry(r);
|
||||
if (partentry4.PartitionType != MBRPartitionType.None)
|
||||
{
|
||||
AddPartition(disk, partentry4);
|
||||
}
|
||||
|
||||
ushort bootSignature = r.ReadUInt16();
|
||||
if (bootSignature != 0xAA55)
|
||||
{
|
||||
Console.Error.WriteLine("ue: mbr: warning: not found 0xAA55 at offset 0x01FE");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void Disk_PartitionDataRequest(object sender, PartitionDataRequestEventArgs e)
|
||||
{
|
||||
long offset = e.Disk.CalculatePartitionOffset(e.Partition);
|
||||
long length = e.Disk.CalculatePartitionSize(e.Partition);
|
||||
|
||||
Accessor.Seek(offset, SeekOrigin.Begin);
|
||||
byte[] data = Accessor.Reader.ReadBytes(length);
|
||||
e.Data = data;
|
||||
}
|
||||
|
||||
private void AddPartition(PartitionedFileSystemObjectModel disk, MBRPartitionEntry partentry1)
|
||||
{
|
||||
Partition part = new Partition();
|
||||
part.FirstAbsoluteSectorLBA = partentry1.FirstAbsoluteSectorLBA;
|
||||
part.FirstAbsoluteSectorAddress = partentry1.FirstAbsoluteSectorAddress;
|
||||
part.LastAbsoluteSectorAddress = partentry1.LastAbsoluteSectorAddress;
|
||||
part.SectorCount = partentry1.SectorCount;
|
||||
part.PartitionType = MBRPartitionTypeToPartitionType(partentry1.PartitionType);
|
||||
|
||||
if ((partentry1.Status & MBRPartitionEntryStatus.Active) == MBRPartitionEntryStatus.Active)
|
||||
{
|
||||
part.IsBootable = true;
|
||||
}
|
||||
disk.Partitions.Add(part);
|
||||
}
|
||||
|
||||
private PartitionType MBRPartitionTypeToPartitionType(MBRPartitionType partitionType)
|
||||
{
|
||||
switch (partitionType)
|
||||
{
|
||||
case MBRPartitionType.FAT12: return PartitionType.FAT12;
|
||||
case MBRPartitionType.FAT32LBA: return PartitionType.FAT32LBA;
|
||||
case MBRPartitionType.IFS_HPFS_NTFS_exFAT_QNX: return PartitionType.IFS_HPFS_NTFS_exFAT_QNX;
|
||||
case MBRPartitionType.None: return PartitionType.None;
|
||||
case MBRPartitionType.XenixRoot: return PartitionType.XenixRoot;
|
||||
case MBRPartitionType.XenixUsr: return PartitionType.XenixUsr;
|
||||
}
|
||||
throw new ArgumentOutOfRangeException();
|
||||
}
|
||||
|
||||
private MBRPartitionEntry ReadMBRPartitionEntry(Reader r)
|
||||
{
|
||||
MBRPartitionEntry entry = new MBRPartitionEntry();
|
||||
entry.Status = (MBRPartitionEntryStatus)r.ReadByte();
|
||||
|
||||
entry.FirstAbsoluteSectorAddress = ReadCHSPartitionAddress(r);
|
||||
entry.PartitionType = (MBRPartitionType)r.ReadByte();
|
||||
entry.LastAbsoluteSectorAddress = ReadCHSPartitionAddress(r);
|
||||
entry.FirstAbsoluteSectorLBA = r.ReadUInt32();
|
||||
entry.SectorCount = r.ReadUInt32();
|
||||
return entry;
|
||||
}
|
||||
|
||||
private CHSPartitionAddress ReadCHSPartitionAddress(Reader r)
|
||||
{
|
||||
byte head = r.ReadByte();
|
||||
byte sectorAndCylinder1 = r.ReadByte();
|
||||
byte cylinder2 = r.ReadByte();
|
||||
return new CHSPartitionAddress(0, head, 0);
|
||||
}
|
||||
|
||||
protected override void SaveInternal(ObjectModel objectModel)
|
||||
{
|
||||
PartitionedFileSystemObjectModel part = objectModel as PartitionedFileSystemObjectModel;
|
||||
if (part == null)
|
||||
throw new ObjectModelNotSupportedException();
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,35 @@
|
||||
//
|
||||
// MBRPartitionEntry.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
using UniversalEditor.ObjectModels.PartitionedFileSystem;
|
||||
|
||||
namespace UniversalEditor.DataFormats.PartitionedFileSystem.MBR
|
||||
{
|
||||
public struct MBRPartitionEntry
|
||||
{
|
||||
public MBRPartitionEntryStatus Status;
|
||||
public CHSPartitionAddress FirstAbsoluteSectorAddress;
|
||||
public MBRPartitionType PartitionType;
|
||||
public CHSPartitionAddress LastAbsoluteSectorAddress;
|
||||
public uint FirstAbsoluteSectorLBA;
|
||||
public uint SectorCount;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,30 @@
|
||||
//
|
||||
// MBRPartitionEntryStatus.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
namespace UniversalEditor.DataFormats.PartitionedFileSystem.MBR
|
||||
{
|
||||
[Flags()]
|
||||
public enum MBRPartitionEntryStatus : byte
|
||||
{
|
||||
Inactive = 0x00,
|
||||
Active = 0x80
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,48 @@
|
||||
//
|
||||
// MBRPartitionType.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
namespace UniversalEditor.DataFormats.PartitionedFileSystem.MBR
|
||||
{
|
||||
public enum MBRPartitionType : byte
|
||||
{
|
||||
None = 0x00,
|
||||
/// <summary>
|
||||
/// FAT12 as primary partition in first physical 32 MB of disk or as
|
||||
/// logical drive anywhere on disk (else use 06h instead)
|
||||
/// </summary>
|
||||
FAT12 = 0x01,
|
||||
/// <summary>
|
||||
/// XENIX root
|
||||
/// </summary>
|
||||
XenixRoot = 0x02,
|
||||
/// <summary>
|
||||
/// XENIX usr
|
||||
/// </summary>
|
||||
XenixUsr = 0x03,
|
||||
|
||||
IFS_HPFS_NTFS_exFAT_QNX = 0x07,
|
||||
|
||||
/// <summary>
|
||||
/// FAT32 with Logical Block Addressing (LBA)
|
||||
/// </summary>
|
||||
FAT32LBA = 0x0C
|
||||
}
|
||||
}
|
||||
@ -69,12 +69,28 @@ namespace UniversalEditor.DataFormats.PropertyList.ExtensibleConfiguration
|
||||
if (nextString.StartsWith(Settings.SingleLineCommentStart))
|
||||
{
|
||||
string comment = tr.ReadLine();
|
||||
if (nextGroup != null)
|
||||
{
|
||||
nextGroup.Items.Add(new Comment(comment));
|
||||
}
|
||||
else
|
||||
{
|
||||
plom.Items.Add(new Comment(comment));
|
||||
}
|
||||
}
|
||||
if (nextString.StartsWith(Settings.MultiLineCommentStart))
|
||||
{
|
||||
string comment = tr.ReadUntil(Settings.MultiLineCommentEnd);
|
||||
string cmntend = tr.ReadFixedLengthString(Settings.MultiLineCommentEnd.Length);
|
||||
nextString = String.Empty;
|
||||
if (nextGroup != null)
|
||||
{
|
||||
nextGroup.Items.Add(new Comment(comment));
|
||||
}
|
||||
else
|
||||
{
|
||||
plom.Items.Add(new Comment(comment));
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
@ -193,13 +209,30 @@ namespace UniversalEditor.DataFormats.PropertyList.ExtensibleConfiguration
|
||||
tw.Write(Settings.PropertyNameSuffix);
|
||||
tw.Write(Settings.PropertyNameValueSeparator);
|
||||
tw.Write(Settings.PropertyValuePrefix);
|
||||
tw.WriteFixedLengthString((p as Property).Value.ToString());
|
||||
tw.WriteFixedLengthString((p as Property).Value?.ToString());
|
||||
tw.Write(Settings.PropertyValueSuffix);
|
||||
tw.WriteLine();
|
||||
}
|
||||
else if (p is Group)
|
||||
{
|
||||
this.WriteGroup(tw, (p as Group), 0);
|
||||
}
|
||||
else if (p is Comment)
|
||||
{
|
||||
Comment c = (Comment)p;
|
||||
if (c.Text.Contains("\r") || c.Text.Contains("\n"))
|
||||
{
|
||||
tw.WriteLine(Settings.MultiLineCommentStart);
|
||||
tw.WriteLine(c.Text);
|
||||
tw.WriteLine(Settings.MultiLineCommentEnd);
|
||||
}
|
||||
else
|
||||
{
|
||||
tw.Write(Settings.SingleLineCommentStart);
|
||||
tw.Write(' ');
|
||||
tw.WriteLine(c.Text);
|
||||
}
|
||||
}
|
||||
}
|
||||
tw.Flush();
|
||||
tw.Close();
|
||||
|
||||
@ -0,0 +1,37 @@
|
||||
//
|
||||
// CHSPartitionAddress.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
namespace UniversalEditor.ObjectModels.PartitionedFileSystem
|
||||
{
|
||||
public struct CHSPartitionAddress
|
||||
{
|
||||
public byte Cylinder { get; }
|
||||
public byte Head { get; }
|
||||
public byte Sector { get; }
|
||||
|
||||
public CHSPartitionAddress(byte cylinder, byte head, byte sector)
|
||||
{
|
||||
this.Cylinder = cylinder;
|
||||
this.Head = head;
|
||||
this.Sector = sector;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,50 @@
|
||||
//
|
||||
// Partition.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
using UniversalEditor.DataFormats.PartitionedFileSystem.MBR;
|
||||
|
||||
namespace UniversalEditor.ObjectModels.PartitionedFileSystem
|
||||
{
|
||||
public class Partition : ICloneable
|
||||
{
|
||||
public class PartitionCollection
|
||||
: System.Collections.ObjectModel.Collection<Partition>
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
|
||||
public bool IsBootable { get; set; } = false;
|
||||
|
||||
public long FirstAbsoluteSectorLBA { get; set; }
|
||||
public CHSPartitionAddress FirstAbsoluteSectorAddress { get; set; }
|
||||
public CHSPartitionAddress LastAbsoluteSectorAddress { get; set; }
|
||||
public uint SectorCount { get; set; }
|
||||
public PartitionType PartitionType { get; set; }
|
||||
|
||||
public object Clone()
|
||||
{
|
||||
Partition clone = new Partition();
|
||||
clone.IsBootable = IsBootable;
|
||||
return clone;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,37 @@
|
||||
//
|
||||
// PartitionDataRequestEventArgs.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
using UniversalEditor.ObjectModels.FileSystem;
|
||||
|
||||
namespace UniversalEditor.ObjectModels.PartitionedFileSystem
|
||||
{
|
||||
public class PartitionDataRequestEventArgs : DataRequestEventArgs
|
||||
{
|
||||
public PartitionedFileSystemObjectModel Disk { get; }
|
||||
public Partition Partition { get; }
|
||||
|
||||
public PartitionDataRequestEventArgs(PartitionedFileSystemObjectModel disk, Partition partition)
|
||||
{
|
||||
Disk = disk;
|
||||
Partition = partition;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,28 @@
|
||||
//
|
||||
// PartitionFlags.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
namespace UniversalEditor.ObjectModels.PartitionedFileSystem
|
||||
{
|
||||
[Flags]
|
||||
public enum PartitionFlags
|
||||
{
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,45 @@
|
||||
//
|
||||
// PartitionType.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
namespace UniversalEditor.ObjectModels.PartitionedFileSystem
|
||||
{
|
||||
public enum PartitionType
|
||||
{
|
||||
None = 0,
|
||||
/// <summary>
|
||||
/// FAT12 as primary partition in first physical 32 MB of disk or as
|
||||
/// logical drive anywhere on disk (else use 06h instead)
|
||||
/// </summary>
|
||||
FAT12,
|
||||
/// <summary>
|
||||
/// XENIX root
|
||||
/// </summary>
|
||||
XenixRoot,
|
||||
/// <summary>
|
||||
/// XENIX usr
|
||||
/// </summary>
|
||||
XenixUsr,
|
||||
|
||||
IFS_HPFS_NTFS_exFAT_QNX,
|
||||
|
||||
FAT32LBA
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,86 @@
|
||||
//
|
||||
// PartitionedFileSystemObjectModel.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
using UniversalEditor.ObjectModels.FileSystem;
|
||||
|
||||
namespace UniversalEditor.ObjectModels.PartitionedFileSystem
|
||||
{
|
||||
public class PartitionedFileSystemObjectModel : ObjectModel
|
||||
{
|
||||
private static ObjectModelReference _omr = null;
|
||||
|
||||
public int SectorSize { get; set; } = 512;
|
||||
|
||||
public Partition.PartitionCollection Partitions { get; } = new Partition.PartitionCollection();
|
||||
|
||||
public long CalculatePartitionSize(Partition part)
|
||||
{
|
||||
return part.SectorCount * SectorSize;
|
||||
}
|
||||
|
||||
protected override ObjectModelReference MakeReferenceInternal()
|
||||
{
|
||||
if (_omr == null)
|
||||
{
|
||||
_omr = base.MakeReferenceInternal();
|
||||
_omr.Path = new string[] { "General", "Partitioned file system" };
|
||||
}
|
||||
return _omr;
|
||||
}
|
||||
|
||||
public override void Clear()
|
||||
{
|
||||
Partitions.Clear();
|
||||
}
|
||||
|
||||
public override void CopyTo(ObjectModel where)
|
||||
{
|
||||
PartitionedFileSystemObjectModel clone = where as PartitionedFileSystemObjectModel;
|
||||
if (clone == null)
|
||||
throw new ObjectModelNotSupportedException();
|
||||
|
||||
foreach (Partition p in Partitions)
|
||||
{
|
||||
clone.Partitions.Add(p.Clone() as Partition);
|
||||
}
|
||||
}
|
||||
|
||||
public event EventHandler<PartitionDataRequestEventArgs> PartitionDataRequest;
|
||||
protected virtual void OnPartitionDataRequest(PartitionDataRequestEventArgs e)
|
||||
{
|
||||
PartitionDataRequest?.Invoke(this, e);
|
||||
}
|
||||
|
||||
public byte[] GetPartitionData(Partition part)
|
||||
{
|
||||
PartitionDataRequestEventArgs e = new PartitionDataRequestEventArgs(this, part);
|
||||
OnPartitionDataRequest(e);
|
||||
|
||||
return e.Data;
|
||||
}
|
||||
|
||||
public long CalculatePartitionOffset(Partition partition)
|
||||
{
|
||||
long firstAbsoluteSectorLBA = partition.FirstAbsoluteSectorLBA;
|
||||
return firstAbsoluteSectorLBA * SectorSize;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,48 @@
|
||||
//
|
||||
// Comment.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
namespace UniversalEditor.ObjectModels.PropertyList
|
||||
{
|
||||
public class Comment : PropertyListItem
|
||||
{
|
||||
public string Text { get; set; }
|
||||
|
||||
public override object Clone()
|
||||
{
|
||||
Comment clone = new Comment();
|
||||
clone.Text = Text;
|
||||
return clone;
|
||||
}
|
||||
|
||||
public override void Combine(PropertyListItem item)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public Comment()
|
||||
{
|
||||
}
|
||||
public Comment(string text)
|
||||
{
|
||||
Text = text;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -228,6 +228,17 @@
|
||||
<Compile Include="ObjectModels\Markup\IMarkupElementContainer.cs" />
|
||||
<Compile Include="ObjectModels\Markup\MarkupDefinition.cs" />
|
||||
<Compile Include="ObjectModels\FileSystem\FileSources\ObjectModelFileSource.cs" />
|
||||
<Compile Include="ObjectModels\PropertyList\Comment.cs" />
|
||||
<Compile Include="DataFormats\PartitionedFileSystem\MBR\MBRDataFormat.cs" />
|
||||
<Compile Include="ObjectModels\PartitionedFileSystem\PartitionedFileSystemObjectModel.cs" />
|
||||
<Compile Include="DataFormats\PartitionedFileSystem\MBR\MBRPartitionEntry.cs" />
|
||||
<Compile Include="DataFormats\PartitionedFileSystem\MBR\MBRPartitionEntryStatus.cs" />
|
||||
<Compile Include="DataFormats\PartitionedFileSystem\MBR\MBRPartitionType.cs" />
|
||||
<Compile Include="ObjectModels\PartitionedFileSystem\Partition.cs" />
|
||||
<Compile Include="ObjectModels\PartitionedFileSystem\PartitionFlags.cs" />
|
||||
<Compile Include="ObjectModels\PartitionedFileSystem\CHSPartitionAddress.cs" />
|
||||
<Compile Include="ObjectModels\PartitionedFileSystem\PartitionType.cs" />
|
||||
<Compile Include="ObjectModels\PartitionedFileSystem\PartitionDataRequestEventArgs.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\UniversalEditor.Core\UniversalEditor.Core.csproj">
|
||||
@ -275,10 +286,14 @@
|
||||
<Folder Include="DataFormats\Package\OpenDocument\Internal\ManifestXML\" />
|
||||
<Folder Include="DataFormats\Markup\BML\" />
|
||||
<Folder Include="DataFormats\Markup\BML\Internal\" />
|
||||
<Folder Include="DataFormats\PartitionedFileSystem\" />
|
||||
<Folder Include="DataFormats\PartitionedFileSystem\MBR\" />
|
||||
<Folder Include="ObjectModels\PartitionedFileSystem\" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<EmbeddedResource Include="Associations\PlainText.uexml" />
|
||||
<EmbeddedResource Include="Associations\BML.uexml" />
|
||||
<EmbeddedResource Include="Associations\MBR.uexml" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="ObjectModels\Chunked\RIFFMetadata.cs">
|
||||
|
||||
@ -0,0 +1,165 @@
|
||||
//
|
||||
// PartitionedFileSystemEditor.cs
|
||||
//
|
||||
// Author:
|
||||
// beckermj <>
|
||||
//
|
||||
// Copyright (c) 2023 ${CopyrightHolder}
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
using System;
|
||||
using MBS.Framework;
|
||||
using MBS.Framework.UserInterface;
|
||||
using MBS.Framework.UserInterface.Controls.ListView;
|
||||
using MBS.Framework.UserInterface.Dialogs;
|
||||
using UniversalEditor.ObjectModels.PartitionedFileSystem;
|
||||
using UniversalEditor.UserInterface;
|
||||
|
||||
namespace UniversalEditor.Editors.PartitionedFileSystem
|
||||
{
|
||||
[ContainerLayout("~/Editors/PartitionedFileSystem/PartitionedFileSystemEditor.glade")]
|
||||
public class PartitionedFileSystemEditor : Editor
|
||||
{
|
||||
private CustomControl cnvPartitions;
|
||||
private ListViewControl tvPartitions;
|
||||
|
||||
private static EditorReference _er = null;
|
||||
public override EditorReference MakeReference()
|
||||
{
|
||||
if (_er == null)
|
||||
{
|
||||
_er = base.MakeReference();
|
||||
_er.SupportedObjectModels.Add(typeof(PartitionedFileSystemObjectModel));
|
||||
}
|
||||
return _er;
|
||||
}
|
||||
|
||||
public override void UpdateSelections()
|
||||
{
|
||||
}
|
||||
|
||||
protected override Selection CreateSelectionInternal(object content)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
protected override void OnCreated(EventArgs e)
|
||||
{
|
||||
base.OnCreated(e);
|
||||
|
||||
OnObjectModelChanged(e);
|
||||
|
||||
Context.AttachCommandEventHandler("PartitionedFileSystemEditor_tvPartitions_ContextMenu_CopyTo", PartitionedFileSystemEditor_tvPartitions_ContextMenu_CopyTo);
|
||||
}
|
||||
|
||||
private void PartitionedFileSystemEditor_tvPartitions_ContextMenu_CopyTo(object sender, EventArgs e)
|
||||
{
|
||||
PartitionedFileSystemObjectModel disk = ObjectModel as PartitionedFileSystemObjectModel;
|
||||
if (disk == null)
|
||||
return;
|
||||
|
||||
if (tvPartitions.SelectedRows.Count == 1)
|
||||
{
|
||||
FileDialog dlg = new FileDialog();
|
||||
dlg.Mode = FileDialogMode.Save;
|
||||
|
||||
if (dlg.ShowDialog() == DialogResult.OK)
|
||||
{
|
||||
Partition part = tvPartitions.SelectedRows[0].GetExtraData<Partition>("part");
|
||||
byte[] data = disk.GetPartitionData(part);
|
||||
|
||||
System.IO.File.WriteAllBytes(dlg.SelectedFileName, data);
|
||||
}
|
||||
}
|
||||
else if (tvPartitions.SelectedRows.Count > 1)
|
||||
{
|
||||
FileDialog dlg = new FileDialog();
|
||||
dlg.Mode = FileDialogMode.SelectFolder;
|
||||
if (dlg.ShowDialog() == DialogResult.OK)
|
||||
{
|
||||
string dirname = dlg.SelectedPath;
|
||||
if (!System.IO.Directory.Exists(dirname))
|
||||
{
|
||||
System.IO.Directory.CreateDirectory(dirname);
|
||||
}
|
||||
|
||||
Partition part = tvPartitions.SelectedRows[0].GetExtraData<Partition>("part");
|
||||
byte[] data = disk.GetPartitionData(part);
|
||||
|
||||
System.IO.File.WriteAllBytes(dlg.SelectedFileName, data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
[EventHandler(nameof(tvPartitions), nameof(Control.BeforeContextMenu))]
|
||||
private void tvPartitions_BeforeContextMenu(object sender, EventArgs e)
|
||||
{
|
||||
tvPartitions.ContextMenuCommandID = "PartitionedFileSystemEditor_tvPartitions_ContextMenu_Unselected";
|
||||
}
|
||||
[EventHandler(nameof(tvPartitions), nameof(ListViewControl.SelectionChanged))]
|
||||
private void tvPartitions_SelectionChanged(object sender, EventArgs e)
|
||||
{
|
||||
Context.Commands["PartitionedFileSystemEditor_tvPartitions_ContextMenu_CopyTo"].Enabled = (tvPartitions.SelectedRows.Count == 1);
|
||||
}
|
||||
|
||||
protected override void OnObjectModelChanged(EventArgs e)
|
||||
{
|
||||
if (!IsCreated)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
PartitionedFileSystemObjectModel disk = ObjectModel as PartitionedFileSystemObjectModel;
|
||||
if (disk == null)
|
||||
return;
|
||||
|
||||
for (int i = 0; i < disk.Partitions.Count; i++)
|
||||
{
|
||||
TreeModelRow rowPartition = new TreeModelRow(new TreeModelRowColumn[]
|
||||
{
|
||||
new TreeModelRowColumn(tvPartitions.Model.Columns[0], String.Format("@dev@{0}", i)),
|
||||
new TreeModelRowColumn(tvPartitions.Model.Columns[1], String.Empty /* Name */),
|
||||
new TreeModelRowColumn(tvPartitions.Model.Columns[2], String.Empty /* File System */),
|
||||
new TreeModelRowColumn(tvPartitions.Model.Columns[3], String.Empty /* Mount Point */),
|
||||
new TreeModelRowColumn(tvPartitions.Model.Columns[4], String.Empty /* Label */),
|
||||
new TreeModelRowColumn(tvPartitions.Model.Columns[5], UserInterface.Common.FileInfo.FormatSize(disk.CalculatePartitionSize(disk.Partitions[i]))),
|
||||
new TreeModelRowColumn(tvPartitions.Model.Columns[6], UserInterface.Common.FileInfo.FormatSize(0) /* Used */),
|
||||
new TreeModelRowColumn(tvPartitions.Model.Columns[7], UserInterface.Common.FileInfo.FormatSize(0) /* Unused */),
|
||||
new TreeModelRowColumn(tvPartitions.Model.Columns[8], Flagstr(disk.Partitions[i]))
|
||||
|
||||
});
|
||||
rowPartition.SetExtraData<Partition>("part", disk.Partitions[i]);
|
||||
tvPartitions.Model.Rows.Add(rowPartition);
|
||||
}
|
||||
|
||||
|
||||
base.OnObjectModelChanged(e);
|
||||
}
|
||||
|
||||
private string Flagstr(Partition partition)
|
||||
{
|
||||
System.Text.StringBuilder sb = new System.Text.StringBuilder();
|
||||
|
||||
if (partition.IsBootable)
|
||||
{
|
||||
sb.Append("boot,");
|
||||
}
|
||||
|
||||
string flagstr = sb.ToString();
|
||||
if (flagstr.EndsWith(","))
|
||||
flagstr = flagstr.Substring(0, flagstr.Length - 1);
|
||||
return flagstr;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -59,6 +59,7 @@ namespace UniversalEditor.Editors.PropertyList
|
||||
{
|
||||
Group group = row.GetExtraData<Group>("group");
|
||||
Property property = row.GetExtraData<Property>("property");
|
||||
Comment comment = row.GetExtraData<Comment>("comment");
|
||||
if (group != null)
|
||||
{
|
||||
Selections.Add(new PropertyListSelection(ObjectModel as PropertyListObjectModel, group));
|
||||
@ -67,6 +68,10 @@ namespace UniversalEditor.Editors.PropertyList
|
||||
{
|
||||
Selections.Add(new PropertyListSelection(ObjectModel as PropertyListObjectModel, property));
|
||||
}
|
||||
else if (comment != null)
|
||||
{
|
||||
Selections.Add(new PropertyListSelection(ObjectModel as PropertyListObjectModel, comment));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -74,8 +79,11 @@ namespace UniversalEditor.Editors.PropertyList
|
||||
{
|
||||
base.OnCreated(e);
|
||||
|
||||
tv.BeforeContextMenu += tv_BeforeContextMenu;
|
||||
|
||||
Context.AttachCommandEventHandler("PropertyListContextMenu_New_Property", PropertyListContextMenu_New_Property);
|
||||
Context.AttachCommandEventHandler("PropertyListContextMenu_New_Group", PropertyListContextMenu_New_Group);
|
||||
Context.AttachCommandEventHandler("PropertyListContextMenu_New_Comment", PropertyListContextMenu_New_Comment);
|
||||
|
||||
OnObjectModelChanged(EventArgs.Empty);
|
||||
}
|
||||
@ -91,6 +99,7 @@ namespace UniversalEditor.Editors.PropertyList
|
||||
{
|
||||
Group group = e.Row.GetExtraData<Group>("group");
|
||||
Property property = e.Row.GetExtraData<Property>("property");
|
||||
Comment comment = e.Row.GetExtraData<Comment>("comment");
|
||||
|
||||
if (e.NewValue == e.OldValue)
|
||||
return;
|
||||
@ -120,6 +129,10 @@ namespace UniversalEditor.Editors.PropertyList
|
||||
{
|
||||
property.Value = e.NewValue;
|
||||
}
|
||||
else if (comment != null)
|
||||
{
|
||||
comment.Text = e.NewValue?.ToString();
|
||||
}
|
||||
}
|
||||
|
||||
EndEdit();
|
||||
@ -149,17 +162,33 @@ namespace UniversalEditor.Editors.PropertyList
|
||||
return lastIndex + 1;
|
||||
}
|
||||
|
||||
private void PropertyListContextMenu_New_Property(object sender, EventArgs e)
|
||||
private IPropertyListContainer GetSelectedParent(out TreeModelRow rowParent)
|
||||
{
|
||||
Property p = new Property();
|
||||
|
||||
TreeModelRow rowParent = null;
|
||||
rowParent = null;
|
||||
IPropertyListContainer parent = ObjectModel as PropertyListObjectModel;
|
||||
if (tv.SelectedRows.Count == 1)
|
||||
{
|
||||
rowParent = tv.SelectedRows[0];
|
||||
parent = rowParent.GetExtraData<Group>("group");
|
||||
while (parent == null)
|
||||
{
|
||||
rowParent = rowParent.ParentRow;
|
||||
if (rowParent == null)
|
||||
{
|
||||
parent = ObjectModel as PropertyListObjectModel;
|
||||
break;
|
||||
}
|
||||
parent = rowParent.GetExtraData<Group>("group");
|
||||
}
|
||||
}
|
||||
return parent;
|
||||
}
|
||||
|
||||
private void PropertyListContextMenu_New_Property(object sender, EventArgs e)
|
||||
{
|
||||
Property p = new Property();
|
||||
|
||||
IPropertyListContainer parent = GetSelectedParent(out TreeModelRow rowParent);
|
||||
|
||||
p.Name = String.Format("New Property {0}", GetNextIndex<Property>());
|
||||
parent.Items.Add(p);
|
||||
@ -169,18 +198,22 @@ namespace UniversalEditor.Editors.PropertyList
|
||||
{
|
||||
Group p = new Group();
|
||||
|
||||
TreeModelRow rowParent = null;
|
||||
IPropertyListContainer parent = ObjectModel as PropertyListObjectModel;
|
||||
if (tv.SelectedRows.Count == 1)
|
||||
{
|
||||
rowParent = tv.SelectedRows[0];
|
||||
parent = rowParent.GetExtraData<Group>("group");
|
||||
}
|
||||
IPropertyListContainer parent = GetSelectedParent(out TreeModelRow rowParent);
|
||||
|
||||
p.Name = String.Format("New Group {0}", GetNextIndex<Group>());
|
||||
parent.Items.Add(p);
|
||||
RecursiveAddGroup(p, rowParent);
|
||||
}
|
||||
private void PropertyListContextMenu_New_Comment(object sender, EventArgs e)
|
||||
{
|
||||
Comment p = new Comment();
|
||||
|
||||
IPropertyListContainer parent = GetSelectedParent(out TreeModelRow rowParent);
|
||||
|
||||
p.Text = "Your comment here";
|
||||
parent.Items.Add(p);
|
||||
RecursiveAddComment(p, rowParent);
|
||||
}
|
||||
|
||||
[EventHandler(nameof(tv), nameof(ListViewControl.SelectionChanged))]
|
||||
private void tv_SelectionChanged(object sender, EventArgs e)
|
||||
@ -277,5 +310,24 @@ namespace UniversalEditor.Editors.PropertyList
|
||||
}
|
||||
row.SetExtraData<Group>("group", g);
|
||||
}
|
||||
private void RecursiveAddComment(Comment p, TreeModelRow parent = null)
|
||||
{
|
||||
TreeModelRow row = new TreeModelRow(new TreeModelRowColumn[]
|
||||
{
|
||||
new TreeModelRowColumn(tm.Columns[0], "//"),
|
||||
new TreeModelRowColumn(tm.Columns[1], p.Text),
|
||||
new TreeModelRowColumn(tm.Columns[2], Image.FromStock(StockType.Info, 16))
|
||||
});
|
||||
|
||||
if (parent == null)
|
||||
{
|
||||
tm.Rows.Add(row);
|
||||
}
|
||||
else
|
||||
{
|
||||
parent.Rows.Add(row);
|
||||
}
|
||||
row.SetExtraData<Comment>("comment", p);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -141,6 +141,7 @@
|
||||
<Compile Include="PanelReference.cs" />
|
||||
<Compile Include="Editors\Text\Formatted\FormattedTextEditor.cs" />
|
||||
<Compile Include="Panels\OutputWindowPanel.cs" />
|
||||
<Compile Include="Editors\PartitionedFileSystem\PartitionedFileSystemEditor.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<BootstrapperPackage Include="Microsoft.Net.Client.3.5">
|
||||
@ -201,6 +202,7 @@
|
||||
<Folder Include="SettingsProviders\" />
|
||||
<Folder Include="Editors\Database\Dialogs\" />
|
||||
<Folder Include="Editors\Text\Formatted\" />
|
||||
<Folder Include="Editors\PartitionedFileSystem\" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<EmbeddedResource Include="SettingsProviders\DefaultSettingsProvider.xml" />
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user