Oblivion

File information

Last updated

Original upload

Created by

qwerty

Uploaded by

qwertyasdfgh

Virus scan

Safe to use

41 comments

  1. qwertyasdfgh
    qwertyasdfgh
    • member
    • 793 posts
    • 110 kudos
    Locked
    Sticky
    Hello, and thank you for checking out the mod. The initial release doesn't contain a lot of recipes, I'm mainly posting it for feedback, and to have it as a requirement for some future mods.

    However, some recipes for base game items, Skyrim Ingredients, and COBL items are already there.
  2. Claudia1288
    Claudia1288
    • premium
    • 139 posts
    • 3 kudos
     
  3. Wiseman05
    Wiseman05
    • member
    • 129 posts
    • 7 kudos
    Hey, this looks neat! I like the idea of crafting, and it could be fun to be able to add crafting recipes for mod items too - especially items that you can only get through shops or something. How does this compare to MOO's crafting system? Because I like MOO a lot, but the Crafting system isn't very easy to work with. 

    Well guess I'll have to see for myself in any case, but I'm still excited to see where this goes. 
  4. Darkaxt
    Darkaxt
    • premium
    • 87 posts
    • 2 kudos
    Hi

    I really hope to see this project evolving to fully support all vanilla craftablish assets. As my two cent, I am providing an adapted xedit plugin to convert all static references to CookingPot and Anvil01 to their equivalent active ones OCRAFTStationCookingPot and OCRAFTStationAnvil.

    To use this script you need to create an empty plugin named 'Static Replacer - Extended' (you can manually change the name in the script for whatever) and copy the references for the actives elements over to the new plugin. Then select the new plugin and apply the script. This also has the benefit of carrying over all previous form changes so that no conflict resolution patch would be needed:

    {
      Purpose: Reference Replace
      Game: The Elder Scrolls V: Skyrim SE
      Original Author: Sandman53
      Adapted by: Darkaxt
      Version: 1.1
      Instructions:
      1. Add Editor IDs and Masters
      2. Apply Script
    }
    unit UserScript;
    //-------------------------------------------------------------------------------
    // Global Variables
    //-------------------------------------------------------------------------------
    var
      stReplaceReference, stRefName: TStringList;
      userFile, iReplaceRef: IInterface;
      sRefType: string;
    //-------------------------------------------------------------------------------
    // Initialize Variables and File
    //-------------------------------------------------------------------------------
    function Initialize: integer;
      var 
        stObjectEID, stSplitText: TStringList;
        i, n: integer;
        sModName, sRefName, sRefType: string;
        iRef, searchFile: IInterface;
      begin
        //-------------------------------------------------------------------------------
        // Setup Variables
        //-------------------------------------------------------------------------------
        // Mod Name
        sModName := 'Static Replacer - Extended.esp';
        // Base Objects that will replacing existing object. The delimiter seperates the objects type
        stObjectEID := TStringList.Create;
        stObjectEID.Add('OCRAFTStationCookingPot;ACTI'); // 0  
        stObjectEID.Add('OCRAFTStationAnvil;ACTI'); // 1  
        
        // Editor ID of Objects to replace. Include the Type and the corresponding reference above to replace with
        stReplaceReference := TStringList.Create;
        stReplaceReference.Add('CookingPot;STAT;0');
        stReplaceReference.Add('Anvil01;STAT;1');
        
        
        
        //-------------------------------------------------------------------------------
        // Get Main Form IDs
        //-------------------------------------------------------------------------------
        // Save Main Editor FormIDs for later
        stRefName := TStringList.Create;
        for i := 0 to Pred(FileCount) do begin
          searchFile := FileByIndex(i);
          if (GetFileName(searchFile) = sModName) then begin
            RemoveNode(GroupBySignature(searchFile, 'CELL'));
            RemoveNode(GroupBySignature(searchFile, 'WRLD'));
            userFile := searchFile;
            for n := 0 to stObjectEID.Count-1 do begin
              // Split string for Name and Type
              stSplitText := TStringList.Create;
              SplitText(';', stObjectEID[n], stSplitText);
              sRefName := stSplitText[0];
              sRefType := stSplitText[1];
              iRef := MainRecordByEditorID(GroupBySignature(searchFile, sRefType), sRefName);
              stRefName.add(GetEditValue(ElementByPath(iRef, 'Record Header\FormID')));
            end;
          end;
        end;  
        //-------------------------------------------------------------------------------
        // File Creation
        //-------------------------------------------------------------------------------
        
        if not Assigned(userFile) then begin
          AddMessage('Failed to create patch.');
          exit;
        end;
        // Patch will be an ESL
        SetFlag(ElementByPath(ElementByIndex(userFile, 0), 'Record Header\Record Flags'), 9, true);
        
        // Add Base Masters
        CleanMasters(userFile);
        AddMasterIfMissing(userFile, 'Oblivion.esm');
        AddMasterIfMissing(userFile, 'OCRAFT.esp');
        //AddMasterIfMissing(userFile, sModName);
         SortMasters(userFile);
      end;
    //-------------------------------------------------------------------------------
    // Update all Objects
    //-------------------------------------------------------------------------------
    function Finalize: Integer;
      var
        stProcessedForms, stSplitText: TStringList;
        baseIndex, i, refIndex, recIndex, baseObject: integer;
        iSearchRef, iFoundRef, iNewRef, iRef, iCell, iCellCopy, iGroup: IInterface;
        sFormID, sRefName, sRefType: string;
        frm: TForm;
        clb: TCheckListBox;
      begin
        AddMessage('-------------------------------------------------------------------------------');
        AddMessage( 'Modifying References' );
        AddMessage('-------------------------------------------------------------------------------');
        // Setup Processed List
        stProcessedForms := TStringList.Create;
        // Process each Base Form
        for baseIndex := 0 to stReplaceReference.Count-1 do begin
          // Split the current string and extract Name, Type and the replacement object
          stSplitText := TStringList.Create;
          SplitText(';', stReplaceReference[baseIndex], stSplitText);
          sRefName := stSplitText[0];
          sRefType := stSplitText[1];
          baseObject := stSplitText[2];
          // Find the Base Form ID of the object we are working with
          for i := 0 to Pred(FileCount) do begin
            iSearchRef := MainRecordByEditorID(GroupBySignature(FileByIndex(i), sRefType), sRefName);
            if Assigned(iSearchRef) then
              break;
          end;
          // Get all of the references to the Base Form
          for refIndex := ReferencedByCount(MasterOrSelf(iSearchRef))-1 downto 0 do begin
            iFoundRef := ReferencedByIndex(MasterOrSelf(iSearchRef), refIndex);
            sFormID := GetEditValue(ElementByPath(iFoundRef, 'Record Header\FormID'));
            // If it is not a reference we skip it
            if Signature(iFoundRef) <> 'REFR' then
              continue;
            // Make sure we have not already processed it
            if (wbStringListInString(stProcessedForms, sFormID) = -1) then begin
              if not ( IsWinningOverride(iFoundRef)) then begin
                //AddMessage('Skipping reference ' + sformID); 
                stProcessedForms.add(sFormID);
                continue;
              end;
              AddMessage('Comparing ' + sformId + ' element ' + Name(iSearchRef) + ', name ' + GetElementEditValues(iFoundRef, 'NAME'));
            
              // Copy Cell Data
              iCell := WinningOverride(LinksTo(ElementByName(iFoundRef, 'Cell')));
              UpdateMasters(iCell);
              
              iCellCopy := wbCopyElementToFile(iCell, userFile, false, true);
              // Add Required masters and copy element to our file
              UpdateMasters(iFoundRef);
              iNewRef := wbCopyElementToFile(iFoundRef, userFile, false, true);
              // Update the reference with the new name
              SetElementEditValues(iNewRef, 'NAME', stRefName[baseObject]);
              // Show Processing Message
              if GetElementEditValues(iCellCopy, 'FULL') = '' then
                AddMessage('Modified Reference at: ' + GetElementEditValues(iCellCopy, 'Worldspace'))
              else
                AddMessage('Modified Reference at: ' + GetElementEditValues(iCellCopy, 'FULL'));
              // Add the form we just processed
              stProcessedForms.add(sFormID);
            end;
          end;
          
          // Clean Masters
          CleanMasters(userFile);
        end;
        // Clean and Sort Masters
        CleanMasters(userFile);
         SortMasters(userFile);
        // Free Memory
        stProcessedForms.Free;
        AddMessage('-------------------------------------------------------------------------------');
        AddMessage('Processing Complete');
        AddMessage('-------------------------------------------------------------------------------');
      end;
    //-------------------------------------------------------------------------------
    // Split String
    //-------------------------------------------------------------------------------
    procedure SplitText(aDelimiter: Char; const s: String; aList: TStringList);
      begin
        aList.Delimiter := aDelimiter;
        aList.StrictDelimiter := True; // Spaces excluded from being a delimiter
        aList.DelimitedText := s;
      end;
    //-------------------------------------------------------------------------------
    // Set Flags
    //-------------------------------------------------------------------------------
    procedure SetFlag(element: IInterface; index: Integer; state: boolean);
      var
        mask: Integer;
      begin
        mask := 1 shl index;
        if state then
          SetNativeValue(element, GetNativeValue(element) or mask)
        else
          SetNativeValue(element, GetNativeValue(element) and not mask);
      end;
    //-------------------------------------------------------------------------------
    // Update Masters
    //-------------------------------------------------------------------------------
    procedure UpdateMasters(element: IInterface);
      var
        i: Integer;
        workFile: iwbFile;
      begin
        workFile := GetFile(element);
        for i := 0 to MasterCount(workFile) - 1 do begin
          AddMasterIfMissing(userFile, GetFileName(MasterByIndex(workFile, i)));
        end;
        AddMasterIfMissing(userFile, GetFileName(workFile));
      end;
    end.
  5. Dispensation
    Dispensation
    • premium
    • 3,072 posts
    • 199 kudos
    There's some conflicts with the Unofficial Oblivion Patch, concerning the placement of some items, and they float in the air a bit because they undo the Z position:


    And you should probably add Shivering Isles to the requirements tab, also.
    1. qwertyasdfgh
      qwertyasdfgh
      • member
      • 793 posts
      • 110 kudos
      I had to move those objects to make room for an anvil. I'll check their positions, but they'll show up as a "conflict" regardless. 

      Shivering Isles is part of Oblivion.esm. Since you literally can't play without it, I think adding it as a "requirement" is kinda strange. 
    2. marcerx1x2
      marcerx1x2
      • member
      • 18 posts
      • 0 kudos
      I just booted up good ol' Oblivion from an old DVD and I have the base game only. I even had to patch it up with the official patches to use other mods lol
      I know it's unusual but here I am, the rare exception :P :D

      Most mods doesn't require Shivering Isles and I barely encounter any that dependent on it but it's still good to know if it's needed in order to use a mod.

      Anyway good concept and good work! :D Keep it up!

      Once I'll get the DLC / the Deluxe edition I'll try your mod too
  6. MichaelMarxxMann
    MichaelMarxxMann
    • premium
    • 134 posts
    • 1 kudos
    I'm just curious, will this be compatible or patched to work with Oblivion Jobs.
  7. Dispensation
    Dispensation
    • premium
    • 3,072 posts
    • 199 kudos
    You can also use Better Camps to add some fires under the cooking pots in the camp sites, for added immersion.

    Will these crafting actions ever reward XP if you are also using the Ultimate Leveling mod?
    1. qwertyasdfgh
      qwertyasdfgh
      • member
      • 793 posts
      • 110 kudos
      ?Will these crafting actions ever reward XP if you are also using the Ultimate Leveling mod?
      I don't use it, but I'm assuming there is some command I can use for compatibility. I'll check the documentation.
      Also, I'm not sure how much XP such mundane action should give?
    2. Dispensation
      Dispensation
      • premium
      • 3,072 posts
      • 199 kudos
      I don't use it, but I'm assuming there is some command I can use for compatibility. I'll check the documentation.

      "Ultimate Leveling can automatically support mods using that as long as they call the custom OnXPMessage event handler."

      Also, I'm not sure how much XP such mundane action should give?

      Probably similar to creating a potion, which is 6.5 XP I believe.

      I've also noticed some minor conflicts with Better Camps. I will make a patch probably:

      Spoiler:  
      Show
    3. qwertyasdfgh
      qwertyasdfgh
      • member
      • 793 posts
      • 110 kudos
      Version 1.01 should award XP for Ultimate Leveling. I would appreciate if someone using it could test if it works.
  8. ChampionKnifeFighter
    ChampionKnifeFighter
    • member
    • 414 posts
    • 5 kudos
    is weapons and armor craftable with this mod?
    1. qwertyasdfgh
      qwertyasdfgh
      • member
      • 793 posts
      • 110 kudos
      Not at the moment. I'm currently working on recipes for weapons; armor would soon follow.
    2. sonicthebandicoot
      sonicthebandicoot
      • member
      • 127 posts
      • 1 kudos
      this might help pickaxes to become a useful tool. use pickaxes to mine ore to craft things!
    3. DEEJMASTER333
      DEEJMASTER333
      • member
      • 1,419 posts
      • 74 kudos
      That’s already included in Maskar’s Oblivion Overhaul. In fact pretty much this whole mod as a concept is.
    4. SigilHunter
      SigilHunter
      • member
      • 31 posts
      • 15 kudos
      True, but this Crafting system is a much nicer implementation.
  9. Darkvisor66
    Darkvisor66
    • member
    • 97 posts
    • 0 kudos
    This seems very interesting. Was it based on the alchemy system's design? Always thought Oblivion had a robust crafting system hidden away in that.
    1. qwertyasdfgh
      qwertyasdfgh
      • member
      • 793 posts
      • 110 kudos
      Not really, it's completely separate. Built entirely on OBSE scripts.
  10. GeorgeCorbul
    GeorgeCorbul
    • member
    • 743 posts
    • 7 kudos
    Oooh, this is good! I'm currently using that Skyrim Crafting mod (forgot the actual name), but it's got too many esps, the grammar is a bit messy and the interface isn't very comfortable. Can't wait to see what people make of this framework!
  11. Xorpie
    Xorpie
    • premium
    • 286 posts
    • 8 kudos
    This. Is. Amazing. By Azura, I hope all crafting mods incorporate this framework into their mods.