implement a UWT-based RIFF chunked document editor
This commit is contained in:
parent
8b8213824b
commit
be832ce119
@ -0,0 +1,34 @@
|
||||
<UniversalEditor Version="5.0">
|
||||
<Editors>
|
||||
<Editor ID="{217A8EF5-BD32-4AC9-8A33-E14AFD290213}" TypeName="UniversalEditor.Editors.RIFF.RIFFEditor">
|
||||
<Commands>
|
||||
<Command ID="RIFFEditorContextMenu_Add_NewDataChunk" Title="New _Data Chunk..." />
|
||||
<Command ID="RIFFEditorContextMenu_Add_ExistingFile" Title="Data Chunk from E_xisting File..." />
|
||||
<Command ID="RIFFEditorContextMenu_Add_NewGroupChunk" Title="New _Group Chunk..." />
|
||||
<Command ID="RIFFEditorContextMenu_Add" Title="A_dd">
|
||||
<Items>
|
||||
<CommandReference CommandID="RIFFEditorContextMenu_Add_NewDataChunk" />
|
||||
<CommandReference CommandID="RIFFEditorContextMenu_Add_ExistingFile" />
|
||||
<Separator />
|
||||
<CommandReference CommandID="RIFFEditorContextMenu_Add_NewGroupChunk" />
|
||||
</Items>
|
||||
</Command>
|
||||
<Command ID="RIFFEditorContextMenu_Export" Title="E_xport..." />
|
||||
|
||||
<Command ID="RIFFEditorContextMenu">
|
||||
<Items>
|
||||
<CommandReference CommandID="RIFFEditorContextMenu_Add" />
|
||||
<CommandReference CommandID="RIFFEditorContextMenu_Export" />
|
||||
<Separator />
|
||||
<CommandReference CommandID="FileProperties" />
|
||||
</Items>
|
||||
</Command>
|
||||
</Commands>
|
||||
<Layout FileName="RIFFEditor.glade">
|
||||
<Controls>
|
||||
<Control ID="tv" ContextMenuCommandID="RIFFEditorContextMenu" />
|
||||
</Controls>
|
||||
</Layout>
|
||||
</Editor>
|
||||
</Editors>
|
||||
</UniversalEditor>
|
||||
@ -0,0 +1,283 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.22.1 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.20"/>
|
||||
<object class="GtkListStore" id="tmChunkType">
|
||||
<columns>
|
||||
<!-- column-name colChunkTypeName -->
|
||||
<column type="gchararray"/>
|
||||
</columns>
|
||||
<data>
|
||||
<row>
|
||||
<col id="0" translatable="yes">Data</col>
|
||||
</row>
|
||||
<row>
|
||||
<col id="0" translatable="yes">Group</col>
|
||||
</row>
|
||||
</data>
|
||||
</object>
|
||||
<object class="GtkDialog" id="RIFFChunkPropertiesDialog">
|
||||
<property name="can_focus">False</property>
|
||||
<property name="title" translatable="yes">RIFF Chunk Properties</property>
|
||||
<property name="type_hint">dialog</property>
|
||||
<child>
|
||||
<placeholder/>
|
||||
</child>
|
||||
<child internal-child="vbox">
|
||||
<object class="GtkBox">
|
||||
<property name="can_focus">False</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<property name="spacing">2</property>
|
||||
<child internal-child="action_area">
|
||||
<object class="GtkButtonBox">
|
||||
<property name="can_focus">False</property>
|
||||
<property name="layout_style">end</property>
|
||||
<child>
|
||||
<object class="GtkButton">
|
||||
<property name="label">gtk-ok</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkButton" id="button1">
|
||||
<property name="label">gtk-cancel</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">False</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkGrid">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="hexpand">True</property>
|
||||
<property name="vexpand">True</property>
|
||||
<child>
|
||||
<object class="GtkLabel">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Chunk _type</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="xalign">0</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="left_attach">0</property>
|
||||
<property name="top_attach">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkComboBox" id="cboChunkType">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="hexpand">True</property>
|
||||
<property name="model">tmChunkType</property>
|
||||
<property name="active">0</property>
|
||||
<property name="id_column">0</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">0</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="left_attach">1</property>
|
||||
<property name="top_attach">0</property>
|
||||
<property name="width">2</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkLabel" id="lblChunkID">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Chunk _ID</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="xalign">0</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="left_attach">0</property>
|
||||
<property name="top_attach">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkLabel" id="lblGroupID">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">_Type ID</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="xalign">0</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="left_attach">0</property>
|
||||
<property name="top_attach">2</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkExpander">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="expanded">True</property>
|
||||
<property name="label_fill">True</property>
|
||||
<property name="resize_toplevel">True</property>
|
||||
<child>
|
||||
<object class="GtkBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<child>
|
||||
<object class="GtkBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkButton" id="cmdImportData">
|
||||
<property name="label" translatable="yes">Import...</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">True</property>
|
||||
<property name="use_underline">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkButton" id="cmdImportData1">
|
||||
<property name="label" translatable="yes">Export...</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">True</property>
|
||||
<property name="use_underline">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkDrawingArea" id="hexData">
|
||||
<property name="name">MBS.Framework.UserInterface.Controls.HexEditor.HexEditorControl</property>
|
||||
<property name="width_request">400</property>
|
||||
<property name="height_request">200</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child type="label">
|
||||
<object class="GtkLabel">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Data</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="left_attach">0</property>
|
||||
<property name="top_attach">3</property>
|
||||
<property name="width">3</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkComboBox" id="cboTypeID">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="model">tmChunkTypeIDs</property>
|
||||
<property name="has_entry">True</property>
|
||||
<property name="entry_text_column">0</property>
|
||||
<child internal-child="entry">
|
||||
<object class="GtkEntry">
|
||||
<property name="can_focus">True</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="left_attach">1</property>
|
||||
<property name="top_attach">2</property>
|
||||
<property name="width">2</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkEntry" id="txtChunkID">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="left_attach">1</property>
|
||||
<property name="top_attach">1</property>
|
||||
<property name="width">2</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<action-widgets>
|
||||
<action-widget response="-6">button1</action-widget>
|
||||
</action-widgets>
|
||||
</object>
|
||||
<object class="GtkListStore" id="tmChunkTypeIDs">
|
||||
<columns>
|
||||
<!-- column-name colChunkID -->
|
||||
<column type="gchararray"/>
|
||||
</columns>
|
||||
<data>
|
||||
<row>
|
||||
<col id="0" translatable="yes">RIFF</col>
|
||||
</row>
|
||||
<row>
|
||||
<col id="0" translatable="yes">RIFX</col>
|
||||
</row>
|
||||
<row>
|
||||
<col id="0" translatable="yes">FORM</col>
|
||||
</row>
|
||||
<row>
|
||||
<col id="0" translatable="yes">LIST</col>
|
||||
</row>
|
||||
<row>
|
||||
<col id="0" translatable="yes">CAT </col>
|
||||
</row>
|
||||
</data>
|
||||
</object>
|
||||
</interface>
|
||||
@ -0,0 +1,83 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.22.1 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.20"/>
|
||||
<object class="GtkTreeStore" id="tm">
|
||||
<columns>
|
||||
<!-- column-name colChunkID -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colChunkType -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name colChunkLength -->
|
||||
<column type="gchararray"/>
|
||||
</columns>
|
||||
</object>
|
||||
<object class="GtkWindow">
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<placeholder/>
|
||||
</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="tv">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="model">tm</property>
|
||||
<child internal-child="selection">
|
||||
<object class="GtkTreeSelection"/>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcChunkID">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Chunk ID</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<property name="sort_column_id">0</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">0</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcChunkType">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Type</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<property name="sort_column_id">1</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">1</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn" id="tvcChunkLength">
|
||||
<property name="resizable">True</property>
|
||||
<property name="title" translatable="yes">Length</property>
|
||||
<property name="clickable">True</property>
|
||||
<property name="reorderable">True</property>
|
||||
<property name="sort_column_id">2</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">2</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
||||
@ -723,6 +723,9 @@
|
||||
<Content Include="Editors\PropertyList\PropertyListEditor.glade" />
|
||||
<Content Include="Editors\FileSystem\FileSystemEditor.glade" />
|
||||
<Content Include="Dialogs\ManageBookmarksDialog.glade" />
|
||||
<Content Include="Editors\RIFF\RIFFEditor.glade" />
|
||||
<Content Include="Editors\RIFF\Commands.uexml" />
|
||||
<Content Include="Editors\RIFF\Dialogs\RIFFChunkPropertiesDialog.glade" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Content Include="Configuration\Application.upl" />
|
||||
@ -776,6 +779,7 @@
|
||||
<Folder Include="Extensions\GameDeveloper\Extensions\Webfoot\" />
|
||||
<Folder Include="Extensions\GameDeveloper\Extensions\Webfoot\Associations\" />
|
||||
<Folder Include="Extensions\GameDeveloper\Extensions\CRI\" />
|
||||
<Folder Include="Editors\RIFF\" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Content Include="Extensions\SoftwareDeveloper\Templates\Project\Software Development\Arduino\Images\Blink.xcf" />
|
||||
|
||||
@ -24,7 +24,7 @@ namespace UniversalEditor.ObjectModels.Chunked
|
||||
/// <summary>
|
||||
/// Provides an <see cref="ObjectModel" /> for manipulating chunked binary files (such as RIFF).
|
||||
/// </summary>
|
||||
public class ChunkedObjectModel : ObjectModel
|
||||
public class ChunkedObjectModel : ObjectModel, IChunkContainer
|
||||
{
|
||||
private ObjectModelReference _omr = null;
|
||||
protected override ObjectModelReference MakeReferenceInternal()
|
||||
@ -44,19 +44,23 @@ namespace UniversalEditor.ObjectModels.Chunked
|
||||
public RIFFMetadataItem.RIFFMetadataItemCollection Information { get { return mvarInformation; } }
|
||||
|
||||
#endif
|
||||
|
||||
private RIFFChunk.RIFFChunkCollection mvarChunks = new RIFFChunk.RIFFChunkCollection();
|
||||
public RIFFChunk.RIFFChunkCollection Chunks { get { return mvarChunks; } }
|
||||
|
||||
public ChunkedObjectModel()
|
||||
{
|
||||
Chunks = new RIFFChunk.RIFFChunkCollection(this);
|
||||
}
|
||||
|
||||
public RIFFChunk.RIFFChunkCollection Chunks { get; private set; } = null;
|
||||
|
||||
public override void Clear()
|
||||
{
|
||||
mvarChunks.Clear();
|
||||
Chunks.Clear();
|
||||
}
|
||||
|
||||
public override void CopyTo(ObjectModel where)
|
||||
{
|
||||
ChunkedObjectModel clone = where as ChunkedObjectModel;
|
||||
foreach (RIFFChunk chunk in mvarChunks)
|
||||
foreach (RIFFChunk chunk in Chunks)
|
||||
{
|
||||
clone.Chunks.Add(chunk.Clone() as RIFFChunk);
|
||||
}
|
||||
|
||||
@ -0,0 +1,28 @@
|
||||
//
|
||||
// IChunkContainer.cs
|
||||
//
|
||||
// Author:
|
||||
// Michael Becker <alcexhim@gmail.com>
|
||||
//
|
||||
// Copyright (c) 2020 Mike Becker's Software
|
||||
//
|
||||
// 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.Chunked
|
||||
{
|
||||
public interface IChunkContainer
|
||||
{
|
||||
RIFFChunk.RIFFChunkCollection Chunks { get; }
|
||||
}
|
||||
}
|
||||
@ -28,8 +28,16 @@ namespace UniversalEditor.ObjectModels.Chunked
|
||||
/// </summary>
|
||||
public abstract class RIFFChunk : ICloneable
|
||||
{
|
||||
public IChunkContainer Parent { get; private set; } = null;
|
||||
|
||||
public class RIFFChunkCollection : System.Collections.ObjectModel.Collection<RIFFChunk>
|
||||
{
|
||||
private IChunkContainer _parent = null;
|
||||
public RIFFChunkCollection(IChunkContainer parent)
|
||||
{
|
||||
_parent = parent;
|
||||
}
|
||||
|
||||
public RIFFChunk this[string Name]
|
||||
{
|
||||
get
|
||||
@ -59,6 +67,31 @@ namespace UniversalEditor.ObjectModels.Chunked
|
||||
base.Add(chunk);
|
||||
return chunk;
|
||||
}
|
||||
|
||||
protected override void InsertItem(int index, RIFFChunk item)
|
||||
{
|
||||
base.InsertItem(index, item);
|
||||
item.Parent = _parent;
|
||||
}
|
||||
protected override void RemoveItem(int index)
|
||||
{
|
||||
this[index].Parent = null;
|
||||
base.RemoveItem(index);
|
||||
}
|
||||
protected override void SetItem(int index, RIFFChunk item)
|
||||
{
|
||||
this[index].Parent = null;
|
||||
base.SetItem(index, item);
|
||||
item.Parent = _parent;
|
||||
}
|
||||
protected override void ClearItems()
|
||||
{
|
||||
for (int i = 0; i < Count; i++)
|
||||
{
|
||||
this[i].Parent = null;
|
||||
}
|
||||
base.ClearItems();
|
||||
}
|
||||
}
|
||||
|
||||
private string mvarID = String.Empty;
|
||||
|
||||
@ -26,16 +26,19 @@ namespace UniversalEditor.ObjectModels.Chunked
|
||||
/// <summary>
|
||||
/// Represents a group chunk (which can contain subchunks) in a Resource Interchange File Format file.
|
||||
/// </summary>
|
||||
public class RIFFGroupChunk : RIFFChunk
|
||||
public class RIFFGroupChunk : RIFFChunk, IChunkContainer
|
||||
{
|
||||
private RIFFChunkCollection mvarChunks = new RIFFChunkCollection();
|
||||
public RIFFChunkCollection Chunks { get { return mvarChunks; } }
|
||||
public RIFFChunkCollection Chunks { get; private set; } = null;
|
||||
public RIFFGroupChunk()
|
||||
{
|
||||
Chunks = new RIFFChunkCollection(this);
|
||||
}
|
||||
|
||||
public override object Clone()
|
||||
{
|
||||
RIFFGroupChunk clone = new RIFFGroupChunk();
|
||||
clone.ID = base.ID;
|
||||
foreach (RIFFChunk chunk in mvarChunks)
|
||||
foreach (RIFFChunk chunk in Chunks)
|
||||
{
|
||||
clone.Chunks.Add(chunk.Clone() as RIFFChunk);
|
||||
}
|
||||
@ -47,7 +50,7 @@ namespace UniversalEditor.ObjectModels.Chunked
|
||||
get
|
||||
{
|
||||
int size = base.Size;
|
||||
foreach (RIFFChunk chunk in mvarChunks)
|
||||
foreach (RIFFChunk chunk in Chunks)
|
||||
{
|
||||
size += chunk.Size;
|
||||
}
|
||||
|
||||
@ -197,6 +197,7 @@
|
||||
<Compile Include="DataFormats\Binary\PEM\PEMDataFormat.cs" />
|
||||
<Compile Include="ObjectModels\FileSystem\FileAdditionalDetail.cs" />
|
||||
<Compile Include="ObjectModels\FileSystem\FileAdditionalDetailValue.cs" />
|
||||
<Compile Include="ObjectModels\Chunked\IChunkContainer.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\UniversalEditor.Core\UniversalEditor.Core.csproj">
|
||||
|
||||
@ -0,0 +1,106 @@
|
||||
//
|
||||
// RIFFChunkPropertiesDialog.cs
|
||||
//
|
||||
// Author:
|
||||
// Michael Becker <alcexhim@gmail.com>
|
||||
//
|
||||
// Copyright (c) 2020 Mike Becker's Software
|
||||
//
|
||||
// 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.UserInterface;
|
||||
using MBS.Framework.UserInterface.Controls;
|
||||
using MBS.Framework.UserInterface.Controls.HexEditor;
|
||||
using UniversalEditor.ObjectModels.Chunked;
|
||||
|
||||
namespace UniversalEditor.Editors.RIFF.Dialogs
|
||||
{
|
||||
[ContainerLayout("~/Editors/RIFF/Dialogs/RIFFChunkPropertiesDialog.glade")]
|
||||
public class RIFFChunkPropertiesDialog : CustomDialog
|
||||
{
|
||||
private ComboBox cboChunkType;
|
||||
private Label lblChunkID;
|
||||
private TextBox txtChunkID;
|
||||
private Label lblGroupID;
|
||||
private ComboBox cboTypeID;
|
||||
private HexEditorControl hexData;
|
||||
|
||||
public RIFFChunk Chunk { get; set; } = null;
|
||||
|
||||
protected override void OnCreated(EventArgs e)
|
||||
{
|
||||
base.OnCreated(e);
|
||||
|
||||
cboChunkType.Changed += cboChunkType_Changed;
|
||||
|
||||
Buttons[0].ResponseValue = (int)DialogResult.None;
|
||||
Buttons[0].Click += cmdOK_Click;
|
||||
|
||||
if (Chunk != null)
|
||||
{
|
||||
txtChunkID.Text = Chunk.ID;
|
||||
if (Chunk is RIFFDataChunk)
|
||||
{
|
||||
cboChunkType.SelectedItem = (cboChunkType.Model as DefaultTreeModel).Rows[0];
|
||||
hexData.Data = (Chunk as RIFFDataChunk).Data;
|
||||
}
|
||||
else if (Chunk is RIFFGroupChunk)
|
||||
{
|
||||
cboChunkType.SelectedItem = (cboChunkType.Model as DefaultTreeModel).Rows[1];
|
||||
cboTypeID.Text = (Chunk as RIFFGroupChunk).TypeID;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void cmdOK_Click(object sender, EventArgs e)
|
||||
{
|
||||
if (cboChunkType.SelectedItem == (cboChunkType.Model as DefaultTreeModel).Rows[0])
|
||||
{
|
||||
// Data
|
||||
Chunk = new RIFFDataChunk();
|
||||
(Chunk as RIFFDataChunk).Data = hexData.Data;
|
||||
(Chunk as RIFFDataChunk).ID = txtChunkID.Text;
|
||||
}
|
||||
else if (cboChunkType.SelectedItem == (cboChunkType.Model as DefaultTreeModel).Rows[1])
|
||||
{
|
||||
// Group
|
||||
Chunk = new RIFFGroupChunk();
|
||||
(Chunk as RIFFGroupChunk).TypeID = cboTypeID.Text;
|
||||
(Chunk as RIFFGroupChunk).ID = txtChunkID.Text;
|
||||
}
|
||||
|
||||
this.DialogResult = DialogResult.OK;
|
||||
this.Close();
|
||||
}
|
||||
|
||||
void cboChunkType_Changed(object sender, EventArgs e)
|
||||
{
|
||||
if (cboChunkType.SelectedItem == (cboChunkType.Model as DefaultTreeModel).Rows[0])
|
||||
{
|
||||
// Data
|
||||
cboTypeID.Visible = false;
|
||||
lblGroupID.Visible = false;
|
||||
}
|
||||
else if (cboChunkType.SelectedItem == (cboChunkType.Model as DefaultTreeModel).Rows[1])
|
||||
{
|
||||
// Group
|
||||
cboTypeID.Visible = true;
|
||||
lblGroupID.Visible = true;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,259 @@
|
||||
//
|
||||
// RIFFEditor.cs
|
||||
//
|
||||
// Author:
|
||||
// Michael Becker <alcexhim@gmail.com>
|
||||
//
|
||||
// Copyright (c) 2020 Mike Becker's Software
|
||||
//
|
||||
// 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.UserInterface;
|
||||
using MBS.Framework.UserInterface.Controls;
|
||||
using MBS.Framework.UserInterface.Dialogs;
|
||||
using UniversalEditor.ObjectModels.Chunked;
|
||||
using UniversalEditor.UserInterface;
|
||||
using UniversalEditor.Editors.RIFF.Dialogs;
|
||||
|
||||
namespace UniversalEditor.Editors.RIFF
|
||||
{
|
||||
[ContainerLayout("~/Editors/RIFF/RIFFEditor.glade")]
|
||||
public class RIFFEditor : Editor
|
||||
{
|
||||
private ListView tv;
|
||||
private DefaultTreeModel tm;
|
||||
|
||||
public override void UpdateSelections()
|
||||
{
|
||||
}
|
||||
|
||||
protected override EditorSelection CreateSelectionInternal(object content)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
private static EditorReference _er = null;
|
||||
public override EditorReference MakeReference()
|
||||
{
|
||||
if (_er == null)
|
||||
{
|
||||
_er = base.MakeReference();
|
||||
_er.SupportedObjectModels.Add(typeof(ChunkedObjectModel));
|
||||
}
|
||||
return _er;
|
||||
}
|
||||
|
||||
protected override void OnObjectModelChanged(EventArgs e)
|
||||
{
|
||||
base.OnObjectModelChanged(e);
|
||||
|
||||
if (!IsCreated) return;
|
||||
|
||||
tm.Rows.Clear();
|
||||
|
||||
ChunkedObjectModel riff = (ObjectModel as ChunkedObjectModel);
|
||||
if (riff == null) return;
|
||||
|
||||
if (riff.Chunks.Count == 0)
|
||||
{
|
||||
riff.Chunks.Add(new RIFFGroupChunk { TypeID = "RIFF" });
|
||||
}
|
||||
|
||||
for (int i = 0; i < riff.Chunks.Count; i++)
|
||||
{
|
||||
AddChunkRecursive(riff.Chunks[i], null);
|
||||
}
|
||||
}
|
||||
|
||||
private void AddChunkRecursive(RIFFChunk chunk, TreeModelRow parent = null)
|
||||
{
|
||||
TreeModelRow row = new TreeModelRow(new TreeModelRowColumn[]
|
||||
{
|
||||
new TreeModelRowColumn(tm.Columns[0], chunk.ID),
|
||||
new TreeModelRowColumn(tm.Columns[1], String.Empty),
|
||||
new TreeModelRowColumn(tm.Columns[2], chunk.Size)
|
||||
});
|
||||
row.SetExtraData<RIFFChunk>("chunk", chunk);
|
||||
|
||||
if (chunk is RIFFGroupChunk)
|
||||
{
|
||||
RIFFGroupChunk g = (RIFFGroupChunk)chunk;
|
||||
row.RowColumns[1].Value = g.TypeID;
|
||||
for (int i = 0; i < g.Chunks.Count; i++)
|
||||
{
|
||||
AddChunkRecursive(g.Chunks[i], row);
|
||||
}
|
||||
}
|
||||
|
||||
if (parent == null)
|
||||
{
|
||||
tm.Rows.Add(row);
|
||||
}
|
||||
else
|
||||
{
|
||||
parent.Rows.Add(row);
|
||||
}
|
||||
}
|
||||
|
||||
protected override bool ShowDocumentPropertiesDialogInternal()
|
||||
{
|
||||
if (tv.Focused)
|
||||
{
|
||||
if (tv.SelectedRows.Count == 0)
|
||||
return true;
|
||||
|
||||
RIFFChunkPropertiesDialog dlg = new RIFFChunkPropertiesDialog();
|
||||
RIFFChunk originalChunk = tv.SelectedRows[0].GetExtraData<RIFFChunk>("chunk");
|
||||
dlg.Chunk = originalChunk;
|
||||
|
||||
if (dlg.ShowDialog() == DialogResult.OK)
|
||||
{
|
||||
BeginEdit();
|
||||
|
||||
int originalIndex = originalChunk.Parent.Chunks.IndexOf(originalChunk);
|
||||
originalChunk.Parent.Chunks[originalIndex] = dlg.Chunk;
|
||||
|
||||
tv.SelectedRows[0].RowColumns[0].Value = dlg.Chunk.ID;
|
||||
tv.SelectedRows[0].RowColumns[1].Value = (dlg.Chunk as RIFFGroupChunk)?.TypeID ?? String.Empty;
|
||||
tv.SelectedRows[0].RowColumns[2].Value = dlg.Chunk.Size;
|
||||
tv.SelectedRows[0].SetExtraData<RIFFChunk>("chunk", dlg.Chunk);
|
||||
|
||||
EndEdit();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
return base.ShowDocumentPropertiesDialogInternal();
|
||||
}
|
||||
|
||||
private void RIFFEditorContextMenu_Add_NewGroupChunk(object sender, EventArgs e)
|
||||
{
|
||||
if (tv.SelectedRows.Count == 0) return;
|
||||
TreeModelRow rowParent = tv.SelectedRows[0];
|
||||
|
||||
RIFFGroupChunk group = (rowParent.GetExtraData<RIFFChunk>("chunk") as RIFFGroupChunk);
|
||||
if (group == null) return;
|
||||
|
||||
RIFFChunkPropertiesDialog dlg2 = new RIFFChunkPropertiesDialog();
|
||||
|
||||
dlg2.Chunk = new RIFFGroupChunk();
|
||||
if (dlg2.ShowDialog() == DialogResult.OK)
|
||||
{
|
||||
BeginEdit();
|
||||
group.Chunks.Add(dlg2.Chunk);
|
||||
EndEdit();
|
||||
|
||||
TreeModelRow row = new TreeModelRow(new TreeModelRowColumn[]
|
||||
{
|
||||
new TreeModelRowColumn(tm.Columns[0], dlg2.Chunk.ID),
|
||||
new TreeModelRowColumn(tm.Columns[1], (dlg2.Chunk as RIFFGroupChunk)?.TypeID),
|
||||
new TreeModelRowColumn(tm.Columns[2], dlg2.Chunk.Size)
|
||||
});
|
||||
row.SetExtraData<RIFFChunk>("chunk", dlg2.Chunk);
|
||||
rowParent.Rows.Add(row);
|
||||
}
|
||||
}
|
||||
|
||||
private void RIFFEditorContextMenu_Add_NewDataChunk(object sender, EventArgs e)
|
||||
{
|
||||
if (tv.SelectedRows.Count == 0) return;
|
||||
TreeModelRow rowParent = tv.SelectedRows[0];
|
||||
|
||||
RIFFGroupChunk group = (rowParent.GetExtraData<RIFFChunk>("chunk") as RIFFGroupChunk);
|
||||
if (group == null) return;
|
||||
|
||||
RIFFChunkPropertiesDialog dlg2 = new RIFFChunkPropertiesDialog();
|
||||
|
||||
dlg2.Chunk = new RIFFDataChunk { Data = new byte[0] };
|
||||
if (dlg2.ShowDialog() == DialogResult.OK)
|
||||
{
|
||||
BeginEdit();
|
||||
group.Chunks.Add(dlg2.Chunk);
|
||||
EndEdit();
|
||||
|
||||
TreeModelRow row = new TreeModelRow(new TreeModelRowColumn[]
|
||||
{
|
||||
new TreeModelRowColumn(tm.Columns[0], dlg2.Chunk.ID),
|
||||
new TreeModelRowColumn(tm.Columns[1], (dlg2.Chunk as RIFFGroupChunk)?.TypeID),
|
||||
new TreeModelRowColumn(tm.Columns[2], dlg2.Chunk.Size)
|
||||
});
|
||||
row.SetExtraData<RIFFChunk>("chunk", dlg2.Chunk);
|
||||
rowParent.Rows.Add(row);
|
||||
}
|
||||
}
|
||||
|
||||
private void RIFFEditorContextMenu_Add_ExistingFile(object sender, EventArgs e)
|
||||
{
|
||||
if (tv.SelectedRows.Count == 0) return;
|
||||
TreeModelRow rowParent = tv.SelectedRows[0];
|
||||
|
||||
RIFFGroupChunk group = (rowParent.GetExtraData<RIFFChunk>("chunk") as RIFFGroupChunk);
|
||||
if (group == null) return;
|
||||
|
||||
FileDialog dlg = new FileDialog();
|
||||
dlg.Mode = FileDialogMode.Open;
|
||||
if (dlg.ShowDialog() == DialogResult.OK)
|
||||
{
|
||||
RIFFChunkPropertiesDialog dlg2 = new RIFFChunkPropertiesDialog();
|
||||
|
||||
dlg2.Chunk = new RIFFDataChunk { Data = System.IO.File.ReadAllBytes(dlg.SelectedFileName) };
|
||||
if (dlg2.ShowDialog() == DialogResult.OK)
|
||||
{
|
||||
BeginEdit();
|
||||
group.Chunks.Add(dlg2.Chunk);
|
||||
EndEdit();
|
||||
|
||||
TreeModelRow row = new TreeModelRow(new TreeModelRowColumn[]
|
||||
{
|
||||
new TreeModelRowColumn(tm.Columns[0], dlg2.Chunk.ID),
|
||||
new TreeModelRowColumn(tm.Columns[1], (dlg2.Chunk as RIFFGroupChunk)?.TypeID),
|
||||
new TreeModelRowColumn(tm.Columns[2], dlg2.Chunk.Size)
|
||||
});
|
||||
row.SetExtraData<RIFFChunk>("chunk", dlg2.Chunk);
|
||||
rowParent.Rows.Add(row);
|
||||
}
|
||||
}
|
||||
}
|
||||
private void RIFFEditorContextMenu_Export(object sender, EventArgs e)
|
||||
{
|
||||
if (tv.SelectedRows.Count < 1) return;
|
||||
|
||||
RIFFChunk chunk = tv.SelectedRows[0].GetExtraData<RIFFChunk>("chunk");
|
||||
if (chunk is RIFFDataChunk)
|
||||
{
|
||||
FileDialog dlg = new FileDialog();
|
||||
dlg.Mode = FileDialogMode.Save;
|
||||
if (dlg.ShowDialog() == DialogResult.OK)
|
||||
{
|
||||
System.IO.File.WriteAllBytes(dlg.SelectedFileName, (chunk as RIFFDataChunk).Data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected override void OnCreated(EventArgs e)
|
||||
{
|
||||
base.OnCreated(e);
|
||||
|
||||
Context.AttachCommandEventHandler("RIFFEditorContextMenu_Add_NewGroupChunk", RIFFEditorContextMenu_Add_NewGroupChunk);
|
||||
Context.AttachCommandEventHandler("RIFFEditorContextMenu_Add_NewDataChunk", RIFFEditorContextMenu_Add_NewDataChunk);
|
||||
Context.AttachCommandEventHandler("RIFFEditorContextMenu_Add_ExistingFile", RIFFEditorContextMenu_Add_ExistingFile);
|
||||
Context.AttachCommandEventHandler("RIFFEditorContextMenu_Export", RIFFEditorContextMenu_Export);
|
||||
|
||||
tv.ContextMenuCommandID = "RIFFEditorContextMenu";
|
||||
|
||||
OnObjectModelChanged(EventArgs.Empty);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -130,6 +130,8 @@
|
||||
<Compile Include="Panels\DocumentExplorerPanel.cs" />
|
||||
<Compile Include="Editors\FileSystem\FileSystemEditorDocumentPropertiesSettingsProvider.cs" />
|
||||
<Compile Include="Dialogs\ManageBookmarksDialog.cs" />
|
||||
<Compile Include="Editors\RIFF\RIFFEditor.cs" />
|
||||
<Compile Include="Editors\RIFF\Dialogs\RIFFChunkPropertiesDialog.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<BootstrapperPackage Include="Microsoft.Net.Client.3.5">
|
||||
@ -182,6 +184,8 @@
|
||||
<Folder Include="Controls\" />
|
||||
<Folder Include="Editors\Binary\" />
|
||||
<Folder Include="Editors\Database\" />
|
||||
<Folder Include="Editors\RIFF\" />
|
||||
<Folder Include="Editors\RIFF\Dialogs\" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user