Beispiel #1
0
        public void ConfigureRecords(IEnumerable<Record> records)
        {
            var recs = records.Select(rec => rec.GetStructure()).Distinct();
            this.rec = (recs.Count() == 1) ? recs.FirstOrDefault() : null;
            if (this.rec == null)
            {
                this.filterTree.Roots = null;
            }
            else
            {
                //this.records = records;

                var srs = (from sr in this.rec.subrecords
                           let children = sr.elements.Select(se => new BatchElement() { Name = se.name, Parent = null, Record = se, Type = BatchCondElementType.Set, Checked = false }).ToList()
                           select new BatchSubrecord() { Name = string.Format("{0}: {1}", sr.name, sr.desc), Record = sr, Children = children, Checked = false, }).ToList();

                // Construct specialized editors for FormID and related headers
            #if false
                {
                    var elems = new List<TESVSnip.Data.SubrecordElement>
                    {
                        new TESVSnip.Data.SubrecordElement{name = "FormID", desc = "Form ID", hexview = true, type = "uint"},
                        new TESVSnip.Data.SubrecordElement{name = "Flags1", desc = "Flags 1", hexview = true, type = "uint"},
                        new TESVSnip.Data.SubrecordElement{name = "Flags2", desc = "Flags 2", hexview = true, type = "uint"},
                        new TESVSnip.Data.SubrecordElement{name = "Flags3", desc = "Flags 3", hexview = true, type = "uint"},
                    };
                    var frmHdr = new TESVSnip.Data.Subrecord { name = "Header", desc = "Record Header", Elements = elems };
                    var hdr = new SubrecordStructure(frmHdr);
                    var hdrElems = hdr.elements.Select(se =>
                        new BatchElement { Name = se.name, Parent = null, Record = se, Type = BatchCondElementType.Set, Checked = false }
                        ).ToList();
                    srs.Insert(0, new BatchSubrecord
                    {
                        Name = string.Format("{0}: {1}", hdr.name, hdr.desc),
                        Record = hdr,
                        Children = hdrElems,
                        Checked = false,
                    });
                }
            #endif

                // fix parents after assignments
                foreach (var sr in srs)
                {
                    foreach (var se in sr.Children)
                    {
                        se.Parent = sr;
                    }
                }

                this.filterTree.Roots = srs;
            }
        }
Beispiel #2
0
        public void ConfigureRecords(IEnumerable <Record> records)
        {
            var recs = records.Select(
                x => {
                RecordStructure rs;
                return(RecordStructure.Records.TryGetValue(x.Name, out rs) ? rs : null);
            }).Distinct();

            this.rec = (recs.Count() == 1) ? recs.FirstOrDefault() : null;
            if (this.rec == null)
            {
                this.filterTree.Roots = null;
            }
            else
            {
                this.records = records;

                var srs = (from sr in this.rec.subrecords
                           let children = sr.elements.Select(se => new BatchElement()
                {
                    Name = se.name, Parent = null, Record = se, Type = BatchCondElementType.Set, Checked = false
                }).ToList()
                                          select new BatchSubrecord()
                {
                    Name = string.Format("{0}: {1}", sr.name, sr.desc), Record = sr, Children = children, Checked = false,
                }).ToList();

                // Construct specialized editors for FormID and related headers
#if false
                {
                    var elems = new List <TESVSnip.Data.SubrecordElement>
                    {
                        new TESVSnip.Data.SubrecordElement {
                            name = "FormID", desc = "Form ID", hexview = true, type = "uint"
                        },
                        new TESVSnip.Data.SubrecordElement {
                            name = "Flags1", desc = "Flags 1", hexview = true, type = "uint"
                        },
                        new TESVSnip.Data.SubrecordElement {
                            name = "Flags2", desc = "Flags 2", hexview = true, type = "uint"
                        },
                        new TESVSnip.Data.SubrecordElement {
                            name = "Flags3", desc = "Flags 3", hexview = true, type = "uint"
                        },
                    };
                    var frmHdr = new TESVSnip.Data.Subrecord {
                        name = "Header", desc = "Record Header", Elements = elems
                    };
                    var hdr      = new SubrecordStructure(frmHdr);
                    var hdrElems = hdr.elements.Select(se =>
                                                       new BatchElement {
                        Name = se.name, Parent = null, Record = se, Type = BatchCondElementType.Set, Checked = false
                    }
                                                       ).ToList();
                    srs.Insert(0, new BatchSubrecord
                    {
                        Name     = string.Format("{0}: {1}", hdr.name, hdr.desc),
                        Record   = hdr,
                        Children = hdrElems,
                        Checked  = false,
                    });
                }
#endif

                // fix parents after assignments
                foreach (var sr in srs)
                {
                    foreach (var se in sr.Children)
                    {
                        se.Parent = sr;
                    }
                }

                this.filterTree.Roots = srs;
            }
        }
Beispiel #3
0
        public bool Process(Record p)
        {
            TESVSnip.Data.RecordsRecord rr = ProcessBase(p);

            // int srIdx = 0;
            var groups = from psr in p.SubRecords
                         group psr by psr.Name into g
                         select new { Name = g.Key, Records = g.ToArray() };

            int lastIndex = 0;
            Dictionary <string, TESVSnip.Data.Subrecord> dict = new Dictionary <string, TESVSnip.Data.Subrecord>();

            foreach (var kvp in groups)
            {
                if (IsCanceled)
                {
                    return(false);
                }

                TESVSnip.Data.Subrecord sr = rr.Subrecords.FirstOrDefault(x => x.name == kvp.Name);
                if (sr == null)
                {
                    sr          = new TESVSnip.Data.Subrecord();
                    sr.name     = sr.desc = kvp.Name;
                    sr.optional = 1;
                    if (lastIndex + 1 <= rr.Items.Count)
                    {
                        rr.Items.Insert(++lastIndex, sr);
                    }
                    else
                    {
                        rr.Items.Add(sr);
                    }
                }
                else
                {
                    lastIndex = rr.Items.IndexOf(sr, lastIndex);
                    if (lastIndex < 0)  // out of order
                    {
                        lastIndex = rr.Items.IndexOf(sr);
                    }
                }
                int n = kvp.Records.Length;
                if (n > 0)
                {
                    if (sr.repeat == 0 && n > 1)
                    {
                        sr.optional = sr.repeat = 1;
                    }
                    int idx1 = p.SubRecords.IndexOf(kvp.Records[0]);
                    int idx2 = idx1;
                    for (int i = 1; i < n; ++i, idx1 = idx2)
                    {
                        idx2 = p.SubRecords.IndexOf(kvp.Records[i]);
                        int diff = (idx2 - idx1);
                        if (diff > sr.repeat)
                        {
                            if (diff < 10)
                            {
                                sr.optional = sr.repeat = diff;
                            }
                            else
                            {
                                sr.optional = sr.repeat;
                            }
                        }
                    }
                }
                foreach (var subrec in kvp.Records)
                {
                    if (IsCanceled)
                    {
                        break;
                    }
                    Process(sr, subrec);
                }
            }
            return(true);
        }
Beispiel #4
0
        public void Process(TESVSnip.Data.Subrecord sr, SubRecord subrec)
        {
            TESVSnip.Data.SubrecordElement expectedElement = (sr.Elements.Count >= 1) ? sr.Elements[0] : null;
            if (expectedElement != null && expectedElement.type == "blob")
            {
                return;
            }

            byte[] data = subrec.GetReadonlyData();
            if (data.Length == 0)
            {
                if (sr.Elements.Count == 0)
                {
                    sr.Elements.Add(CreateBlob());
                }
                return;
            }
            if (data.Length == 2)
            {
// common scenarios
                if (expectedElement != null && expectedElement.size == 2)
                {
                    return;
                }

                TESVSnip.Data.SubrecordElement elem = new TESVSnip.Data.SubrecordElement();
                elem.name = "Unknown";
                elem.type = "short";
                elem.size = 2;
                sr.Elements.Add(elem);
                UpdateSize(sr);
                return;
            }

            if (data.Length > 0)
            {
                bool isAscii = true;
                for (int i = 0; i < data.Length - 1 && isAscii; ++i)
                {
                    isAscii = !Char.IsControl((char)data[i]);
                }
                isAscii = (isAscii && data[data.Length - 1] == 0);
                if (isAscii)
                {
                    // test if its a string
                    if (expectedElement == null)
                    {
                        TESVSnip.Data.SubrecordElement elem = new TESVSnip.Data.SubrecordElement();
                        elem.name = "Unknown";
                        elem.type = "string";
                        sr.Elements.Add(elem);
                    }
                    else if (expectedElement.type != "string")
                    {
                        sr.Elements.Clear();
                        sr.Elements.Add(CreateBlob());
                    }
                    return;
                }
            }
            for (int offset = 0, elemSize = 4; offset < data.Length; offset += elemSize)
            {
                if (IsCanceled)
                {
                    return;
                }

                int left = data.Length - offset;
                if (left >= 4)
                {
// common scenarios
                    if (expectedElement != null && expectedElement.size == 4)
                    {
                        continue;
                    }

                    ushort lhs = TypeConverter.h2s(data[offset], data[offset + 1]);
                    ushort uhs = TypeConverter.h2s(data[offset + 2], data[offset + 3]);
                    uint   ui4 = TypeConverter.h2i(data[offset], data[offset + 1], data[offset + 2], data[offset + 3]);
                    if (ui4 == 0)
                    {
                        if (expectedElement == null)
                        {
                            TESVSnip.Data.SubrecordElement elem = new TESVSnip.Data.SubrecordElement();
                            elem.name = "Unknown";
                            elem.type = "int";
                            elem.size = 4;
                            sr.Elements.Add(elem);
                            UpdateSize(sr);
                            continue;
                        }
                    }
                    else
                    {
                        float flt = TypeConverter.h2f(data[offset], data[offset + 1], data[offset + 2], data[offset + 3]);
                        if (IsLikelyFloat(flt))
                        {
// replace element which is int with float
                            if (expectedElement == null)
                            {
                                TESVSnip.Data.SubrecordElement elem = new TESVSnip.Data.SubrecordElement();
                                elem.name = "Unknown";
                                elem.type = "float";
                                elem.size = 4;
                                sr.Elements.Add(elem);
                            }
                            else
                            {
                                if (expectedElement.type == "int")
                                {
                                    expectedElement.type = "float";
                                }
                            }
                            continue;
                        }
                        else
                        {
                            Record r = this.FormLookup(ui4);
                            if (r != null)
                            {
                                string reftype = r.DescriptiveName.Substring(0, 4); // ???
                                if (expectedElement == null)
                                {
                                    TESVSnip.Data.SubrecordElement elem = new TESVSnip.Data.SubrecordElement();
                                    elem.name    = "ID";
                                    elem.type    = "formid";
                                    elem.reftype = reftype;
                                    elem.size    = 4;
                                    sr.Elements.Add(elem);
                                }
                                else
                                {
                                    if (expectedElement.type == "formid")
                                    {
                                        if (expectedElement.reftype != reftype)
                                        {
                                            expectedElement.reftype = string.Empty;
                                        }
                                    }
                                }
                                continue;
                            }
                            else
                            {
                                string s = this.StringLookup(ui4);
                                if (!string.IsNullOrEmpty(s))
                                {
                                    if (expectedElement == null)
                                    {
                                        TESVSnip.Data.SubrecordElement elem = new TESVSnip.Data.SubrecordElement();
                                        elem.name = "Unknown";
                                        elem.type = "string";
                                        sr.Elements.Add(elem);
                                    }
                                    continue;
                                }
                            }
                            if (expectedElement == null)
                            {
                                if (lhs > 0 && lhs < 255 && uhs > 0 && uhs < 255)
                                {
                                    TESVSnip.Data.SubrecordElement elem = new TESVSnip.Data.SubrecordElement();
                                    elem.name = "Unknown";
                                    elem.type = "short";
                                    elem.size = 2;
                                    sr.Elements.Add(elem);
                                    sr.Elements.Add(elem);
                                }
                                else
                                {
                                    TESVSnip.Data.SubrecordElement elem = new TESVSnip.Data.SubrecordElement();
                                    elem.name = "Unknown";
                                    elem.type = "int";
                                    elem.size = 4;
                                    sr.Elements.Add(elem);
                                    UpdateSize(sr);
                                }
                            }
                        }
                    }
                }
            }


            if (sr.Elements.Count == 0)
            {
                sr.Elements.Add(CreateBlob());
            }
            UpdateSize(sr);
        }
Beispiel #5
0
        public bool Process(Record p)
        {
            TESVSnip.Data.RecordsRecord rr = ProcessBase(p);

            // int srIdx = 0;
            var groups = from psr in p.SubRecords
                         group psr by psr.Name into g
                         select new { Name = g.Key, Records = g.ToArray() };

            int lastIndex = 0;
            Dictionary<string, TESVSnip.Data.Subrecord> dict = new Dictionary<string, TESVSnip.Data.Subrecord>();
            foreach (var kvp in groups)
            {
                if (IsCanceled) return false;

                TESVSnip.Data.Subrecord sr = rr.Subrecords.FirstOrDefault(x => x.name == kvp.Name);
                if (sr == null)
                {
                    sr = new TESVSnip.Data.Subrecord();
                    sr.name = sr.desc = kvp.Name;
                    sr.optional = 1;
                    if (lastIndex + 1 <= rr.Items.Count)
                    {
                        rr.Items.Insert(++lastIndex, sr);
                    }
                    else
                    {
                        rr.Items.Add(sr);
                    }
                }
                else
                {
                    lastIndex = rr.Items.IndexOf(sr, lastIndex);
                    if (lastIndex < 0)  // out of order
                        lastIndex = rr.Items.IndexOf(sr);
                }
                int n = kvp.Records.Length;
                if (n > 0)
                {
                    if (sr.repeat == 0 && n > 1)
                        sr.optional = sr.repeat = 1;
                    int idx1 = p.SubRecords.IndexOf(kvp.Records[0]);
                    int idx2 = idx1;
                    for (int i = 1; i < n; ++i, idx1 = idx2)
                    {
                        idx2 = p.SubRecords.IndexOf(kvp.Records[i]);
                        int diff = (idx2 - idx1);
                        if (diff > sr.repeat)
                        {
                            if (diff < 10)
                            {
                                sr.optional = sr.repeat = diff;
                            }
                            else
                            {
                                sr.optional = sr.repeat;
                            }
                        }
                    }
                }
                foreach (var subrec in kvp.Records)
                {
                    if (IsCanceled) break;
                    Process(sr, subrec);
                }
            }
            return true;
        }