Estoy enfrentando dificultades para que responda de acuerdo con varios tamaños de pantalla. ¿Cómo hacerlo receptivo?
@override
Widget build(BuildContext context) {
return new Container(
decoration: new BoxDecoration(color: Colors.white),
child: new Stack(
children: [
new Padding(
padding: const EdgeInsets.only(bottom: 350.0),
child: new GradientAppBar(" "),
),
new Positioned(
bottom: 150.0,
height: 260.0,
left: 10.0,
right: 10.0,
child: new Padding(
padding: new EdgeInsets.all(10.0),
child: new Card(
child: new Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
const ListTile(
title: const Text(
'LOGIN',
textAlign: TextAlign.center,
style: const TextStyle(
fontSize: 16.50,
fontFamily: "Helvetica",
fontWeight: FontWeight.bold,
color: Colors.black87,
letterSpacing: 1.00,
),
),
),
new ListTile(
leading: const Icon(Icons.person),
title: new TextField(
controller: _user1,
decoration: new InputDecoration(
labelText: ' Enter a username'),
),
),
new ListTile(
leading: const Icon(Icons.person_pin),
title: new TextField(
controller: _pass1,
decoration: new InputDecoration(
labelText: ' Enter a password'),
obscureText: true,
),
),
],
),
),
),
),
new Positioned(
bottom: 70.0,
left: 15.0,
right: 05.0,
child: new ButtonTheme.bar(
// make buttons use the appropriate styles for cards
child: new ButtonBar(
children: <Widget>[
new FlatButton(
padding: new EdgeInsets.only(right: 13.0),
child: new Text(
'REGISTER HERE',
style: new TextStyle(
color: Colors.black87,
fontFamily: "Helvetica",
fontSize: 15.00,
fontWeight: FontWeight.bold),
),
onPressed: () {
Navigator.of(context).pushNamed('/facebook');
},
),
new FlatButton(
padding: new EdgeInsets.only(right: 22.0),
child: new Text(
'FORGOT PASSWORD?',
style: new TextStyle(
color: Colors.black87,
fontFamily: "Helvetica",
fontSize: 15.00,
fontWeight: FontWeight.bold),
),
onPressed: () {
Navigator.of(context).pushNamed('/Forgot');
},
),
],
),
),
),
new Positioned(
bottom: 73.0,
height: 180.0,
left: 20.0,
right: 52.0,
child: new Padding(
padding: new EdgeInsets.all(0.00),
child: new ButtonTheme(
minWidth: 10.0,
height: 20.0,
padding: new EdgeInsets.only(right: 37.0),
child: new ButtonBar(children: <Widget>[
new CupertinoButton(
borderRadius:
const BorderRadius.all(const Radius.circular(36.0)),
padding: new EdgeInsets.only(left: 70.0),
color: const Color(0xFF426DB7),
child: new Text(
" LOGIN ",
style: new TextStyle(
color: Colors.white,
fontSize: 12.50,
fontFamily: "Handwriting",
fontWeight: FontWeight.w500,
letterSpacing: 0.00),
),
onPressed: () {})
]),
),
),
),
],
),
);
}
}
queryData
?Esta clase ayudará y luego inicializará la clase con el método init.
import 'package:flutter/widgets.dart'; class SizeConfig { static MediaQueryData _mediaQueryData; static double screenWidth; static double screenHeight; static double blockSizeHorizontal; static double blockSizeVertical; static double _safeAreaHorizontal; static double _safeAreaVertical; static double safeBlockHorizontal; static double safeBlockVertical; void init(BuildContext context){ _mediaQueryData = MediaQuery.of(context); screenWidth = _mediaQueryData.size.width; screenHeight = _mediaQueryData.size.height; blockSizeHorizontal = screenWidth/100; blockSizeVertical = screenHeight/100; _safeAreaHorizontal = _mediaQueryData.padding.left + _mediaQueryData.padding.right; _safeAreaVertical = _mediaQueryData.padding.top + _mediaQueryData.padding.bottom; safeBlockHorizontal = (screenWidth - _safeAreaHorizontal)/100; safeBlockVertical = (screenHeight - _safeAreaVertical)/100; } }
luego en la dimensión de tus widgets haz esto
Widget build(BuildContext context) { SizeConfig().init(context); return Container( height: SizeConfig.safeBlockVertical * 10, //10 for example width: SizeConfig.safeBlockHorizontal * 10, //10 for example );}
Todos los créditos al autor de esta publicación: https://medium.com/flutter-community/flutter-effectively-scale-ui-according-to-different-screen-sizes-2cb7c115ea0a
fuente
Lo que hago es tomar el ancho y la altura de la pantalla y calcular una cuadrícula de 100 * 100 para colocar y escalar cosas y guardarlas como variables estáticas que se pueden reutilizar. Funciona bastante bien en la mayoría de los casos. Me gusta esto:
AppConfig.width = MediaQuery.of(context).size.width; AppConfig.height = MediaQuery.of(context).size.height; AppConfig.blockSize = AppConfig.width / 100; AppConfig.blockSizeVertical = AppConfig.height / 100;
Luego escalo todo de acuerdo con estos valores, así:
double elementWidth = AppConfig.blockSize * 10.0; // 10% of the screen width
o
double fontSize = AppConfig.blockSize * 1.2;
A veces, el área segura (muesca, etc.) mata un diseño, por lo que también puede considerar esto:
AppConfig.safeAreaHorizontal = MediaQuery.of(context).padding.left + MediaQuery.of(context).padding.right; double screenWidthWithoutSafeArea = AppConfig.width - AppConfig.safeAreaHorizontal;
Esto funcionó muy bien en algunos proyectos recientes.
fuente
Consultar
MediaQuery
claseEntonces puedes hacer lo siguiente:
new Container( height: MediaQuery.of(context).size.height/2, .. )
fuente
Puede tomar un porcentaje del ancho o alto como entrada para el tamaño de escala.
fontSize: MediaQuery.of(_ctxt).size.height * 0.065
Donde el multiplicador al final tiene un valor que hace que el texto se vea bien para el emulador activo.
A continuación se muestra cómo lo configuré para que todas las dimensiones escaladas estén centralizadas en un solo lugar. De esta manera, puede ajustarlos fácilmente y volver a ejecutarlos rápidamente con Hot Reload sin tener que buscar las
Media.of()
llamadas en todo el código.class AppScale { BuildContext _ctxt; AppScale(this._ctxt); double get labelDim => scaledWidth(.04); double get popupMenuButton => scaledHeight(.065); double scaledWidth(double widthScale) { return MediaQuery.of(_ctxt).size.width * widthScale; } double scaledHeight(double heightScale) { return MediaQuery.of(_ctxt).size.height * heightScale; } }
AppScale _scale = AppScale(context); // ... Widget label1 = Text( "Some Label", style: TextStyle(fontSize: _scale.labelDim), );
Gracias a las respuestas en esta publicación.
fuente
He estado criticando un poco las soluciones de otras personas (@datayeah y Vithani Ravi) aquí, así que pensé en compartir mis propios intentos para resolver este problema de escala de densidad de pantalla variable o callarme. Así que abordo este problema desde una base sólida / fija: baso toda mi escala en una proporción fija (inmutable) de 2: 1 (alto: ancho). Tengo una clase de ayuda "McGyver" que hace todo el trabajo pesado (y el código útil) en mi aplicación. Esta clase "McGyver" contiene solo métodos estáticos y miembros de clase constantes estáticos.
MÉTODO DE ESCALA DE RELACIÓN: Escalo tanto el ancho como la altura de forma independiente en función de la relación de aspecto 2: 1. Tomo valores de entrada de ancho y alto y divido cada uno por las constantes de ancho y alto y finalmente calculo un factor de ajuste por el cual escalar los respectivos valores de entrada de ancho y alto. El código real tiene el siguiente aspecto:
import 'dart:math'; import 'package:flutter/material.dart'; class McGyver { static const double _fixedWidth = 410; // Set to an Aspect Ratio of 2:1 (height:width) static const double _fixedHeight = 820; // Set to an Aspect Ratio of 2:1 (height:width) // Useful rounding method (@andyw solution -> /programming/28419255/how-do-you-round-a-double-in-dart-to-a-given-degree-of-precision-after-the-decim/53500405#53500405) static double roundToDecimals(double val, int decimalPlaces){ double mod = pow(10.0, decimalPlaces); return ((val * mod).round().toDouble() / mod); } // The 'Ratio-Scaled' Widget method (takes any generic widget and returns a "Ratio-Scaled Widget" - "rsWidget") static Widget rsWidget(BuildContext ctx, Widget inWidget, double percWidth, double percHeight) { // ---------------------------------------------------------------------------------------------- // // INFO: Ratio-Scaled "SizedBox" Widget - Scaling based on device's height & width at 2:1 ratio. // // ---------------------------------------------------------------------------------------------- // final int _decPlaces = 5; final double _fixedWidth = McGyver._fixedWidth; final double _fixedHeight = McGyver._fixedHeight; Size _scrnSize = MediaQuery.of(ctx).size; // Extracts Device Screen Parameters. double _scrnWidth = _scrnSize.width.floorToDouble(); // Extracts Device Screen maximum width. double _scrnHeight = _scrnSize.height.floorToDouble(); // Extracts Device Screen maximum height. double _rsWidth = 0; if (_scrnWidth == _fixedWidth) { // If input width matches fixedWidth then do normal scaling. _rsWidth = McGyver.roundToDecimals((_scrnWidth * (percWidth / 100)), _decPlaces); } else { // If input width !match fixedWidth then do adjustment factor scaling. double _scaleRatioWidth = McGyver.roundToDecimals((_scrnWidth / _fixedWidth), _decPlaces); double _scalerWidth = ((percWidth + log(percWidth + 1)) * pow(1, _scaleRatioWidth)) / 100; _rsWidth = McGyver.roundToDecimals((_scrnWidth * _scalerWidth), _decPlaces); } double _rsHeight = 0; if (_scrnHeight == _fixedHeight) { // If input height matches fixedHeight then do normal scaling. _rsHeight = McGyver.roundToDecimals((_scrnHeight * (percHeight / 100)), _decPlaces); } else { // If input height !match fixedHeight then do adjustment factor scaling. double _scaleRatioHeight = McGyver.roundToDecimals((_scrnHeight / _fixedHeight), _decPlaces); double _scalerHeight = ((percHeight + log(percHeight + 1)) * pow(1, _scaleRatioHeight)) / 100; _rsHeight = McGyver.roundToDecimals((_scrnHeight * _scalerHeight), _decPlaces); } // Finally, hand over Ratio-Scaled "SizedBox" widget to method call. return SizedBox( width: _rsWidth, height: _rsHeight, child: inWidget, ); } }
... ... ...
Luego, escalaría individualmente sus widgets (que para mi enfermedad perfeccionista es TODA mi IU) con una simple llamada estática al método "rsWidget ()" de la siguiente manera:
// Step 1: Define your widget however you like (this widget will be supplied as the "inWidget" arg to the "rsWidget" method in Step 2)... Widget _btnLogin = RaisedButton(color: Colors.blue, elevation: 9.0, shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(McGyver.rsDouble(context, ScaleType.width, 2.5))), child: McGyver.rsText(context, "LOGIN", percFontSize: EzdFonts.button2_5, textColor: Colors.white, fWeight: FontWeight.bold), onPressed: () { _onTapBtnLogin(_tecUsrId.text, _tecUsrPass.text); }, ); // Step 2: Scale your widget by calling the static "rsWidget" method... McGyver.rsWidget(context, _btnLogin, 34.5, 10.0) // ...and Bob's your uncle!!
¡Lo bueno es que el método "rsWidget ()" devuelve un widget! Por lo tanto, puede asignar el widget escalado a otra variable
_rsBtnLogin
para usar en todo el lugar, o simplemente puede usar laMcGyver.rsWidget()
llamada al método completo en el lugar dentro de subuild()
método (exactamente cómo necesita colocarlo en el árbol de widgets) y funcionará perfectamente como debería.Para aquellos programadores más astutos: habrán notado que utilicé dos métodos adicionales de escala de proporción
McGyver.rsText()
yMcGyver.rsDouble()
(no definido en el código anterior) en miRaisedButton()
- así que básicamente me vuelvo loco con estas cosas de escala ... porque exijo que mis aplicaciones sean ¡absolutamente perfecto en píxeles a cualquier escala o densidad de pantalla! Escalo en proporción mis entradas, dobles, relleno, texto (todo lo que requiere coherencia de la interfaz de usuario en todos los dispositivos). Escalo mis textos solo en función del ancho, pero especifico qué eje usar para todas las demás escalas (como se hizo con laScaleType.width
enumeración utilizada para laMcGyver.rsDouble()
llamada en el ejemplo de código anterior).Sé que esto es una locura, y hay mucho trabajo por hacer en el hilo principal, pero espero que alguien vea mi intento aquí y me ayude a encontrar una solución mejor (más liviana) para mi escala de densidad de pantalla 1: 1 pesadillas.
fuente
Después de mucha investigación y pruebas, he desarrollado una solución para una aplicación que actualmente estoy convirtiendo de Android / iOS a Flutter.
Con Android e iOS utilicé un 'Factor de escala' aplicado a los tamaños de fuente base, representando tamaños de texto que eran relativos al tamaño de pantalla.
Este artículo fue muy útil: https://medium.com/flutter-community/flutter-effectively-scale-ui-according-to-different-screen-sizes-2cb7c115ea0a
Creé un StatelessWidget para obtener los tamaños de fuente de los estilos tipográficos de Material Design. Obtener las dimensiones del dispositivo mediante MediaQuery, calcular un factor de escala y luego restablecer los tamaños de texto de Material Design. El widget se puede utilizar para definir un tema de diseño de materiales personalizado.
Emuladores utilizados:
Con tamaños de fuente estándar
Con tamaños de fuente escalados
set_app_theme.dart (widget SetAppTheme)
import 'package:flutter/material.dart'; import 'dart:math'; class SetAppTheme extends StatelessWidget { final Widget child; SetAppTheme({this.child}); @override Widget build(BuildContext context) { final _divisor = 400.0; final MediaQueryData _mediaQueryData = MediaQuery.of(context); final _screenWidth = _mediaQueryData.size.width; final _factorHorizontal = _screenWidth / _divisor; final _screenHeight = _mediaQueryData.size.height; final _factorVertical = _screenHeight / _divisor; final _textScalingFactor = min(_factorVertical, _factorHorizontal); final _safeAreaHorizontal = _mediaQueryData.padding.left + _mediaQueryData.padding.right; final _safeFactorHorizontal = (_screenWidth - _safeAreaHorizontal) / _divisor; final _safeAreaVertical = _mediaQueryData.padding.top + _mediaQueryData.padding.bottom; final _safeFactorVertical = (_screenHeight - _safeAreaVertical) / _divisor; final _safeAreaTextScalingFactor = min(_safeFactorHorizontal, _safeFactorHorizontal); print('Screen Scaling Values:' + '_screenWidth: $_screenWidth'); print('Screen Scaling Values:' + '_factorHorizontal: $_factorHorizontal '); print('Screen Scaling Values:' + '_screenHeight: $_screenHeight'); print('Screen Scaling Values:' + '_factorVertical: $_factorVertical '); print('_textScalingFactor: $_textScalingFactor '); print('Screen Scaling Values:' + '_safeAreaHorizontal: $_safeAreaHorizontal '); print('Screen Scaling Values:' + '_safeFactorHorizontal: $_safeFactorHorizontal '); print('Screen Scaling Values:' + '_safeAreaVertical: $_safeAreaVertical '); print('Screen Scaling Values:' + '_safeFactorVertical: $_safeFactorVertical '); print('_safeAreaTextScalingFactor: $_safeAreaTextScalingFactor '); print('Default Material Design Text Themes'); print('display4: ${Theme.of(context).textTheme.display4}'); print('display3: ${Theme.of(context).textTheme.display3}'); print('display2: ${Theme.of(context).textTheme.display2}'); print('display1: ${Theme.of(context).textTheme.display1}'); print('headline: ${Theme.of(context).textTheme.headline}'); print('title: ${Theme.of(context).textTheme.title}'); print('subtitle: ${Theme.of(context).textTheme.subtitle}'); print('body2: ${Theme.of(context).textTheme.body2}'); print('body1: ${Theme.of(context).textTheme.body1}'); print('caption: ${Theme.of(context).textTheme.caption}'); print('button: ${Theme.of(context).textTheme.button}'); TextScalingFactors _textScalingFactors = TextScalingFactors( display4ScaledSize: (Theme.of(context).textTheme.display4.fontSize * _safeAreaTextScalingFactor), display3ScaledSize: (Theme.of(context).textTheme.display3.fontSize * _safeAreaTextScalingFactor), display2ScaledSize: (Theme.of(context).textTheme.display2.fontSize * _safeAreaTextScalingFactor), display1ScaledSize: (Theme.of(context).textTheme.display1.fontSize * _safeAreaTextScalingFactor), headlineScaledSize: (Theme.of(context).textTheme.headline.fontSize * _safeAreaTextScalingFactor), titleScaledSize: (Theme.of(context).textTheme.title.fontSize * _safeAreaTextScalingFactor), subtitleScaledSize: (Theme.of(context).textTheme.subtitle.fontSize * _safeAreaTextScalingFactor), body2ScaledSize: (Theme.of(context).textTheme.body2.fontSize * _safeAreaTextScalingFactor), body1ScaledSize: (Theme.of(context).textTheme.body1.fontSize * _safeAreaTextScalingFactor), captionScaledSize: (Theme.of(context).textTheme.caption.fontSize * _safeAreaTextScalingFactor), buttonScaledSize: (Theme.of(context).textTheme.button.fontSize * _safeAreaTextScalingFactor)); return Theme( child: child, data: _buildAppTheme(_textScalingFactors), ); } } final ThemeData customTheme = ThemeData( primarySwatch: appColorSwatch, // fontFamily: x, ); final MaterialColor appColorSwatch = MaterialColor(0xFF3787AD, appSwatchColors); Map<int, Color> appSwatchColors = { 50 : Color(0xFFE3F5F8), 100 : Color(0xFFB8E4ED), 200 : Color(0xFF8DD3E3), 300 : Color(0xFF6BC1D8), 400 : Color(0xFF56B4D2), 500 : Color(0xFF48A8CD), 600 : Color(0xFF419ABF), 700 : Color(0xFF3787AD), 800 : Color(0xFF337799), 900 : Color(0xFF285877), }; _buildAppTheme (TextScalingFactors textScalingFactors) { return customTheme.copyWith( accentColor: appColorSwatch[300], buttonTheme: customTheme.buttonTheme.copyWith(buttonColor: Colors.grey[500],), cardColor: Colors.white, errorColor: Colors.red, inputDecorationTheme: InputDecorationTheme(border: OutlineInputBorder(),), primaryColor: appColorSwatch[700], primaryIconTheme: customTheme.iconTheme.copyWith(color: appColorSwatch), scaffoldBackgroundColor: Colors.grey[100], textSelectionColor: appColorSwatch[300], textTheme: _buildAppTextTheme(customTheme.textTheme, textScalingFactors), appBarTheme: customTheme.appBarTheme.copyWith( textTheme: _buildAppTextTheme(customTheme.textTheme, textScalingFactors)), // accentColorBrightness: , // accentIconTheme: , // accentTextTheme: , // appBarTheme: , // applyElevationOverlayColor: , // backgroundColor: , // bannerTheme: , // bottomAppBarColor: , // bottomAppBarTheme: , // bottomSheetTheme: , // brightness: , // buttonBarTheme: , // buttonColor: , // canvasColor: , // cardTheme: , // chipTheme: , // colorScheme: , // cupertinoOverrideTheme: , // cursorColor: , // dialogBackgroundColor: , // dialogTheme: , // disabledColor: , // dividerColor: , // dividerTheme: , // floatingActionButtonTheme: , // focusColor: , // highlightColor: , // hintColor: , // hoverColor: , // iconTheme: , // indicatorColor: , // materialTapTargetSize: , // pageTransitionsTheme: , // platform: , // popupMenuTheme: , // primaryColorBrightness: , // primaryColorDark: , // primaryColorLight: , // primaryTextTheme: , // secondaryHeaderColor: , // selectedRowColor: , // sliderTheme: , // snackBarTheme: , // splashColor: , // splashFactory: , // tabBarTheme: , // textSelectionHandleColor: , // toggleableActiveColor: , // toggleButtonsTheme: , // tooltipTheme: , // typography: , // unselectedWidgetColor: , ); } class TextScalingFactors { final double display4ScaledSize; final double display3ScaledSize; final double display2ScaledSize; final double display1ScaledSize; final double headlineScaledSize; final double titleScaledSize; final double subtitleScaledSize; final double body2ScaledSize; final double body1ScaledSize; final double captionScaledSize; final double buttonScaledSize; TextScalingFactors({ @required this.display4ScaledSize, @required this.display3ScaledSize, @required this.display2ScaledSize, @required this.display1ScaledSize, @required this.headlineScaledSize, @required this.titleScaledSize, @required this.subtitleScaledSize, @required this.body2ScaledSize, @required this.body1ScaledSize, @required this.captionScaledSize, @required this.buttonScaledSize }); } TextTheme _buildAppTextTheme( TextTheme _customTextTheme, TextScalingFactors _scaledText) { return _customTextTheme.copyWith( display4: _customTextTheme.display4.copyWith(fontSize: _scaledText.display4ScaledSize), display3: _customTextTheme.display3.copyWith(fontSize: _scaledText.display3ScaledSize), display2: _customTextTheme.display2.copyWith(fontSize: _scaledText.display2ScaledSize), display1: _customTextTheme.display1.copyWith(fontSize: _scaledText.display1ScaledSize), headline: _customTextTheme.headline.copyWith(fontSize: _scaledText.headlineScaledSize), title: _customTextTheme.title.copyWith(fontSize: _scaledText.titleScaledSize), subtitle: _customTextTheme.subtitle.copyWith(fontSize: _scaledText.subtitleScaledSize), body2: _customTextTheme.body2.copyWith(fontSize: _scaledText.body2ScaledSize), body1: _customTextTheme.body1.copyWith(fontSize: _scaledText.body1ScaledSize), caption: _customTextTheme.caption.copyWith(fontSize: _scaledText.captionScaledSize), button: _customTextTheme.button.copyWith(fontSize: _scaledText.buttonScaledSize), ).apply(bodyColor: Colors.black); }
main.dart (aplicación de demostración)
import 'package:flutter/material.dart'; import 'package:scaling/set_app_theme.dart'; void main() => runApp(MyApp()); class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { return MaterialApp( home: SetAppTheme(child: HomePage()), ); } } class HomePage extends StatelessWidget { final demoText = '0123456789'; @override Widget build(BuildContext context) { return SafeArea( child: Scaffold( appBar: AppBar( title: Text('Text Scaling with SetAppTheme', style: TextStyle(color: Colors.white),), ), body: SingleChildScrollView( child: Center( child: Padding( padding: const EdgeInsets.all(8.0), child: Column( children: <Widget>[ Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.display4.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.display3.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.display2.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.display1.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.headline.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.title.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.subtitle.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.body2.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.body1.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.caption.fontSize, ), ), Text( demoText, style: TextStyle( fontSize: Theme.of(context).textTheme.button.fontSize, ), ), ], ), ), ), ), ), ); } }
fuente
Place dependency in pubspec.yaml flutter_responsive_screen: ^1.0.0 Function hp = Screen(MediaQuery.of(context).size).hp; Function wp = Screen(MediaQuery.of(context).size).wp; Example : return Container(height: hp(27),weight: wp(27));
fuente
Puede usar MediaQuery para la dimensión principal o FractionallySizedBox como contenedores.
fuente
Mi enfoque del problema es similar a la forma en que lo hizo datayeah. Tenía muchos valores de ancho y alto codificados y la aplicación se veía bien en un dispositivo específico. Así que obtuve la altura de la pantalla del dispositivo y creé un factor para escalar los valores codificados.
double heightFactor = MediaQuery.of(context).size.height/708
donde 708 es la altura del dispositivo específico.
fuente
Intento hacerlo lo más simple posible. pruébalo. Hago una utilidad receptiva que tiene la función getresponsivevalue responsable de proporcionar valor de acuerdo con el tamaño de la pantalla si no asigna un valor para una pantalla mediana, pantalla grande, modo horizontal De forma predeterminada, proporciona un valor asignado de pantalla corta. una cálida bienvenida para cualquier consulta. Me encantaría mejorar
class SampleView extends StatelessWidget { @override Widget build(BuildContext context) { return Center( child: Container( width: 200, height: 200, color: Responsive().getResponsiveValue( forLargeScreen: Colors.red, forMediumScreen: Colors.green, forShortScreen: Colors.yellow, forMobLandScapeMode: Colors.blue, context: context), ), );
}}
// utility class class Responsive { // function reponsible for providing value according to screensize getResponsiveValue( {dynamic forShortScreen, dynamic forMediumScreen, dynamic forLargeScreen, dynamic forMobLandScapeMode, BuildContext context}) { if (isLargeScreen(context)) { return forLargeScreen ?? forShortScreen; } else if (isMediumScreen(context)) { return forMediumScreen ?? forShortScreen; } else if (isSmallScreen(context) && isLandScapeMode(context)) { return forMobLandScapeMode ?? forShortScreen; } else { return forShortScreen; } } isLandScapeMode(BuildContext context) { if (MediaQuery.of(context).orientation == Orientation.landscape) { return true; } else { return false; } } static bool isLargeScreen(BuildContext context) { return getWidth(context) > 1200; } static bool isSmallScreen(BuildContext context) { return getWidth(context) < 800; } static bool isMediumScreen(BuildContext context) { return getWidth(context) > 800 && getWidth(context) < 1200; } static double getWidth(BuildContext context) { return MediaQuery.of(context).size.width; } }
fuente
echa un vistazo a esta página de flutter wiki:
Creación de aplicaciones receptivas
fuente
cree el nombre del archivo (app_config.dart) en el nombre de la carpeta (responsive_screen) en la carpeta lib:
import 'package:flutter/material.dart'; class AppConfig { BuildContext _context; double _height; double _width; double _heightPadding; double _widthPadding; AppConfig(this._context) { MediaQueryData _queryData = MediaQuery.of(_context); _height = _queryData.size.height / 100.0; _width = _queryData.size.width / 100.0; _heightPadding = _height - ((_queryData.padding.top + _queryData.padding.bottom) / 100.0); _widthPadding = _width - (_queryData.padding.left + _queryData.padding.right) / 100.0; } double rH(double v) { return _height * v; } double rW(double v) { return _width * v; } double rHP(double v) { return _heightPadding * v; } double rWP(double v) { return _widthPadding * v; } }
entonces:
import 'responsive_screen/app_config.dart'; ... class RandomWordsState extends State<RandomWords> { AppConfig _ac; ... @override Widget build(BuildContext context) { _ac = AppConfig(context); ... return Scaffold( body: Container( height: _ac.rHP(50), width: _ac.rWP(50), color: Colors.red, child: Text('Test'), ), ); ... }
fuente
Este problema se puede resolver usando MediaQuery.of (contexto)
Para obtener el ancho de la pantalla:
MediaQuery.of(context).size.width
Para obtener la altura de la pantalla:
MediaQuery.of(context).size.height
Para obtener más información sobre el reloj MediaQuery Widget, https://www.youtube.com/watch?v=A3WrA4zAaPw
fuente
padding: EdgeInsets.only( left: 4.0, right: ResponsiveWidget.isSmallScreen(context) ? 4: 74, //Check for screen type top: 10, bottom: 40),
Esto está bien por recomendación de Google, pero puede que no sea perfecto.
fuente
ResponsiveBuilder o ScreenTypeLayout usados
import 'package:flutter/material.dart'; import 'package:flutter/widgets.dart'; import 'package:responsive_builder/responsive_builder.dart'; class Sample extends StatelessWidget { @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar( elevation: 0, backgroundColor: Colors.black, ), body: ResponsiveBuilder( builder: (context, info) { var screenType = info.deviceScreenType; String _text; switch (screenType){ case DeviceScreenType.desktop: { _text = 'Desktop'; break; } case DeviceScreenType.tablet: { _text = 'Tablet'; break; } case DeviceScreenType.mobile: { _text = 'Mobile'; break; } case DeviceScreenType.watch: { _text = 'Watch'; break; } default: return null; } return Center(child: Text(_text, style: TextStyle(fontSize: 32, color: Colors.black),)); }, ), ); } } // screen type layout ScreenTypeLayout.builder( mobile: MobilePage(), tablet: TabletPage(), desktop: DesktopPage(), watch: Watchpage(), );
fuente
Puede usar el paquete responsive_helper para que su aplicación responda.
Es un método muy fácil para hacer que su aplicación responda. Simplemente eche un vistazo a la página de ejemplo y luego averiguará cómo usarla.
fuente
La forma más fácil de hacer una interfaz de usuario receptiva para diferentes tamaños de pantalla es el complemento Sizer .
Haga una interfaz de usuario receptiva en cualquier dispositivo de tamaño de pantalla, también en tableta. Compruébalo en este complemento ⬇️
https://pub.dev/packages/sizer
.h - for widget height .w - for widget width .sp - for font size
Uso
.h
,.w
,.sp
después de valor como esto ⬇️Ejemplo:
Container( height: 10.0.h, //10% of screen height width: 80.0.w, //80% of screen width child: Text('Sizer', style: TextStyle(fontSize: 12.0.sp)), );
He creado muchas aplicaciones receptivas con este complemento.
fuente
Anchura:
MediaQuery.of(context).size.width
,Altura:
MediaQuery.of(context).size.height
,fuente