تقييم الموضوع :
  • 0 أصوات - بمعدل 0
  • 1
  • 2
  • 3
  • 4
  • 5
توسيع مجال الأسماء My باستخدام My Extensibility
#1
كاتب الموضوع : samerselo

تم تقديم مجال الأسماء My بدءا من Visual Basic 2005 ليوفر اختصارات للطرائق واستدعاءات API الشائعة ومنذ ذلك الوقت كان يمكن للمستخدمين كتابة توسعاتهم الخاصة لمجال الأسماء My مضيفين له مكتبات الكود الخاصة بهم. وقد قدم My Extensiility كجديد في Visual Basic 2008 مما سهل توسيع المجال My. ومع ميزة My Extensibility الجديدة أصبح بالإمكان تفعيل وإلغاء تفعيل My Extensibility من خلال مصمم المشاريع أو عندما يتم ربط أو إزالة مرجع لمجمع في المشروع الأمر الذي جعل عملية توسيع بيئة تطوير Visual studio أكثر بساطة.

طرق توسيع المجال My
هناك القليل من نماذج الكود التي يمكن استخدامها لتوسيع المجال My. والطريقة الأسهل لعمل ذلك هي تلك التي نعرفها سابقا فعملية إضافة أي شئ للمجال My هي عملية مماثلة لعملية إضافة أي شئ لأي مجال أسماء آخر كما في المثال


كود :
Namespace My.HandyStuffForMy
<Global.Microsoft.VisualBasic.HideModuleName()> _
Friend Module HandyStuffForMyModule
Sub Foo()
...
End Sub

Property Bar()
...
End Property
End Module
End Namespace
الذي يجعل الإجراء Foo و الخاصية Bar يظهران ضمن المجال HandyStuffForMy ضمن المجال My. حيث استخدمنا الواصفة attribute المسماة HideModuleName التي تمنع اسم الـ module من الظهور لأنك لا تحتاجه للوصول إلى العناصر المحتواة ضمنه. وإن أردت إضافة هذه العناصر للمجال My بدون إنشاء مجال فرعي عدل اسم المجال في الكود السابق ليصبح My فقط كما يلي


كود :
Namespace My
<Global.Microsoft.VisualBasic.HideModuleName()> _
Friend Module HandyStuffForMyModule
Sub Foo()
...
End Sub

Property Bar()
...
End Property
End Module
End Namespace
وإن استخدمت اسم مجال موجود سلفا ضمن المجال My كـ Resources مثلا فهذه العناصر سيتم إضافتها لذلك المجال مما يعطيك مرونة كبيرة في كيفية الوصول إلى توسعاتك. والشئ الذي يجب الانتباه إليه هو محدد الوصول فمحدد الوصول Friend سيقوم بمنع المجمعات الأخرى من الوصول إلى هذه العناصر وإن استخدمت محدد الوصول Public ربما تتضارب هذه العناصر مع رموز معرفة في المشاريع الأخرى التي تستخدم المجال My
}}}
تم الشكر بواسطة:
#2


التوسيع باستخدام الورقة المفردة Singleton
My.Computer و My.Settings و My.Application هي تواجدات وحيدة الورقة Singleton Instances للفئات My.MyComputer و My.MySettings و My.MyApplication حيث يمكننا إضافة عناصر لهذه الفئات بسهولة باستخدام ميزة الفئات المجزأة Partial Class فمثلا الكود التالي يضيف إجراء يدعى Shutdown للغرض My.Computer


كود :
Namespace My
Partial Class MyComputer
Sub Shutdown()
...
End Sub
End Class
End Namespace
كما يمكن استخدام هذا الكود لتوسيع My.Application و My.Settings أيضا حيث تمكنك ميزة الفئات المجزأة من إضافة عناصر إلى فئات معرفة في مكان آخر وهذا يتضمن فئات مثل MyComputer في مشاريع Visual Basic حيث يقوم المترجم بحقن الفئات قبل أن يتم ترجمة الكود.
وإذا أردت جعل عناصرك التي قمت بإضافتها يمكن الوصول إليها كورقة مفردة مثل الفئات المذكورة يجب عليك إضافة خاصية للقراءة فقط للمجال My تعيد تواجدا عاما يماثل ذلك المزود من ThreadSafeObjectProvider(Of T) الذي يقوم بإنشاء صورة من تلك الفئة على مستوى المسلك Thread والكود التالي يرينا كيفية إضافة My.CustomMyObject مع عناصره


كود :
Namespace My
<Global.System.ComponentModel.EditorBrowsable _
(Global.System.ComponentModel.EditorBrowsableState.Never)> _
Partial Friend Class MyCustomMyObject
Public Sub Foo()
...
End Sub

Public Property Bar()
...
End Property
End Class

<Global.Microsoft.VisualBasic.HideModuleName()> _
Friend Module CustomMyObjectModule
Private instance As ThreadSafeObjectProvider(Of MyCustomMyObject)

ReadOnly Property CustomMyObject() As MyCustomMyObject
Get
Return instance.GetInstance()
End Get
End Property
End Module
End Namespace
}}}
تم الشكر بواسطة:
#3


كتابة التوسع
سنبدأ بتشغيل Visual Studio وإنشاء تطبيق كونسول جديد وتسميته MyValidation وأضافة Module جديدة للمشروع وتسميتها MyValidation.vb ثم استبدل كامل الكود الموجود بالكود التالي


كود :
Imports System.Text.RegularExpressions
Imports System
Imports System.Linq
Imports Microsoft.VisualBasic

Namespace My.Validation
<Global.Microsoft.VisualBasic.HideModuleName()> _
Public Module MyValidationMod
Public Function IsEmpty(ByVal value As Object) As Boolean
If (value Is Nothing) OrElse _
(value Is System.DBNull.Value) OrElse _
(value.ToString = String.Empty) OrElse _
(TypeOf value Is Date AndAlso CDate(value) = Date.MinValue) _
Then
Return True
Else
Return False
End If
End Function

Public Function IsAlphaNumeric(ByVal value As String, _
Optional ByVal emptyOK As Boolean = False, Optional ByVal _
whitespaceOK As Boolean = False) As Boolean
If IsEmpty(value) Then Return emptyOK

Dim expr As String
If whitespaceOK Then
expr = "^[a-zA-Z0-9\s]+$"
Else
expr = "^[a-zA-Z0-9]+$"
End If

Return Regex.IsMatch(value, expr)
End Function

Public Function IsCanadianProvince(ByVal st As String) As Boolean
Dim allProv = "|AB|BC|MB|NB|NL|NT|NS|NU|ON|PE|QC|SK|YT"
Return st.Length = 2 AndAlso allProv.IndexOf("|" & st) <> -1
End Function

Public Function IsUSAState(ByRef st As String) As Boolean
Dim allStates = "|AL|AK|AZ|AR|CA|CO|CT|DE|FL|GA|HI|ID|IL|IN|IA|" & _
"KS|KY|LA|ME|MD|MA|MI|MN|MS|MO|MT|NE|NV|NH|NJ|NM|NY|NC|ND|OH|" & _
"OK|OR|PA|RI|SC|SD|TN|TX|UT|VT|VA|WA|WV|WI|WY"
Return st.Length = 2 AndAlso allStates.IndexOf("|" & st) <> -1
End Function

Public Function IsUSAPostalCode(ByVal zip As String) As Boolean
If String.IsNullOrEmpty(zip) Then Return False

Return Regex.IsMatch(zip, "^\d{5}(-\d{4})?$")
End Function

Public Function IsCanadianPostalCode(ByVal zip As String) As Boolean
If String.IsNullOrEmpty(zip) Then Return False

Return Regex.IsMatch(zip, "^[A-Z]\d[A-Z] \d[A-Z]\d$")
End Function

Public Function IsNorthAmericanPhone(ByRef phone As String) As Boolean
If String.IsNullOrEmpty(phone) Then Return False

Dim expr As String = "^(?:\([2-9]\d{2}\)\ ?|[2-9]\d{2}" & _
"(?:\-?|\ ?))[2-9]\d{2}[- ]?\d{4}$"

Return Regex.IsMatch(phone, expr)
End Function

Public Function IsEmail(ByRef email As String) As Boolean
If String.IsNullOrEmpty(email) Then Return False

Dim localPartCharset = "[0-9a-zA-Z!#$%*/?|\^{}`~&'+\-=_]"
Dim domainPartCharset = "[0-9a-zA-Z\-]"
Dim expr = String.Format("^{0}+(\.{0}+)*@{1}+(\.{1}+)*", _
localPartCharset, domainPartCharset)

Return Regex.IsMatch(email, expr)
End Function
End Module
End Namespace

عليك أن تكون حذرا عندما تقوم بإنشاء قالب My Extension يمكن أن يستخدم في تعريف أي مشروع فيجب عليك الانتباه بشكل خاص إلى القيم المحتملة لـ Option Explicit و Option Strict و Option Compare و Option Infer عندها يمكنك كتابة كودك ليعمل ضمن التعريف الأقل مرونة أو تحديد كل تعريف بشكل خاص في بداية كل ملف كود في توسعتك الذي يعتبر الأمر الأفضل.
كما يجب أن تأخذ إمكانية الاستيرادات المختلفة في المشاريع لتجنب التضارب في الرموز المعرفة على مستوى المشروع وهنا عليك تعديل أي رموز غير معرفة في قالبك بالكلمة المحجوزة Global أو My فمثلا بدلا من استخدام Text.Encoding استخدم Global.Text.Encoding فإن استخدمت Text.Encoding فقط فلن يعمل قالبك في تطبيقات Windows Forms التي ستستورد عندها مجالي أسماء مسميان Text فإن حذفت Global واستخدمت فقط System.Text.Encoding فربما لن يعمل قالبك الذي يحدد مجال أسماء يدعى System. ويعتبر اختبار كودك جيدا قبل توزيعه على الآخرين من الأفكار الجيدة ولا تشذ My Extensions عن هذه القاعدة.
دعنا نستخدم الـ Module التي تم إنشاؤها آليا باسم Module1 لكتابة تجربة لـ My Extensions ويجدر الانتباه إلى انه سيكون من الصعب إعادة استيراد التوسعات عندما تجد شائبة bug لذا عليك محاولة جعل التوسعة تعمل بشكل كامل قدر الإمكان والتأكد من أنها مختبرة جيدا قبل أن تقوم بتصديرها للمرة الأولى. قم بفتح Module1.vb وذلك بالنقر المزدوج عليها في Solution Explorer واستبدل الكود الموجود بالكود التالي ثم اضغط F5 لتشغيل المشروع


كود :
Module Module1
Private testNumber As Integer
Private testGroup As String

Sub StartTestGroup(ByVal name As String)
testGroup = name
testNumber = 0
End Sub

Sub Test(ByVal result As Boolean, ByVal expected As Boolean)
testNumber += 1

If result <> expected Then
Console.WriteLine("Test #{0} of group {1} FAILED.", _
testNumber, testGroup)
End If
End Sub

Sub Main()

StartTestGroup("IsAlphaNumeric")
Test(My.Validation.IsAlphaNumeric("123HH2", True, True), True)


StartTestGroup("IsCanadianPostalCode")
Test(My.Validation.IsCanadianPostalCode("H0H 0H0"), True)


StartTestGroup("IsCanadianProvince")
Test(My.Validation.IsCanadianProvince("ON"), True)


StartTestGroup("IsEmail")
Test(My.Validation.IsEmail("a@b.com"), True)

Console.WriteLine _
("Tests are finished. No FAILED messages indicates success.")
Console.WriteLine("Press any key to continue.")

Console.ReadKey(True)
End Sub
End Module
}}}
تم الشكر بواسطة:
#4


توضيب التوسعات كقوالب
بعد أن تمت كتابة التوسعة واختبرت بشكل كامل حان الوقت لتوضيبها كقالب My Extension. ولعمل ذلك اترك المشروع مفتوحا واختر الأمر Export Template من القائمة File فيظهر لك معالج Export Template حيث سنختار item Template من نافذة المعالج كما يتوفر لك خيار في الأسفل لاختيار اسم المشروع الذي سنصدر القالب منه ثم اضغط next ومن قائمة Item to export اختر MyValidation.vb ثم اضغط next ثم عليك اختيارا جميع المراجع الضرورية لعمل قالبك ومن أجل هذا المشروع اختر System.Core ثم اضغط next ثم املآ Template Description وقم بإزالة الإشارة عن الخيار Automatically import the template into Visual Studio الذي يجعل بيئة التطوير لا تقوم باستيراد القالب مباشرة بعد تصديره ثم اضغط Finish
}}}
تم الشكر بواسطة:
#5


My Extensions as Templates
في قالب My Extension كما هو الحال في جميع قوالب Visual Studio تكون جميع محددات القالب متوفرة وهي عبارة عن سلاسل نصية خاصة يمكن إدراجها آليا ضمن كود My Extension عندما يتم إضافتها للمشروع فـ $clrversion$ يتم استبدالها برقم النسخة الحالية لـ clr وفي حالة القالب Mu Extension سيتم استبدال $safeitemname$ بقيمة العنصر <DefaultName> في الملف الذي يحمل اللاحقة vstemplate والذي يساوي اسم الملف الذي يحوي كود القالب بدون لاحقته.
وأي شئ آخر يمكن عمله في قالب نظامي يمكنك عمله في القالب My Extension فضبط القيمة <Hidden> في الملف vstemplate إلى False يمكنك من إضافة القالب إلى صندوق الحوار Add New Item عندما تضيف العناصر للمشروع كما يمكنك إجبار إضافة مجمعات للمشروع عند إضافة القالب وذلك ضمن القسم <References> ويمكن إضافة عائلة من ملفات الكود عند انتهائها كالتي يتم إنشاؤها من قبل محرر نماذج ويندوز ذا بالإضافة إلى كود المستخدم.
كما توجد بعض الاختلافات الأساسية بين القوالب الأساسية وقوالب My Extensibility فلكي تمكن قالب العنصر Item Template كي يتم إدارتها من قبل صفحة My Extensions في مصمم مشاريع Visual Basic يجب عليك القيام بعدة خطوات لتعريفها بشكل ملائم.
في البداية يجب عليك إضافة العنصر <CustomDataSignature> للملف MyTemplate.vstemplate المتواجد في ملف zip الذي تم تصديره الذي يشير إلى أن قالب العنصر يجب معاملته كـ My Extension كما يجب عليك منع القالب من الفتح بشكل آلي عندما يتم إضافته للمشروع وذلك بإضافة بعض الصفات للعنصر <ProjectItem> بسبب أن كود MyExtension يجب أن يكون غير مرئي للمستخدم كما يجب عليك إضافة العنصر <Hidden> للملف MyTemplate.vstemplate كي لا يظهر القالب ضمن قائمة القوالب المثبتة عندما يختار المستخدم إضافة عناصر لمشروعه من خلال صندوق الحوار Add New Item وأخيرا عليك إضافة ملف باللاحقة customdata للرزمة وذلك لتوفير معلومات لا تنطبق على القوالب القياسية مثل unique Id و Version number و trigger assembly. ولعمل هذا عليك فك الملف ذو اللاحقة zip والقيام بالتعديلات المناسبة ثم إعادة ضغط الملفات الضرورية ثانية.
في البداية قم بفك محتويات القالب الذي قمنا بتصديره سابقا إلى مجلد فارغ ثم افتح الملف myTemplate.vstemplate وقم بالتعديلات كما في الكود


كود :
<VSTemplate Version="2.0.0"
xmlns=http://schemas.microsoft.com/developer/vstemplate/2005
Type="Item">
<TemplateData>
<DefaultName>MyValidation.vb</DefaultName>
<Name>MyValidation</Name>
<Description>Extends the My namespace with a set of string
validation methods.</Description>
<ProjectType>VisualBasic</ProjectType>
<SortOrder>10</SortOrder>
<Icon>TemplateIcon.ico</Icon>

<!-- Configures the template to not be shown as an option
when the user selects to add an item template to his project -->
<Hidden>true</Hidden>

<!-- Indicates it is to be treated as a My Extension. -->
<CustomDataSignature>Microsoft.VisualBasic.MyExtension
</CustomDataSignature>

</TemplateData>
<TemplateContent>
<References>
<Reference> <Assembly>System.Core</Assembly> </Reference>
</References>
<ProjectItem SubType="Code" TargetFileName="$fileinputname$.vb"
ReplaceParameters="true" OpenInEditor="false"
OpenInWebBrowser="false" OpenInHelpBrowser="false">MyValidation.vb
</ProjectItem>
</TemplateContent>
</VSTemplate>
أنشئ ملفا جديدا - سوف نضيفه للرزمة لاحقا - وسمه MyValidation.customdata وافتحه بواسطة الـ Notepad وأضف إليه الكود التالي


كود :
<VBMyExtensionTemplate
ID="MyValidationMyNamespaceExtension"
Version="1.0.0.0" />
والواصفة AssemblyFullName التي تم حذفها في هذا المثال تشير إلى أنه عندما يتم إضافة هذا المجمع للمشروع فسوف يتم دعوة المستخدم لإضافة My Extension وعندما يزال المجمع من المشروع فسوف يتم دعوة المستخدم لإزالة My Extension ولإضافة مجمع قدح Trigger Assembly يمكن إضافة قسم كالتالي للملف customdata


كود :
<VBMyExtensionTemplate
ID="MyValidationMyNamespaceExtension"
Version="1.0.0.0"
AssemblyFullName="System.Windows.Forms" />
قم الآن بإعادة نسخ جميع الملفات لداخل الملف zip باستخدام Windows Explorer
}}}
تم الشكر بواسطة:
#6

الملف vbproj
التعامل مع My Extension هو عملية مخفية آلية ولكي يقوم Visual Studio بمعالجتها بسلاسة باستخدام دخل قليل من المستخدم أصبح لملف المشروع الذي يحتوي على التوسعة بعض الصفات الجديدة التي يمكنك رؤيتها إذا قمت بفتح الملف ذو اللاحقة vbproj الخاص بالمشروع الذي قمت بإضافة التوسعة MyValidation إليه بأي محرر نصي فسوف ترى شيئا شبيها بالتالي


كود :
<ItemGroup>
...
<Compile Include="My Project\MyExtensions\MyValidation.vb">
<VBMyExtensionTemplateID>
MyValidationMyNamespaceExtension
</VBMyExtensionTemplateID>
<VBMyExtensionTemplateVersion>
1.0.0.0
</VBMyExtensionTemplateVersion>
</Compile>
...
</ItemGroup>
ولكن إذا ألقيت نظرة على القسم الخاص بملف كود أساسي مثل الملف Module1.vb فسوف ترى


كود :
<ItemGroup>
<Compile Include="Module1.vb" />
</ItemGroup>
وكما ترى هناك بعض الاختلافات فالملف MyValidation.vb سوف يتم تخزينه في مجلد المشروع وهذا يعني أنه سوف يكون غير مرئي إلا إذا فعلت خيار Show All items في Solution Explorer وستجد أن له قطعتان إضافيتان من البيانات توافق القيم المضافة في الملف MyValidation.customdata. وبتخزين هذه المعلومات يمكن لـ Visual studio أن يسمح للمستخدم بإضافة وإزالة التوسعات من صفحة My Extensions في خصائص المشروع بدلا عن إضافة الملف بشكل يدوي وإن كان هناك مؤشر لمجمع قادح وتمت إزالته فسيقوم لـ Visual Studio بتحذير المستخدم من أن My Extension لن يستطيع العمل ويعطيه خيارا لإزالته كما تمنع من تواجد أكثر من نسخة من التوسعة في نفس المشروع.




مترجم بتصرف
}}}
تم الشكر بواسطة:


المواضيع المحتمل أن تكون متشابهة .
الموضوع : الكاتب الردود : المشاهدات : آخر رد
  التعامل مع الصور Images في بيئة الدوت نت باستخدام +GDI - مقدمة RaggiTech 3 5,867 30-07-21, 05:14 PM
آخر رد: kebboud
  اصنع محرر أكواد خاص بك باستخدام الأداة RichTextBox السكر المغرور 13 7,519 19-08-18, 09:27 AM
آخر رد: elgokr
  كيفية قراءة ملف باستخدام IntPtr الخاص بالملف silverlight 3 3,636 24-12-16, 03:13 AM
آخر رد: silverlight
  [درس فيديو] تشغيل اوامر Run من البرنامج & مثال غلق الويندوز بعد وقت محدد باستخدام VB.net أحمد النجار 1 3,858 23-12-15, 04:26 AM
آخر رد: الماجيك مسعد
  مقارنة الكلمات و الأسماء العربية برمجيا silverlight 4 4,018 20-12-15, 08:34 PM
آخر رد: silverlight
  [VB.NET] التشفير باستخدام خوارزمية rsa alking-0999 10 7,560 08-07-15, 04:24 PM
آخر رد: مبرمج بلا حدود
  رسم الباركود برمجيا باستخدام (Code128) RaggiTech 3 9,437 06-10-12, 12:51 AM
آخر رد: RaggiTech
  مقال- تطوير الفورم رسم الفورم باستخدام +GDI وتحريكه Moving و تغيير أبعاده Resize RaggiTech 2 3,905 05-10-12, 07:00 PM
آخر رد: RaggiTech
  كيف تقوم بإضافة إجراءاتك الخاصة إلى مجال الأسماء My- توسيع مجال الأسماء My في VB2005 RaggiTech 0 1,861 05-10-12, 01:49 AM
آخر رد: RaggiTech
  مجال الاسماء My{} RaggiTech 0 2,090 04-10-12, 10:14 AM
آخر رد: RaggiTech

التنقل السريع :


يقوم بقرائة الموضوع: بالاضافة الى ( 1 ) ضيف كريم