תבנית ברעיון של MVVM עבור VSTO XML RIBBON?
-
לאחרונה יצא לי לעבוד על פרויקט עם הרבה לחצנים בסרגל הכלים של וורד. אמרתי לעצמי שזה לא שפוי ואני חייב לעשות סדר בבלאגן באמצעות חלוקה למשהו כמו-MVVM (Model-View-ViewModel).
מכיון שה-ribbon xml לא באמת נותן גישה לאוסף של הפקדים חשבתי על הרעיון הבא:
הרעיון הוא לקרוא לכל מתודה על ידי ID של הלחצן באותו שם, ולהעביר את הלוגיקה הקשורה ללחיצה על הלחצן לתוך class נפרד ומסודר, מה שיעשה את הקוד יותר נקי וניתן לניהול.
(עוד לא יישמתי את הרעיון לגבי אייקונים אבל שם זה אמור להיות ממש עוצמתי מאחר ובצורה הזו כל מה שהמשתמש יצטרך לעשות זה להוסיף אייקון לפרוייקט ולקרוא לו בשם של הכפתור).
להלן דוגמאות עבור button1 ו-button2.
בתוך ה-callbacks יש להוסיף את הקודים הבאים:
private ButtonInvoker buttonInvoker; public Ribbon() { buttonInvoker = new ButtonInvoker(); }
public void button_Click(Office.IRibbonControl control) { buttonInvoker.InvokeButtonMethod(control.Id); }
במקום ליצור מתודה ייחודית לכל כפתור ב-XML, כל כפתור יקרא לאותה מתודה. הנה דוגמה ל-XML:
xml <?xml version="1.0" encoding="UTF-8"?> <customUI onLoad="Ribbon_Load" xmlns="http://schemas.microsoft.com/office/2006/01/customui"> <ribbon> <tabs> <tab id="tab1" label="Label"> <group id="MyCustomGroup" label="My Custom Group"> <button id="button1" label="Button 1" onAction="button_Click"/> <button id="button2" label="Button 2" onAction="button_Click"/> </group> </tab> </tabs> </ribbon> </customUI>
כעת, נוסיף את מחלקת ה-ButtonInvoker שתטפל בלחצנים:
public class ButtonInvoker { public void InvokeButtonMethod(string methodName) { try { MethodInfo method = this.GetType().GetMethod(methodName, BindingFlags.NonPublic | BindingFlags.Instance); if (method != null) { method.Invoke(this, null); } else { MessageBox.Show($"No method found for button ID: {methodName}"); } } catch (Exception ex) { MessageBox.Show($"Error invoking method for button ID: {methodName}. Error: {ex.Message}"); } } private void button1() { MessageBox.Show("Button 1 clicked"); } private void button2() { MessageBox.Show("Button 2 clicked"); } }
בעזרת הקוד הזה, הצלחנו לפשט את ניהול הלחצנים בסרגל הכלים של וורד ולהקטין את הבלאגן. כל לחצן מזוהה לפי ה-ID שלו וקורא לאותה מתודה כללית שמפעילה את המתודה המתאימה בהתאם ל-ID.
-
אני לא מסכים עם הכיוון.
אתה עושה ככה:
א. כותב id שונה בכל כפתור, שערכו כשם מתודה שאתה רוצה שטפל בו
ב. במטפל הכלל (button_Click) אתה משתמש עם שיקוף לאתר את המתודה ששמה כשם הid.זה זהה לגמרי לכתיבה ישירה של המתודה הרצויה בonAction למעט שאתה מרויח שהמתודות יכולות לשבת בקובץ נפרד (שאם זה כדבריך מגיע כבר עם תמיכה בMVVM אז אמור להיות כן אפשרי).