Bagaimana cara menyesuaikan skrip yang dibuat secara otomatis?


11

Saat Anda membuat skrip melalui editor Unity, skrip tersebut menghasilkan skrip dengan beberapa kode yang telah diformat sebelumnya.

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class GenericClass : MonoBehaviour {

    // Use this for initialization
    void Start () {

    }

    // Update is called once per frame
    void Update () {

    }
}

Ketika saya membuat skrip, saya biasanya dijamin untuk menggunakan kode tambahan, seperti namespace atau editor khusus. Selain itu, saya hampir selalu menghapus konten dari skrip yang dibuat secara otomatis. Apakah ada cara untuk mengubah kode otomatis yang dihasilkan oleh Unity?


1
Saya bahkan tidak pernah berpikir untuk melakukan ini. Terima kasih untuk bertanya! Sekarang untuk menggabungkan dua jawaban untuk memiliki template dan kemudian menguraikannya untuk memasukkan informasi tambahan, seperti namespace ...
Draco18s tidak lagi mempercayai SE

Jawaban:


4

Selain itu kamu juga bisa

  1. Tambahkan skrip editor di folder Aset / Editor yang berlangganan OnWillCreateAssettempat Anda dapat menguraikan output dan memodifikasinya. Misalnya skrip yang secara otomatis memasukkan namespace dapat terlihat seperti berikut:

    using System.Collections.Generic;
    using System.IO;
    using System.Linq;
    using System.Text.RegularExpressions;
    
    using UnityEditor;
    
    public class InsertNS : UnityEditor.AssetModificationProcessor
    {
        public static void OnWillCreateAsset(string path)
        {
            string assetPath = Regex.Replace(path, @".meta$", string.Empty);
            if (!assetPath.EndsWith(".cs")) return;
    
            var code = File.ReadAllLines(assetPath).ToList();
            if (code.Any(line => line.Contains("namespace"))) return;//already added by IDE
    
            //insert namespace
            int idx = code.FindIndex(line => line
                .Contains("class " + Path.GetFileNameWithoutExtension(assetPath)));
            code.Insert(idx, Regex.Replace(
            assetPath.Replace('/','.'), @"^([\w+.]+)\.\w+\.cs$", "namespace $1 {\n"));
            code.Add("}");
    
            //correct indentation
            for (int i = idx + 1; i < code.Count - 1; i++) code[i] = '\t' + code[i];
    
            var finalCode = string.Join("\n", code.ToArray());
            File.WriteAllText(assetPath, finalCode);
            AssetDatabase.Refresh();
        }
    }
    
  2. Masukkan urutan kontrol sendiri ke dalam template untuk memudahkan penggantian OnWillCreateAsset, misalnya

    finalCode = finalCode.Replace(@"#date#", DateTime.Now);
  3. Tambahkan lebih banyak templat ke folder templat, misalnya satu untuk pola Singleton - Unity tidak terbatas pada templat skrip tunggal.

  4. Cuplikan kode visual studio adalah cara untuk menyesuaikan pembuatan skrip baru (... dan lebih jauh lagi - bagian skrip baru). Misalnya, cuplikan kode untuk pribadi SerializeFieldmungkin berguna. Setelah mengimpor privateField.snippet:

    <?xml version="1.0" encoding="utf-8"?>
    <CodeSnippets xmlns="http://schemas.microsoft.com/VisualStudio/2005/CodeSnippet">
      <CodeSnippet Format="1.0.0">
        <Header>
          <Title>
            Serialized private field
          </Title>
          <Author>Myself</Author>
          <Description>Adds private serializable field visible to Unity editor</Description>
          <Shortcut>pf</Shortcut>
        </Header>
        <Snippet>
          <Imports>
            <Import>
              <Namespace>UnityEngine</Namespace>
            </Import>
          </Imports>
          <Declarations>
            <Literal>
              <ID>FieldName</ID>
              <ToolTip>Replace with field name.</ToolTip>
              <Default>myField</Default>
            </Literal>
          </Declarations>
          <Code Language="CSharp">
            <![CDATA[[SerializeField] float _$FieldName$;]]>
          </Code>
        </Snippet>
      </CodeSnippet>
    </CodeSnippets>
    

    ke Tools / Code Snippet Manager / Cuplikan Kode Saya Anda cukup mengetik tab ganda "pf" dan ketik nama bidang. Misalnya:

    //"pf" tab tab "speed" produces
    [SerializeField] float _speed;
    

    Yang lebih nyaman adalah potongan untuk urutan berulang yang sering diulang, misalnya properti hanya baca yang didukung oleh SerializeFieldbidang.

  5. Visual studio juga menawarkan alat penghasil kode yang sangat kuat, Templat Teks T4 (EF menggunakan T4), meskipun saya pribadi menemukan penggunaan praktis untuk proyek Unity diragukan - mereka berlebihan, cukup rumit dan kompilasi proyek kemungkinan akan menjadi tergantung pada Visual Studio.


Ini bekerja seperti pesona! Saya telah menambahkan ruang nama yang relevan untuk pengguna masa depan. Saya juga punya satu masalah lagi, meskipun saya pikir itu mungkin satu keunikan bagi saya; Saya tidak bisa menggunakan Path.GetFileWithoutExtension. Ini memberitahu saya sedang mencoba mengakses MonoBehaviour, yang tampaknya aneh. Saya menyertakan namespace using Path = System.IO.Path.GetFileWithoutExtension, dan saya kehilangan Pathsemuanya. Pada akhirnya, saya harus sepenuhnya memagari garis itu sendiri ( .Contains("class " + System.IO.Path.GetFileNameWithoutExtension(assetPath)));).
Gnemlock

Apa cara paling sederhana untuk memastikan file dibuat dengan LF dan UTF-8 daripada CRLF dan UTF-8 dengan BOM?
Aaron Franke

@ AaronFranke yah ... permintaan itu agak spesifik. Saya akan mencoba bertanya pada stackoverflow.com bagaimana membuat string/ File.Writemenghasilkan LF-only dengan BOM. Sejauh yang saya tahu '\ n' seharusnya hanya LF, Anda juga bisa mencoba Environment.Newlinetetapi itu harus CRLF. Mungkin juga ada opsi untuk menggunakan kait git jika semuanya gagal. BOM seharusnya mudah dengan pertanyaan stackoverflow ini .
wonderra

15

Anda dapat menemukan templat skrip untuk menghasilkan kode secara otomatis di folder instalasi Unity Anda. Saya menemukan templat di bawah "Unity / Editor / Data / Resources / ScriptTemplates" , sementara sumber lain menemukannya di "Unity / Editor / Data / Resources" .

Templat UnityScript dan C # generik diidentifikasi sebagai file "82-Javascript-NewBehaviourScript.js.txt" dan "81-C # Script-NewBehaviourScript.cs.txt" , masing-masing. Anda dapat langsung mengedit file-file ini untuk mengubah cara Unity menghasilkan skrip otomatis.

Anda juga dapat menyertakan templat tambahan, yang akan muncul ketika Anda memilih "Buat" dari jendela "Proyek" . Templat tampaknya tidak memerlukan penomoran yang unik, dan gunakan string awal untuk menentukan hierarki menu, di mana "__" menunjukkan submenu. Misalnya, memiliki file bernama "81-C # Script__Editor Script-NewBehaviourScript.cs.txt" akan memberi Anda menu " C # Script" tambahan , dengan sub opsi untuk membuat "Editor Script" menggunakan templat ini.

Jangan tidak mengubah nama template asli; ini digunakan lebih langsung, oleh mesin. Misalnya, mengganti nama "81-C # Script-NewBehaviourScript.cs.txt" akan mencegah Anda menambahkan skrip C # baru sebagai komponen, langsung melalui inspektur.


Di bawah ini adalah contoh saya sendiri, meskipun itu menunjukkan praktik-praktik khusus yang paling saya sukai. Sebagai contoh, saya lebih suka memiliki skrip editor khusus saya di file yang sama dengan kelas target, jadi saya merangkumnya #if UNITY_EDITOR .. #endif, daripada menempatkannya di folder editor generik "jangan dikompilasi dalam build".

Saya tidak yakin apakah mungkin untuk menyediakan konteks ruang nama kustom; Saya cukup menggunakan "NAMESPACE", karena ini memungkinkan saya untuk memberikan namespace post-creation yang benar, menggunakan fungsi "find..replace all" yang umum dibuat.


Templat:

/* Created by Gnemlock */

using UnityEngine;

#if UNITY_EDITOR
using UnityEditor;
#endif

namespace NAMESPACE
{
    public class #SCRIPTNAME# : MonoBehaviour 
    {
        /// <summary>This method will be called at the start of each frame where this 
        /// instance of <see cref="NAMESPACE.#SCRIPTNAME#"/> is enabled.</summary>
        void Update ()
        {
            #NOTRIM#
        }
    }
}

namespace NAMESPACE.UTILITY
{
    #if UNITY_EDITOR
    [CustomEditor(typeof(#SCRIPTNAME#))] public class #SCRIPTNAME#Editor : Editor
    {
        public override void OnInspectorGUI()
        {
            DrawDefaultInspector();

            #SCRIPTNAME# s#SCRIPTNAME# = target as #SCRIPTNAME#;
        }
    }
    #endif
}

Hasil:

/* Created by Gnemlock */

using UnityEngine;

#if UNITY_EDITOR
using UnityEditor;
#endif

namespace MyNamespace
{

    public class UpdatedClass : MonoBehaviour 
    {
        /// <summary>This method will be called at the start of each frame where this 
        /// instance of <see cref="MyNamespace.UpdatedClass"/> is enabled.</summary>
        void Update ()
        {

        }
    }
}

namespace MyNamespace.UTILITY
{
    #if UNITY_EDITOR
    [CustomEditor(typeof(UpdatedClass))] public class UpdatedClassEditor : Editor
    {
        public override void OnInspectorGUI()
        {
            DrawDefaultInspector();

            UpdatedClass sUpdatedClass = target as UpdatedClass;
        }
    }
    #endif
}
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.