說明(2017-12-22 11:20:44):
1. 因為數學腳本的主標題和副標題沒有格式,目錄導航里不顯示,修改的時候不好定位,所以需要改成下圖格式:
2. 問題的難點有兩個,一個是word的操作,c#操作word本來應該是順理成章、水到渠成的,不過實際上並沒有很好的參考資料,最權威的MSDN雖然很詳細,但是內容太多、查找起來太費勁https://msdn.microsoft.com/vba/vba-word。我查到的一個比較精簡的word操作,https://www.cnblogs.com/shi2172843/p/5848116.html,應付一般的問題足夠了。但是還有很多不常用的設置,比如我這個設置標題,網上根本就查不到了,研究了半天,得出一個終極結論:使用VBA錄制宏,然后去VS里通過智能提示,找到C#里對應的方法,基本跟VBA里的名字是一樣的,比如:
VBA里的設置標題,和左對齊:
C#里的設置標題,和左對齊:
3. 問題的第二個難點是,C#對文件的操作,因為設計目標是把文件夾里所有的word文件都獲取到,但是Directory.GetDirectories和Directory.GetFiles只能獲取一層文件夾里的子文件夾和文件,如果里面還有子文件夾的話就拿不到了。這個問題拖了好幾天,昨天晚上靈光一現給解決了。似乎是用了遞歸,因為一直覺得遞歸挺難的,之前查的資料也是用的遞歸,但是我看不太懂,http://blog.csdn.net/kwy15732621629/article/details/72085701,我對那種參數很多、封裝很好的方法有點抵觸,就決定自己試着寫了一個,我記得之前好像是蔣坤說的,遞歸有兩個特點,一個是調用自身,一個是要有返回值,特別注意不要出現無限遞歸。我覺得自己寫的這個方法這兩點都做到了,反正寫完測試了一下,可以正常獲取所有子目錄文件。代碼如下,應該是很通俗易懂了:
1 using System; 2 using System.Collections.Generic; 3 using System.Linq; 4 using System.Text; 5 using System.IO; 6 7 namespace _00_Test 8 { 9 10 class Program 11 { 12 static void Main(string[] args) 13 { 14 string path = @"C:\Users\JJW\Desktop\新建文件夾"; 15 List<string> list = GetFile(path); 16 foreach (string l in list) 17 { 18 Console.WriteLine(l); 19 } 20 Console.ReadKey(); 21 } 22 private static List<string> GetFile(string path) 23 { 24 //傳入一個路徑 25 List<string> list = new List<string>(); 26 //如果路徑是文件夾,繼續遍歷,把新遍歷出來的文件夾和文件存到list 27 if (Directory.Exists(path)) 28 { 29 string[] dirs = Directory.GetDirectories(path); 30 if (dirs != null) 31 { 32 foreach (string dir in dirs) 33 { 34 list.AddRange(GetFile(dir)); 35 } 36 } 37 38 string[] files = Directory.GetFiles(path); 39 if (files != null) 40 { 41 list.AddRange(files); 42 } 43 } 44 //如果路徑是文件,添加到list 45 else if (File.Exists(path)) 46 { 47 list.Add(path); 48 } 49 return list; 50 } 51 } 52 }
4. 剩下的是完整代碼,為了自己以后方便抄的,不放winform的了,反正就拖一下完事:
Form1.cs
1 using System; 2 using System.Collections.Generic; 3 using System.ComponentModel; 4 using System.Data; 5 using System.Drawing; 6 using System.Linq; 7 using System.Text; 8 using System.Windows.Forms; 9 using System.IO; 10 using msWord = Microsoft.Office.Interop.Word; 11 12 namespace CheckLabel 13 { 14 public partial class Form1 : Form 15 { 16 public Form1() 17 { 18 InitializeComponent(); 19 } 20 21 private void btnOK_Click(object sender, EventArgs e) 22 { 23 //實例化wordapp類 24 msWord.Application app = new msWord.Application(); 25 //操作時顯示word,測試時使用,實際使用時隱藏就可以了 26 app.Visible = false; 27 //判斷拖入的文件夾是否存在 28 if (Directory.Exists(txtBox.Text)) 29 { 30 //獲取路徑下所有doc和docx文件,如果拖入的是文件夾,就需要繼續遍歷文件夾,這里有兩種方式,一種是遞歸遍歷,另一種根據文件夾結構讀取每個文件夾,反正每個版本就一層文件夾。 31 //string[] paths = Directory.GetFiles(Path.GetDirectoryName(txtBox.Text), "*.doc*"); 32 List<string> files = GetFile(txtBox.Text); 33 //兩個泛型,A是標題1,B是副標題 34 List<string> labelA = new List<string> { "課前預習導學", "課后復習鞏固", "自我測試及解答", "能力提升" }; 35 List<string> labelB = new List<string> { "定義及說明", "簡單例題", "(三)練習", "課堂回顧", "經典例題及解答點撥", "寫作業", "中考知識點", "中考真題及解答", "拓展提高及解答" }; 36 37 //遍歷所有路徑 38 foreach (string file in files) 39 { 40 //判斷doc文件是否存在 41 if (File.Exists(file)) 42 { 43 Console.WriteLine(file); 44 //實現wordapp.document接口,打開word 45 msWord.Document doc = app.Documents.Open(file); 46 //獲取word全文為字符串,沒用上 47 //string temp = doc.Content.Text.Trim(); 48 //遍歷所有段落,注意要從1開始,paragraph從1開始而不是從0!! 49 //for (int i = 1; i <= doc.Paragraphs.Count; i++) 50 //{ 51 // Console.WriteLine(doc.Paragraphs[i].Range.Text); 52 //} 53 ///* 54 //用foreach循環也可以 55 foreach (msWord.Paragraph para in doc.Paragraphs) 56 { 57 foreach (string lA in labelA) 58 { 59 //如果段落里包含標題1的文字 60 if (para.Range.Text.Contains(lA)) 61 { 62 //測試一下改顏色 63 //para.Range.Font.ColorIndex = msWord.WdColorIndex.wdBlue; 64 para.Range.set_Style("標題 1"); 65 Console.WriteLine("已處理:" + para.Range.Text); 66 } 67 else 68 { 69 //Console.WriteLine(para.Range.Text + "不包含" + lA); 70 } 71 } 72 foreach (string lB in labelB) 73 { 74 //如果段落里包含標題1的文字 75 if (para.Range.Text.Contains(lB)) 76 { 77 para.Range.set_Style("副標題"); 78 para.Range.ParagraphFormat.Alignment = msWord.WdParagraphAlignment.wdAlignParagraphLeft; 79 Console.WriteLine("已處理:" + para.Range.Text); 80 } 81 else 82 { 83 //Console.WriteLine(para.Range.Text + "不包含" + lB); 84 } 85 } 86 } 87 //*/ 88 doc.Save(); 89 doc.Close(true); 90 } 91 else 92 { 93 MessageBox.Show(file + " ,word文件不存在!"); 94 } 95 } 96 } 97 98 else 99 { 100 MessageBox.Show(txtBox.Text + "文件夾不存在!"); 101 } 102 app.Quit(); 103 MessageBox.Show("修改完畢!"); 104 } 105 106 107 private List<string> GetFile(string path) 108 { 109 //獲取所有目錄包括子目錄的文件 110 //傳入一個路徑 111 List<string> list = new List<string>(); 112 //如果路徑是文件夾,繼續遍歷,把新遍歷出來的文件夾和文件存到list,用了遞歸 113 if (Directory.Exists(path)) 114 { 115 string[] dirs = Directory.GetDirectories(path); 116 if (dirs != null) 117 { 118 foreach (string dir in dirs) 119 { 120 list.AddRange(GetFile(dir)); 121 } 122 } 123 124 string[] files = Directory.GetFiles(path); 125 if (files != null) 126 { 127 list.AddRange(files); 128 } 129 } 130 //如果路徑是文件,添加到list 131 else if (File.Exists(path)) 132 { 133 list.Add(path); 134 } 135 return list; 136 } 137 138 private void btnSelect_DragEnter(object sender, DragEventArgs e) 139 { 140 //拖進文件夾,獲取信息 141 if (e.Data.GetDataPresent(DataFormats.FileDrop)) 142 e.Effect = DragDropEffects.All; 143 else 144 e.Effect = DragDropEffects.None; 145 } 146 147 private void btnSelect_DragDrop(object sender, DragEventArgs e) 148 { 149 //拖動松手后,獲得路徑 150 string path = ((System.Array)e.Data.GetData(DataFormats.FileDrop)).GetValue(0).ToString(); //獲得路徑 151 txtBox.Text = path; 152 } 153 154 private void btnSelect_Click(object sender, EventArgs e) 155 { 156 //選擇文件夾 157 //FolderBrowserDialog fbd = new FolderBrowserDialog(); 158 //fbd.SelectedPath = @"c:\"; 159 //if (fbd.ShowDialog() == DialogResult.OK) 160 //{ 161 // txtBox.Text = fbd.SelectedPath; 162 //} 163 //選擇文件 164 OpenFileDialog ofd = new OpenFileDialog(); 165 if (ofd.ShowDialog() == DialogResult.OK) 166 { 167 //C:\Users\JJW\Desktop\新建文件夾\1_負數的引入.doc 168 txtBox.Text = ofd.FileName; 169 } 170 } 171 172 173 } 174 }
設計器:
結束。