Example #1
0
 /// <summary>
 /// Load top level manifests to track dependencies
 /// </summary>
 public static void LoadManifests(bool makedep = true)
 {
     foreach (var man in Directory.GetFiles(Dir.abdata, "*.*", SearchOption.TopDirectoryOnly))
     {
         var ab = AssetBundle.LoadFromFile(man);
         var fn = man.Substring(Dir.abdata.Length);
         if (ab == null)
         {
             continue;
         }
         Debug.Log("scanning for manifest in ", man);
         var mf = ab.LoadAsset <AssetBundleManifest>("AssetBundleManifest");
         if (mf != null)
         {
             AssetBundleManager.ManifestBundlePack["abdata/" + fn] = new AssetBundleManager.BundlePack()
             {
                 AssetBundleManifest = mf
             };
             if (makedep)
             {
                 foreach (var sab in mf.GetAllAssetBundles())
                 {
                     var rpath = sab.Replace("abdata/", "");
                     if (!File.Exists(Dir.abdata + rpath))
                     {
                         Debug.Error("Nonexistent ", rpath, " announced in manifest ", man);
                         continue;
                     }
                     var abi = LoadedAssetBundle.Make(rpath);
                     abi.hasManifest     = true;
                     abi.hasRealManifest = true;
                     foreach (var tdep in mf.GetAllDependencies(sab))
                     {
                         Debug.Log(" =>", sab, " depends on ", tdep);
                         string dep = tdep.Replace("abdata/", "");
                         if (!abi.deps.Contains(dep))
                         {
                             abi.deps.Add(dep);
                         }
                     }
                 }
             }
         }
         ab.Unload(false);
     }
 }
Example #2
0
    /// <summary>
    /// Rescan the directory mappings
    /// </summary>
    public static void Rescan(bool flush = true)
    {
        Debug.Log("VFS: Rescan");
        string abdata   = "abdata/";
        string inabdata = Dir.root + abdata;

        if (flush)
        {
            dc.abs.Clear();
            LoadManifests();
        }
        dc.dirLists.Clear();
        // initially map everything to self
        Debug.Log("unity3d");
        foreach (var bundle in Directory.GetFiles(inabdata, "*.unity3d", SearchOption.AllDirectories))
        {
            var rel  = bundle.Replace("\\", "/");
            var name = rel.Substring(Dir.abdata.Length);
            if (!settings.withoutManifest && !name.ToLower().StartsWith("sound/") && (!dc.abs.TryGetValue(name, out LoadedAssetBundle mab) || !mab.hasManifest))
            {
                Debug.Info("Skipping mod ", rel, " as it is not in any manifest and mod loading from abdata is not enabled.");
                continue;
            }
            LoadedAssetBundle.Make(name, rel.Substring(Dir.root.Length));
        }
        Debug.Log("dirlists");
        Dictionary <string, bool> lhash = new Dictionary <string, bool>();

        // Now scan for listable bundles in abdata
        foreach (var ld in listable)
        {
            var lld = ld.Replace("!", "");
            lhash[lld] = lld != ld;
            if (!Directory.Exists(Dir.abdata + lld))
            {
                continue;
            }
            dc.dirLists[lld] = new List <string>();
            foreach (var blist in Directory.GetFiles(Dir.abdata + lld, "*.unity3d", ld != lld ? SearchOption.TopDirectoryOnly : SearchOption.AllDirectories))
            {
                var fn = blist.Replace("\\", "/").Substring(Dir.abdata.Length);

                Debug.Log("processing", fn);
                // no manifest; skip it
                if (!settings.withoutManifest && !fn.ToLower().StartsWith("sound/") && (!dc.abs.TryGetValue(fn, out LoadedAssetBundle mab) || !mab.hasManifest))
                {
                    Debug.Info("Skipping mod ", fn, " as it is not in any manifest and mod loading from abdata is not enabled.");
                    continue;
                }
                Debug.Log("added to dirlist");
                dc.dirLists[lld].Add(fn);

                // if recursive, walk up and populate dirlists
                int idx = fn.LastIndexOf('/');
                if (ld == lld && idx >= 0)
                {
                    string td = fn.Remove(idx);
                    while (td != lld)
                    {
                        if (!dc.dirLists.TryGetValue(td, out List <string> tdl))
                        {
                            tdl = dc.dirLists[td] = new List <string>();
                        }
                        tdl.Add(fn);
                        td = td.Remove(td.LastIndexOf('/'));
                    }
                }
            }
        }
        Debug.Log("mods");
        // now scan mods, those will simply override the tables above
        if (settings.loadMods)
        {
            foreach (var mod in Directory.GetDirectories(Dir.mod, "*.*", SearchOption.TopDirectoryOnly))
            {
                Debug.Log("Processing ", mod);
                var inmod = mod + "/";
                foreach (var tmpfn in Directory.GetFiles(inmod, "*.*", SearchOption.AllDirectories))
                {
                    var currentfn = tmpfn.Replace("\\", "/");
                    var realFn    = currentfn.Substring(Dir.root.Length);           // real path relative to root
                    var fn        = currentfn.Substring(inmod.Length);              // virtualpath
                    if (fn.ToLower().StartsWith("abdata/"))
                    {
                        fn = fn.Substring(7);
                    }

                    // may override original abdata mapping
                    if (fn.EndsWith(".unity3d"))
                    {
                        LoadedAssetBundle.Make(fn, realFn);
                    }

                    // keep stripping last path component of the file path until we match
                    // a path which is listable
                    var ofn = fn;
                    int ind;
                    int stripped = 0;
                    while ((ind = fn.LastIndexOf('/')) >= 0)
                    {
                        fn = fn.Remove(ind);                         // is directory now
                        //	Debug.Log("listable lookup", fn, ofn);
                        var virtab = ofn.Remove(ofn.LastIndexOf('/')) + ".unity3d";
                        // a file inside listable folder was detected, we'll need to inspect the folder
                        if (lhash.TryGetValue(fn, out bool norecurse))
                        {
                            // an actual bundle, insert it as-is
                            if (ofn.EndsWith(".unity3d"))
                            {
                                if ((!norecurse || stripped == 0) && !dc.dirLists[fn].Contains(ofn))
                                {
                                    dc.dirLists[fn].Add(ofn.Replace("+", ""));
                                }
                            }
                            else
                            {
                                // a file in a directory. the directory itself then becomes a virtual bundle
                                // if there is no accompanying real one
                                // add to dir listings
                                if ((!norecurse || stripped == 0) || !dc.dirLists[fn].Contains(virtab))
                                {
                                    dc.dirLists[fn].Add(virtab);
                                }
                            }
                        }
                        if (fn != "" && stripped == 0 && !ofn.EndsWith("*.unity3d"))
                        {
                            // create a virtual bundle
                            var assname = RemoveExt(Path.GetFileName(ofn));
                            var vab     = LoadedAssetBundle.Make(virtab);
                            vab.hasManifest = true;
                            Debug.Log("adding virtual asset ", assname, "into", virtab);
                            vab.virtualAssets[assname.ToLower()] = realFn;
                            var nvpath = realFn.Remove(realFn.LastIndexOf('/'));
                            Debug.Log(assname, virtab, fn, nvpath, vab.realPath);
                            if (vab.realPath == null && nvpath != vab.realPath)
                            {
                                vab.realPath = nvpath;
                            }
                            else
                            {
                                Debug.Log("Not overriding ", vab.realPath, " with ", nvpath);
                            }
                        }
                        stripped++;
                    }
                }
            }
        }
    }