Search Unity

Question create multiple scripts instead of one

Discussion in 'Scripting' started by joveem_, Mar 28, 2023.

  1. joveem_

    joveem_

    Joined:
    Oct 28, 2017
    Posts:
    2
    In the "Project" window, when I go to "right click > create > C# script", I type a file name "FooScriptName" and ONE script "FooScriptName.cs" is created from a class "FooScriptName" inheriting from MonoBehaviour

    I created a new template for this default script with some changes that streamlined my default workflow (with "OnDestroy", "Awake" and some libraries that I always import)

    But I have started to make use of "partial classes" (aiming at code organization) and a very recurrent thing is to keep duplicating these standard scripts from the beginning, and always following the same naming pattern ("FooScriptName_View.cs" / " FooScriptName_Controller.cs" / "FooScriptName_Setup.cs" / etc)

    That said, I wanted to know if there was any way after I typed "FooScriptName" instead of creating just a script "FooScriptName.cs" I could create several scripts with their own names and templates (following this pattern of "FooScriptName" + suffix + ".cs") and preferably with the possibility of placing them in subfolders ("Controller" / "View" / etc)

    And if you don't have an easy way to do this (with an ease similar to that of changing the default template), I'd like to know an indication of ways I could achieve this (perhaps creating an editor tool or something of the sort, since I don't I understand enough about editor tools programming to know if this would be possible or where to start)
     
  2. Kurt-Dekker

    Kurt-Dekker

    Joined:
    Mar 16, 2013
    Posts:
    38,745
    This is an awesome process. Partial classes are GREAT, especially in Unity, allowing for far better organization and readability.

    I do this by hand... here's how.

    First I make the base MonoBehaviour class, let's say
    Foo.cs


    Now that you've made that file, add the
    partial
    specifier to it.

    Now just Command-D to dupe the file and name it
    Foo1.cs
    and remove the MonoBehaviour lineage from Foo1.cs

    From now on you never add anything to Foo1.cs. Just leave it there as an empty husk.

    Now anytime you need a new partial of that class, simply Command-D the Foo1.cs file and rename it.

    Usually my Foo.cs will be the ONLY file that has MonoBehaviour in its spec.

    That will also be the file with the primary Unity callbacks: Awake, Start, Update, FixedUpdate, OnEnable, etc.

    ALSO: Be prepared for a whole angry raving army of CompSci-100 types to roar about how bad partials are and how you are wrecking your codebase. Just smile and enjoy your well-organized simple small files.

    Screen Shot 2023-03-28 at 7.19.05 AM.png Screen Shot 2023-03-28 at 7.16.38 AM.png
     
  3. RadRedPanda

    RadRedPanda

    Joined:
    May 9, 2018
    Posts:
    1,648
    I think you could use OnPostprocessAllAssets to get the name of every object you create, check the file name to see if it would be a partial class, and then just manually re-write the script. Unfortunately, I think if you imported any partial scripts from somewhere else, it would just straight up re-write them, so I think you would also have to check if it's not the Unity generated script at the start. Not sure how much overhead this has though.
     
    joveem_ likes this.
  4. Max-om

    Max-om

    Joined:
    Aug 9, 2017
    Posts:
    499
    I think that while partial classes were once useful for extending auto-generated code, they are no longer justified in modern C#. Today, features such as extension methods or composition provide cleaner and more efficient alternatives for achieving the same functionality. Furthermore, partial classes introduce unnecessary complexity and tight coupling, which can make code maintenance and refactoring more difficult.
     
  5. Bunny83

    Bunny83

    Joined:
    Oct 18, 2010
    Posts:
    4,005
    Well, that's of course open for debate. I also wouldn't overuse them like Kurt did :) However they are a feature in your tool belt and there are always usecases which actually make a lot things simpler and easier. They allow you to modularize a class or whole framework and extensions have full access to private members. Since we are still inside the same type, it makes adding (implicit / explicit) conversion operators.

    Though this is kinda off-topic ^^. The creation of multiple source files would be the perfect job for a ScriptableWizard which many don't even know about. They are explicitly designed to open a "configuration window" where you can setup input data and then you submit the wizard by pressing the create button. What will happen when you do that is completely up to you. You can simply create those files yourself, define your own template code, search replace placeholders as you need and finally refresh the assetdatabase to actually compile and import the newly created files.

    A ScriptableWizard is essentially just an ordinary EditorWindow with a whole framework wrapped around. It shows public serializable fields automatically in the wizard like the inspector does. Though you can override the DrawWizardGUI method to extend or replace this behaviour if necessary. The Unity editor is just the perfect tool to do whatever you can think of. People created all sorts of EditorWindows. For example a telnet config dialog. I once made an EditorWindow which essentially wraps a CMD.exe process. You can actually enter commands and the output is shown in the window. You could create git tools directly inside Unity. Literally anything you can imagine (and implement)
     
    spiney199 likes this.
  6. Max-om

    Max-om

    Joined:
    Aug 9, 2017
    Posts:
    499
    There are usecases for goto in c# too ;)
     
  7. Bunny83

    Bunny83

    Joined:
    Oct 18, 2010
    Posts:
    4,005
    There are, but most cases can be worked around by simply using a subroutine / method so you can simply use return :) Yes, there are still cases left where its easier / faster to use goto, but in general it should be used sparingly.