MediaQuery — چیای در Flutter که اطلاعاتی درباره محیط رسانه فعلی ارائه میدهد: اندازه صفحه، جهتگیری دستگاه، تراکم پیکسل، حاشیههای سیستمی و اندازه قلم. MediaQueryData — ظرفی برای همه این معیارها که از طریق MediaQuery.of(context) در دسترس است. بر اساس مستندات رسمی Flutter (2026)، MediaQuery اساس طراحی تطبیقی است: از طریق آن تعیین میکنند که چیدمان موبایل یا تبلت نمایش داده شود، حاشیههای safe area محاسبه شود و اندازه عناصر نسبت به صفحه انتخاب شود.
نکات اصلی
MediaQuery — یک ویجت و کلاس Flutter است که دادههایی درباره محیط رسانه برنامه فراهم میکند. MediaQuery کل برنامه را در ویجت ریشه MaterialApp یا CupertinoApp میپیچد و هر ویجت فرزندی میتواند از طریق MediaQuery.of(context) به این دادهها دسترسی پیدا کند.
وقتی Flutter برنامه را اجرا میکند، یک نمونه MediaQueryData ایجاد میکند که شامل همه معیارهای دستگاه فعلی است. این دادهها بهطور خودکار با تغییرات بهروز میشوند: چرخش دستگاه، تغییر اندازه پنجره (روی دسکتاپ)، ظاهر شدن صفحهکلید یا تغییر تنظیمات دسترسیپذیری سیستم. MediaQuery زیردرخت ویجتها را با هر تغییر داده بازسازی میکند و سازگاری واکنشگرایانه رابط را تضمین میکند.
MediaQueryData شامل: size (اندازه صفحه)، devicePixelRatio (تراکم پیکسل)، textScaleFactor (مقیاس قلم از تنظیمات سیستم)، viewInsets (ناحیه پوشیده شده توسط صفحهکلید)، viewPadding (حاشیههای سیستمی)، orientation (جهتگیری) و platformBrightness (تم روشن یا تاریک).
نتیجه: MediaQuery — منبع مرکزی اطلاعات دستگاه در Flutter است. دسترسی به MediaQuery.of(context) اولین قدم در ساخت هر رابط تطبیقی است.
MediaQueryData شامل دهها ویژگی است، اما بیشترین استفاده از آنهایی است که بر ساخت چیدمان تأثیر میگذارند. بیایید موارد کلیدی را بررسی کنیم.
MediaQuery.of(context).size یک شی Size با عرض و ارتفاع صفحه بر حسب پیکسلهای مستقل از دستگاه (dip) برمیگرداند. این مقادیر حاشیههای سیستمی را در نظر نمیگیرند. برای محاسبات چیدمانهای تطبیقی، size معیار اصلی است: بر اساس آن breakpoints برای چیدمان موبایل، تبلت و دسکتاپ تعیین میشوند.
ViewPadding — حاشیههایی که سیستم برای نوار وضعیت، ناچ (بریدگی صفحه)، پنل ناوبری سیستمی و نشانگر خانه (در iOS) رزرو میکند. بدون در نظر گرفتن این حاشیهها، محتوا ممکن است زیر عناصر سیستمی قرار گیرد. MediaQuery.of(context).padding یک EdgeInsets برمیگرداند که باید بهعنوان padding به کانتینر ریشه صفحه اعمال شود.
ViewInsets — ناحیه صفحهای که توسط صفحهکلید نرمافزاری پوشانده شده است. برای فیلدهای ورودی، ردیابی viewInsets.bottom بسیار مهم است تا محتوا بالای صفحهکلید قرار گیرد. Flutter این را بهطور خودکار در scaffold مدیریت میکند، اما برای چیدمانهای سفارشی باید مستقیماً از MediaQuery.of(context).viewInsets استفاده کرد.
Orientation — جهتگیری عمودی (portrait) یا افقی (landscape). با مقایسه عرض و ارتفاع تعیین میشود: اگر عرض کمتر از ارتفاع باشد — portrait، در غیر این صورت — landscape. در کد تولیدی، از جهتگیری برای جابجایی بین چیدمان عمودی و افقی عناصر استفاده میشود.
نتیجه: چهار ویژگی کلیدی — size، viewPadding، viewInsets و orientation — 90٪ وظایف طراحی تطبیقی را پوشش میدهند. سایر ویژگیها (textScaleFactor، platformBrightness، devicePixelRatio) برای سناریوهای خاص استفاده میشوند.
MediaQuery — اساس طراحی تطبیقی در Flutter است. از طریق آن breakpoints تعیین میشود، layout بسته به اندازه صفحه تغییر میکند و حاشیهها برای دستگاههای مختلف تنظیم میشوند.
سناریوی معمول: برنامه موبایل باید فهرست محصولات را نمایش دهد. روی تلفن (عرض < 600dp) — یک ستون. روی تبلت (عرض 600–900dp) — دو ستون. روی دسکتاپ (عرض > 900dp) — سه ستون. MediaQuery.of(context).size.width امکان انتخاب پویای تعداد ستونها را بدون صفحه جداگانه برای هر فرم فاکتور فراهم میکند.
سناریوی دوم: در نظر گرفتن system gesture insets در دستگاههای مدرن. در iPhone با Dynamic Island یا Android با gesture navigation، حاشیههای سیستمی بخشی از صفحه را اشغال میکنند. MediaQuery.of(context).padding مقادیر صحیحی را برای هر نوع دستگاه برمیگرداند و Scaffold آنها را بهطور خودکار از طریق body اعمال میکند. برای ویجتهای سفارشی باید padding را بهصراحت از MediaQuery منتقل کرد.
سناریوی سوم: تطبیق با تنظیمات دسترسیپذیری سیستم. MediaQuery.of(context).textScaleFactor نشان میدهد که کاربر چقدر قلم را در تنظیمات بزرگ کرده است. در textScaleFactor > 1.3 چیدمان ممکن است خراب شود — متنهای طولانی از مرز کارتها خارج میشوند. چیدمانهای تطبیقی باید این را در نظر بگیرند و در صورت لزوم به چیدمان سادهتری تغییر وضعیت دهند.
نتیجه: MediaQuery — نه فقط منبع معیارها، بلکه ابزاری برای ساخت رابطهای واقعاً تطبیقی است. از آن برای breakpoints، safe area و در نظر گرفتن دسترسیپذیری استفاده کنید.
نمونه 1 دریافت اندازه صفحه و استفاده از breakpoints برای انتخاب تعداد ستونها را نشان میدهد.
int getColumnCount(BuildContext context) {
final width = MediaQuery.of(context).size.width;
if (width > 900) return 3;
if (width > 600) return 2;
return 1;
}
نمونه بالا تابع انتخاب تعداد ستونها بر اساس عرض صفحه را نشان میدهد. breakpoints 600 و 900 با استانداردهای رایج Material Design برای تلفنها، تبلتها و دسکتاپ مطابقت دارند.
نمونه 2 — استفاده از MediaQuery با viewPadding برای قرارگیری صحیح محتوا با در نظر گرفتن حاشیههای سیستمی.
Widget build(BuildContext context) {
final padding = MediaQuery.of(context).padding;
return Padding(
padding: EdgeInsets.only(
top: padding.top,
left: padding.left,
right: padding.right,
),
child: const MyContent(),
);
}
در این نمونه، padding محتوا را با استفاده از حاشیههای سیستمی در Padding قرار میدهد. top نوار وضعیت و ناچ را در نظر میگیرد، left/right — مناطق امن. bottom گنجانده نشده است زیرا Scaffold معمولاً خود ناوبری پایینی را مدیریت میکند.
نمونه 3 — تعیین جهتگیری و تغییر چیدمان عناصر.
Widget build(BuildContext context) {
final isPortrait = MediaQuery.of(context).orientation == Orientation.portrait;
return isPortrait
? const Column(
children: [HeaderBanner(), ContentList()],
)
: const Row(
children: [HeaderBanner(), ContentList()],
);
}
در حالت عمودی عناصر بهصورت عمودی (Column) و در حالت افقی بهصورت افقی (Row) چیده میشوند. این رویکرد بهترین استفاده از فضا را هنگام چرخش دستگاه فراهم میکند.
نتیجه: MediaQuery — ابزار اصلی برای ساخت چیدمانهای تطبیقی است. هنگام توسعه رابطهای Flutter همیشه حاشیههای سیستمی، breakpoints و جهتگیری را در نظر بگیرید.
خطای ۱: فراخوانی MediaQuery.of(context) خارج از زمینهای که MediaQuery تنظیم شده است. اگر ویجت بالاتر از MediaQuery در درخت باشد، فراخوانی منجر به خطای زمان اجرا میشود. راهحل: همیشه MediaQuery.of(context) را داخل ویجتهایی فراخوانی کنید که در MaterialApp یا CupertinoApp پیچیده شدهاند، جایی که MediaQuery بهعنوان ویجت ریشه تنظیم شده است.
خطای ۲: فراموش کردن safe area. توسعهدهندگان از MediaQuery.size برای قرارگیری عناصر بدون در نظر گرفتن حاشیههای سیستمی استفاده میکنند. در دستگاههای دارای ناچ یا gesture navigation، محتوا زیر نوار وضعیت قرار میگیرد. راهحل: MediaQuery.of(context).padding را از مختصات موقعیتیابی کم کنید.
خطای ۳: وابستگی سخت به اندازهها. استفاده از MediaQuery.of(context).size.width برای تعیین اندازههای دقیق عناصر (width: size.width * 0.3) فقط روی دستگاههای یک فرم فاکتور کار میکند. روی دسکتاپ یا تبلت چیدمان غیرطبیعی به نظر میرسد. راهحل: از breakpoints به همراه Expanded و Flexible برای چیدمان انعطافپذیر استفاده کنید، نه درصدهای سخت.
خطای ۴: نادیده گرفتن textScaleFactor. وقتی کاربر قلم سیستم را افزایش میدهد، رابط ممکن است خراب شود — متنها از مرز کانتینرها خارج میشوند. راهحل: MediaQuery.of(context).textScaleFactor را بررسی کنید و در مقادیر بالای ۱.۳ چیدمان را به نسخه سادهتری با قابلیت پیمایش تغییر دهید.
نتیجه: MediaQuery — ابزاری قدرتمند اما ظریف است. حاشیههای سیستمی، جهتگیری و تنظیمات دسترسیپذیری را در نظر بگیرید تا رابط روی همه دستگاهها بهدرستی نمایش داده شود.
سؤالات متداول
MediaQuery.size — اندازه کلی صفحه یا پنجره برنامه بر حسب پیکسل منطقی. MediaQuery.viewInsets — ناحیه پوشیده شده توسط صفحهکلید سیستم. برای محاسبه فضای موجود بدون صفحهکلید: size.height - viewInsets.bottom.
LayoutBuilder اندازههای کانتینر والد را میدهد، نه کل صفحه. وقتی اندازههای ویجت به فضای موجود درون یک والد خاص بستگی دارد از LayoutBuilder استفاده کنید، و وقتی معیارهای سراسری صفحه نیاز است از MediaQuery.
بهطور خودکار. هنگام چرخش دستگاه، Flutter MediaQueryData را بهروز میکند و زیردرخت را بازسازی میکند. ویژگی orientation تغییر میکند و builder همه ویجتهای مشترک با دادههای جدید فراخوانی میشود.
بله. با پیچیدن بخشی از ویجتها در MediaQuery با دادههای بازنویسیشده از طریق MediaQuery.removePadding، MediaQuery.removeViewInsets یا MediaQuery با Data دیگر. این برای جاسازی در iframe یا حالتهای پیشنمایش استفاده میشود.
برای تستها، Flutter setScreenSize و پوشش MediaQuery را در محیط تست فراهم میکند. برای ویجت تستها، کامپوننت مورد آزمایش را در MaterialApp یا MediaQuery با دادههای تست بپیچید تا اندازههای صفحه را کنترل کنید.
خلاصه
ما یک اپلیکیشن موبایل به صورت کلید در دست توسعه خواهیم داد
IT Sectr از سال 2017 برنامههای iOS و Android را برای استارتاپها و کسبوکارها ایجاد میکند. ما به شما مشاوره میدهیم و بهترین راهحل را پیشنهاد خواهیم کرد.
همچنین بخوانید