مطالب
مروری بر کتابخانه ReactJS - قسمت سوم - کامپوننت‌های React

همانطور که در قسمت اول گفته شد، اجزای رابط کاربری (تگ‌های HTML) در کتابخانه‌ی React به عنوان کامپوننت‌ها (مؤلفه‌های جزء)  شناخته میشوند. React تگ‌ها را به عنوان اجزایی مستقل و با وضعیتی مشخص در حافظه میشناسد. دلایل ارزشمند بودن این روش در ادامه بررسی میشود.


خوانایی بهتر (Readability) 

React میتواند تگ‌های یگانه یا مخلوطی از تگ‌های به هم مرتبط را در پس زمینه ساخته و با یک نام واحد (کامپوننت) به HTML DOM ارسال کند. یعنی اگر جایی یک کامپوننت صدا زده شود، تگ یا تگ‌های مرتبط به آن کامپوننت را به عنوان خروجی خواهیم داشت. همانطور که میشود تگ‌های مختلف را به صورت تو در تو استفاده کرد، کامپوننت‌ها را هم میشود به همین روش فراخوانی کرد. در مثال زیر روش صدا زدن چند کامپوننت و تگ‌هایی را که ارائه میدهد، داریم. 

     // Components in a JavaScript file.
    <clickableImage href="http://google.com" src="google.png" />
    <LinksContainer>
        <LinksList>
            <clickableImage href="http://yahoo.com" src="yahoo.png" />
        </LinksList>
    </LinksContainer>

    <!--Output in HTML DOM-->
    <a href="http://google.com">
        <img src="google.png" />
    </a>
    <div>
        <div>
            <ul>
                <li>
                    <a href="http://google.com">
                        <img src="google.png" />
                    </a>
                </li>
            </ul>
        </div>
    </div>

در قسمت کامپوننت‌ها می‌بینیم که چطور کامپوننت‌ها یکبار به صورت تکی و یک بار به صورت تو در تو اجرا میشوند. خروجی در قسمت Output واضح است که با نام کامپوننت‌ها هماهنگی دارد. با این مثال چند مورد مشخص میشود.

  1. به هر کامپوننت قبلا گفته شده چه تگ‌هایی را باید ایجاد کند. در نتیجه با هر بار فراخوانی در هر مکان، تگ یا تگ‌هایی که به آن معرفی شده را می‌سازد. 
  2. هر کامپوننت میتواند مقادیری را به عنوان ورودی دریافت کند و آنها را به تگ‌ها در خروجی اعمال کند. در مثال بالا href و src در فراخوانی‌های مختلف، مقادیر متفاوتی را به خروجی میفرستند.
  3. با انتخاب نام مناسب برای کامپوننت‌ها، بدون آنکه بدانیم چطور ساخته شده‌اند میتوانیم حدس بزنیم چه تگ‌هایی را خواهند ساخت و این دلیلی است که خوانایی برنامه افزایش میابد.
  4. دلیل دیگر که باعث خوانایی برنامه میشود، این است که هر یک از این کامپوننت‌ها میتوانند تگ‌های زیادی را یک جا بسازند که این کار منجر به کم شدن مقدار کد برنامه میشود. برنامه هر چه کم کدتر، با خوانایی بیشتر! 


قابلیت استفاده مجدد 

در ادامه وقتی با روش ساخت کامپوننت‌ها آشنا شدیم، متوجه میشویم که کامپوننت‌ها چیزی بیشتر از یک تابع نیستند. وقتی نام یک کامپوننت را فراخوانی کنیم در واقع یک تابع را اجرا میکنیم، به آن پارامتر ورودی را میدهیم و از آن خروجی میگیریم. میدانیم که توابع را میشود یکبار ساخت و چندبار استفاده کرد. بخصوص اگر این توابع به متغیرهای سراسری و سایر توابع وابسته نباشند و به صورت مستقل عمل کنند، میشود آنها را به برنامه‌های دیگر هم انتقال داد.  


نحوه ساخت یک کامپوننت در React 

در React به سه روش میشود کامپوننت‌ها را ایجاد کرد. در روش اول توضیحات زیاد خواهند بود، اما در دو روش بعدی فقط نکات کلیدی گفته خواهد شد.    


Stateless function components 

میخواهیم یک منو از نوشیدنی‌ها را با استفاده از کامپوننت‌ها نمایش دهیم. در یک فایل جاوااسکریپت کدهای زیر را وارد کنید. در ادامه هر بخش توضیح داده خواهد شد. 

var hotDrinks = [
    { item: "Tea", price: "7000" },
    { item: "Espresso", price: "10000" },
    { item: "Hot Chocolate", price: "12000" }
];
var MenuItem = function (props) {
    return (
        <li className="list-group-item">
            <span className="badge">{props.price}</span>
            <p>{props.item}</p>
        </li>
    )
};
var Menu = function (props) {
    return (
        <div className="row">
            <div className="col-md-4">
                <ul className="list-group">
                    {props.data.map(item => <MenuItem {...item} />)}
                </ul>
            </div>
        </div>
    )
};

ReactDOM.render(
    <Menu data={hotDrinks} />,
    document.getElementById("reactTestContainer")
)

  1. فرض میکنیم که لیست نوشیدنی‌ها و قیمت آنها را به فرمتی که می‌بینید از سرور دریافت کرده‌ایم. (hotDrinks)
  2. شیء MenuItem یک تابع بدون نام را اجرا میکند. از دیدگاه React این تابع یک کامپوننت است. کامپوننت با هر بار فراخوانی مقادیری را برای یک نوشیدنی و قیمت آن، دریافت میکند.کامپوننت به عنوان خروجی یک تگ <li>، پر شده با مقادیر ورودی را بازگشت میدهد. 
  3. شیء Menu یک تابع بدون نام را اجرا میکند. از دید React این تابع یک کامپوننت است. کامپوننت با هر بار فراخوانی، مجموعه‌ای از نوشیدنی‌ها و قیمت آنها را دریافت میکند. متد map به کمک یک Arrow Function آرایه‌ای از کامپوننت MenuItem ایجاد میکند که به ازای هر عضو ایجاد شده، یکبار MenuItem اجرا میشود. هر عضو (item) دارای یک نام نوشیدنی و قیمت آن است. سه نقطه در {…item} برای پر کردن جای خالی نیست! این عبارت یعنی اینکه مقادیر نام و قیمت را به صورت جداگانه (یعنی دو پارامتر مجزا) به کامپوننت MenuItem ارسال میکند. کامپوننت، به عنوان خروجی یک تگ <ul>، پر شده با آرایه‌ای از کامپوننت MenuItem را بازگشت میدهد.
  4. متد render از شیء ReactDOM وظیفه ساخت تگ‌های JSX واقع در کامپوننت‌ها را در HTML DOM به عهده دارد. پارامتر اول render، کامپوننت Menu است با ورودی داده‌های گرفته شده از سرور. همانطور که شرح داده شد، کامپوننت Menu با فراخوانی و به کمک داده‌های ورودی، کامپوننت MenuItem را پیاده‌سازی خواهد کرد. پارامتر دوم render، محلی است که تگ‌ها باید در آن ساخته شوند. مثلا یک تگ <div>
  5. در هر کدام از کامپوننت‌ها و در قسمت ReactDOM.render میشود از کامپوننت‌های دیگر به صورت تو در تو استفاده کرد. 


React.createClass 

React یک API درونی برای ایجاد کامپوننت‌ها، به نام createClass دارد. این تابع باید یک شیء پیکربندی درون خود داشته باشد که در آن و  بین دو آکولاد {} خواص و متدها تعریف می‌شوند. تابع createClass برای کار حداقل باید یک متد به نام render داشته باشد که در آن تگ‌های JSX را قرار میدهیم. کامپوننت MenuItem را که به صورت Stateless ساختیم، دوباره با createClass ایجاد میکنیم. 

var MenuItem = React.createClass({
    render: function () {
        return (
            <li className="list-group-item">
                <span className="badge">{this.props.price}</span>
                <p>{this.props.item}</p>
            </li>
        )
    }
});

برای خواندن مقادیر ورودی در این روش باید از this استفاده کنیم. بر اساس قواعد شیء گراییِ، MenuItem و Menu کلاس هستند و هر بار در ReactDOM.render کامپوننت Menu را به HTML DOM ارسال میکنیم. یک نمونه از این کلاس ساخته میشود و کلاس Menu، نمونه‌هایی از کلاس MenuItem را میسازد. this به نمونه‌ی ساخته شده از یک کلاس اشاره دارد. 


React.Component 

در روش آخر با استفاده از extend، از کلاس React.Component ارث بری میکنیم و کامپوننت را می‌سازیم. مفاهیم کلاس و ارث بری در جاوااسکریپ را میشود از اینجا یاد گرفت. مجددا MenuItem را با  این روش ایجاد میکنیم. 

class MenuItem extends React.Component {
    render() {
        return (
            <li className="list-group-item">
                <span className="badge">{this.props.price}</span>
                <p>{this.props.item}</p>
            </li>
        );
    }
}

همانطور که می‌بینید بین دو روش React.Component و React.createClass تفاوتی جز در syntax آنها نیست. در اینجا از سایر امکانات کلاس در جاوااسکریپت مثل سازنده کلاس میشود استفاده کرد. کامپوننت‌ها در React میتوانند کاری بیشتر از ساخت تگ‌ها در HTML DOM را انجام دهند. در قسمت بعد به قابلیت مهم حفظ و دنبال کردن تغییرات در وضعیت کامپوننت‌ها می‌پردازیم.

اشتراک‌ها
کتابخانه uilang
A minimal, UI-focused programming language for web designers. With uilang, you write your code just like plain English, straight into your HTML using a <code> element. uilang's logic relies on manipulating classes on HTML elements and using these classes in CSS to show, hide, animate and transform elements when a click occurs. This simple logic lets designers create most of the typical user interface behaviours: tabs, popovers, overlays, sliding menus, etc.  Demo
کتابخانه uilang
اشتراک‌ها
ایجاد Responsive jQuery Pop-Up Gallery
in this tutorial you will lean how to create a an awesome popup gallery. Each gallery will have a small preview animation. This tutorial will provide you with five different popup galleries. All the main animations are done using CSS transitions. I would of liked to build the entire thing using CSS only but unfortunately this was a pretty complex gallery so i had to use some JavaScript.  Demo
ایجاد Responsive jQuery Pop-Up Gallery
مطالب
استفاده از LINQ جهت تهیه کدهایی کوتاه‌تر و خواناتر

با کمک امکانات ارائه شده توسط LINQ ، می‌توان بسیاری از اعمال برنامه نویسی را در حجمی کمتر، خواناتر و در نتیجه با قابلیت نگهداری بهتر، انجام داد که تعدادی از آن‌ها را در ادامه مرور خواهیم کرد.

الف) تهیه یک یک رشته، حاوی عناصر یک آرایه، جدا شده با کاما.

using System.Linq;

public class CLinq
{
public static string GetCommaSeparatedListNormal(string[] data)
{
string items = string.Empty;

foreach (var item in data)
{
items += item + ", ";
}

return items.Remove(items.Length - 2, 1).Trim();
}

public static string GetCommaSeparatedList(string[] data)
{
return data.Aggregate((s1, s2) => s1 + ", " + s2);
}
}
همانطور که ملاحظه می‌کنید در روش دوم با استفاده از LINQ Aggregate extension method ، کد جمع و جورتر و خواناتری نسبت به روش اول حاصل شده است.

ب) پیدا کردن تعداد عناصر یک آرایه حاوی مقداری مشخص
برای مثال آرایه زیر را در نظر بگیرید:

var names = new[] { "name1", "name2", "name3", "name4", "name5", "name6", "name7" };
قصد داریم تعداد عناصر حاوی name را مشخص سازیم.
در تابع GetCountNormal زیر، این کار به شکلی متداول انجام شده و در GetCount از LINQ Count extension method کمک گرفته شده است.

using System.Linq;

public class CLinq
{
public static int GetCountNormal()
{
var names = new[] { "name1", "name2", "name3", "name4", "name5", "name6", "name7" };
var count = 0;
foreach (var name in names)
{
if (name.Contains("name"))
count += 1;
}
return count;
}

public static int GetCount()
{
var names = new[] { "name1", "name2", "name3", "name4", "name5", "name6", "name7" };
return names.Count(name => name.Contains("name"));
}
}
به نظر شما کدام روش خواناتر بوده و نگهداری و یا تغییر آن در آینده ساده‌تر می‌باشد؟

ج) دریافت لیستی از عناصر شروع شده با یک عبارت
در اینجا نیز دو روش متداول و استفاده از LINQ بررسی شده است.

using System.Linq;
using System.Collections.Generic;

public class CLinq
{
public static List<string> GetListNormal()
{
List<string> sampleList = new List<string>() { "A1", "A2", "P1", "P10", "B1", "B@", "J30", "P12" };
List<string> result = new List<string>();
foreach (var item in sampleList)
{
if (item.StartsWith("P"))
result.Add(item);
}
return result;
}

public static List<string> GetList()
{
List<string> sampleList = new List<string>() { "A1", "A2", "P1", "P10", "B1", "B@", "J30", "P12" };
return sampleList.Where(x => x.StartsWith("P")).ToList();
}
}

و در حالت کلی، اکثر حلقه‌های foreach متداول را می‌توان با نمونه‌های خواناتر کوئری‌های LINQ معادل، جایگزین کرد.

Vote on iDevCenter
اشتراک‌ها
فرآیند رندر شدن در Angular2
So how exactly is Angular2 built such that it allows for custom renderers to be created? The first thing to understand is that the internal bits of Angular2 are split into two areas: the worker (core) area and the UI area. The worker (core) area is responsible for building out the components, directives, filters, services and bootstrap code; The UI area is responible for rendering out the application in the DOM.
فرآیند رندر شدن در Angular2
اشتراک‌ها
عصر Portable .Net

The new .NET framework is modern, lean, modular and open source. No longer is .NET a system-wide installation – it is merely a folder. Instead of a huge underlying framework, you only pick and choose the pieces of the .NET framework that you need in your apps. And more importantly, you can package the required components of the .NET framework right alongside your app. We’re entering an age of app-runtime silos and ultimate portability. 

عصر Portable .Net
نظرات مطالب
پیاده سازی Unobtrusive Ajax در ASP.NET Core 1.0
بله اون مطلب رو مطالعه کردم
محتویات فایل package.json به این صورت هست
{
  "name": "dntcommon.web.core.testwebapp",
  "version": "1.0.0",
  "description": "",
  "scripts": {},
  "author": "",
  "license": "ISC",
  "dependencies": {
    "bootstrap": "^3.3.7",
    "bootstrap-rtl": "^3.3.4",
    "components-font-awesome": "5.0.6",
    "jquery": "^3.3.1",
    "jquery-ajax-unobtrusive": "^3.2.4",
    "jquery-validation": "^1.17.0",
    "jquery-validation-unobtrusive": "^3.2.8",
    "samim-font": "1.0.2"
  }
}

بعد از اجرای npm install  پاسخ زیر رو می‌دهد
C:\Projects\ZagrosCore\src\Zagros>npm install
npm WARN dntcommon.web.core.testwebapp@1.0.0 No description
npm WARN dntcommon.web.core.testwebapp@1.0.0 No repository field.

up to date in 0.181s
احتمالا ساختار فایل package.json اشتباه نیست؟