如何为项目脚本添加代码行及指定位置的[DoNotRename]属性?
Hey there! Let's break this down for you—first addressing your specific request for adding the [DoNotRename] attribute, then covering the general approach to adding code lines to any script.
[DoNotRename] Attribute to Unity Scripts (Editor Script Implementation) Since your example uses MonoBehaviour, I’ll focus on a Unity Editor script solution that fits your exact requirement: inserting the attribute right after using directives and before the class definition.
Step 1: Prepare the Editor Folder
Unity requires editor-only scripts to live in a folder named Editor (create one in your Project window if you don’t have it). This ensures the code only runs in the Editor, not in game builds.
Step 2: The Full Editor Script
Here’s a ready-to-use script that handles bulk modifications, avoids duplicate attributes, and accounts for common formatting cases (like empty lines after using directives):
using UnityEditor; using UnityEngine; using System.IO; public static class AddDoNotRenameTool { [MenuItem("Assets/Add [DoNotRename] Attribute")] public static void AddAttributeToSelectedScripts() { // Process all selected C# scripts foreach (Object selectedObj in Selection.objects) { string assetPath = AssetDatabase.GetAssetPath(selectedObj); // Skip non-C# files if (!assetPath.EndsWith(".cs")) continue; string scriptContent = File.ReadAllText(assetPath); string updatedContent = InsertAttributeAtTargetPosition(scriptContent); // Only save if changes were made if (updatedContent != scriptContent) { File.WriteAllText(assetPath, updatedContent); AssetDatabase.Refresh(); Debug.Log($"Added [DoNotRename] to: {assetPath}"); } else { Debug.Log($"[DoNotRename] already exists in: {assetPath}"); } } } private static string InsertAttributeAtTargetPosition(string content) { // Find the end of the using directives block int lastUsingIndex = content.LastIndexOf("using "); if (lastUsingIndex == -1) { // No using directives—insert right before the class int classStartIndex = content.IndexOf("public class"); if (classStartIndex != -1) { return content.Insert(classStartIndex, "[DoNotRename]\n"); } return content; } // Move past the last using line to find the start of post-using content int nextNewLine = content.IndexOf('\n', lastUsingIndex); if (nextNewLine == -1) nextNewLine = content.Length; // Skip any empty lines after the using block while (nextNewLine < content.Length && char.IsWhiteSpace(content[nextNewLine])) { nextNewLine++; } // Check if the attribute already exists to avoid duplicates string previewSegment = content.Substring(nextNewLine, Mathf.Min(50, content.Length - nextNewLine)); if (previewSegment.Contains("[DoNotRename]")) { return content; } // Insert the attribute and a newline return content.Insert(nextNewLine, "[DoNotRename]\n"); } }
How to Use It
- Right-click one or more C# scripts in your Unity Project window
- Select
Assets > Add [DoNotRename] Attributefrom the context menu - The tool will automatically add the attribute in the correct position for all selected scripts
For broader use cases (not just this specific attribute), the core workflow is:
- Read the script file: Use
File.ReadAllText()(or similar I/O methods) to load the script content as a string - Locate the target position: Use string methods like
IndexOf(),LastIndexOf(), or regex (for complex patterns) to find where you want to insert the code - Insert the new line: Use
string.Insert()to add your code at the calculated position - Save and refresh: Write the updated content back to the file, and refresh the asset database (in Unity) to apply changes
If you’d rather not write custom code:
- Unity Asset Store: Tools like CodeAssist or Bulk Code Modifier offer configurable bulk editing features that can be set up to add attributes or code lines
- Roslyn Analyzers: For more advanced scenarios, you can use Roslyn (the .NET compiler platform) to parse and modify C# code programmatically—this is powerful but has a steeper learning curve
For your specific need, the custom editor script above is lightweight and tailored exactly to what you’re asking for.
内容的提问来源于stack exchange,提问作者user13619793

