Ratnadeep
Ratnadeep

Reputation: 1233

How to solve it when Flutter MaterialPageRoute navigates to a screen with black background?

I'm using Flutter for first time for one of my projects which is a Newspaper App.

The problem takes place when I try to navigate from main.dart to newsfeed_for_other_category.dart using MaterialPageRoute from my Drawer. In that screen it shows the news but with a black background. But in the screen newsfeed_screen.dart which is called in the body in my main.dart it shows perfectly.

I'm posting the codes below.

main.dart

import 'package:flutter/material.dart';
import './SizeConfig.dart';
import './screens/newsfeed_screen.dart';
import 'package:curved_navigation_bar/curved_navigation_bar.dart';
import 'factory/widget_factory.dart';
import 'widgets/top_news_widget.dart';
import 'package:splashscreen/splashscreen.dart';
import './widgets/drawer.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Newspaper App',
      theme: ThemeData(
        primarySwatch: Colors.blue,
        //backgroundColor: Colors.lightGreenAccent,
      ),
      home: MyHomePage(title: 'The Business Standard'),
      routes: <String, WidgetBuilder> {
        '/screen1': (BuildContext context) => new NewsFeedScreen(216, 5, "Top News"),
        '/screen2' : (BuildContext context) => new NewsFeedScreen(4, 7, "National"),
        '/screen3' : (BuildContext context) => new NewsFeedScreen(13, 70, "International"),
        /*'/screen4' : (BuildContext context) => new Screen4()*/
      },
    );
  }
}

class MyHomePage extends StatefulWidget {
  MyHomePage({Key key, this.title}) : super(key: key);

  final String title;

  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  int _counter = 0;
  final GlobalKey<ScaffoldState> _scaffoldKey = new GlobalKey<ScaffoldState>(debugLabel: '_MainScreenKey');

  Widget build(BuildContext context) {
    return SplashScreen(
        seconds: 3,
        navigateAfterSeconds: AfterSplash(),
        title: Text(
          'The Business Standard',
          style: TextStyle(
              fontWeight: FontWeight.bold,
              fontSize: 20.0
          ),
        ),
        image: Image.asset(
            'assets/TBS_logo.jpg',
        ),
        backgroundColor: Colors.white,
        styleTextUnderTheLoader: TextStyle(),
        photoSize: 100.0,
        onClick: ()=>print("Flutter Egypt"),
        loaderColor: Colors.red
    );
  }
}

class AfterSplash extends StatefulWidget {

  @override
  _AfterSplashState createState() => _AfterSplashState();
}

class _AfterSplashState extends State<AfterSplash> {
  final GlobalKey<ScaffoldState> _scaffoldKey = new GlobalKey<ScaffoldState>(debugLabel: '_MainScreenKey');

  @override
  Widget build(BuildContext context) {
    SizeConfig().init(context);
    return Scaffold(
      key: _scaffoldKey,
      appBar: AppBar(
        backgroundColor: Colors.white,
        title: Row(
          mainAxisAlignment: MainAxisAlignment.start,
          children: <Widget>[
            Image.asset(
              'assets/TBS.png',
              fit: BoxFit.cover,
              height: 45,
            )
          ],
        ),
        leading: IconButton(
          icon: Icon(Icons.dehaze),
          color: Colors.black,
          onPressed: () => _scaffoldKey.currentState.openDrawer(),
        ),
      ),
      drawer: SideDrawer(),
      body: NewsFeedScreen(22, 71, "Sports"),
      bottomNavigationBar: CurvedNavigationBar(
        backgroundColor: const Color(0xFF2b4849),
        items: <Widget>[
          Icon(Icons.bookmark, size: 30,),
          Icon(Icons.perm_identity, size: 30,),
          Icon(Icons.settings, size: 30,),
        ],
        onTap: (index) {
          if(index == 2) {
            _scaffoldKey.currentState.showSnackBar(const SnackBar(
                content: const Text('Will open Settings menu')));
          } else if(index == 0) {
            _scaffoldKey.currentState.showSnackBar(const SnackBar(
                content: const Text('Implement Bookmark function')));
          } else {
            _scaffoldKey.currentState.showSnackBar(const SnackBar(
                content: const Text('Will show User profile and information')));
          }
        },
      ),
    );
  }
}

newsfeed_for_other_category.dart, the page to which I'm navigating and this is where the black background shows up.

import 'package:flutter/material.dart';
import '../SizeConfig.dart';
import '../widgets/headlines.dart';
import '../widgets/secondary_headlines.dart';
import '../widgets/listed_news.dart';
import '../models/NewsPost.dart';
import 'package:http/http.dart' as http;
import 'dart:convert';
import 'dart:developer';
import '../screens/newsPost_details.dart';
import '../screens/newsfeed_for_specific_category.dart';
import 'package:flutter_swiper/flutter_swiper.dart';
import '../transition_animation_routes/ScaleTransitionRoute.dart';
import '../widgets/top_news_widget.dart';

class NewsfeedForOtherCategory extends StatefulWidget {
  int categoryId;
  int childrenCategoryId;
  String categoryName;

  NewsfeedForOtherCategory(this.categoryId, this.childrenCategoryId, this.categoryName);
  @override
  _NewsfeedForOtherCategoryState createState() => _NewsfeedForOtherCategoryState(this.categoryId, this.childrenCategoryId, this.categoryName);
}

class _NewsfeedForOtherCategoryState extends State<NewsfeedForOtherCategory> {
  int categoryId;
  int childrenCategoryId;
  String categoryName;

  _NewsfeedForOtherCategoryState(this.categoryId, this.childrenCategoryId, this.categoryName);

  bool _isRequestSent = false;
  List<NewsPost> newsPostList = [];

  @override
  Widget build(BuildContext context) {
    SizeConfig().init(context);

    if(!_isRequestSent) {
      _sendRequest();
    }

    return Container(
      alignment: Alignment.center,
      child: !_isRequestSent
          ? CircularProgressIndicator()
          : Container(
        child: ListView.builder(
            itemCount: newsPostList.length,
            scrollDirection: Axis.vertical,
            itemBuilder: (BuildContext context, int index) {
              return _getNewsPostWidgets(index);
            }
        ),
      ),
    );
  }

  void _sendRequest() async {
    String url = "https://tbsnews.net/json/category/news/"+this.categoryId.toString()+"/"+this.childrenCategoryId.toString()+"";
    http.Response response = await http.get(url);
    List<dynamic> decode = json.decode(response.body);
    log('response: $response');
    List results = decode[0]['items'];
    for (var jsonObject in results) {
      var post = NewsPost.getNewsPostFromAPI(jsonObject);
      newsPostList.add(post);
      print(post);
    }
    setState(() => _isRequestSent = true);
  }

  Widget _getNewsPostWidgets(int index) {
    var newsPost = newsPostList[index];

    if(index < this.newsPostList.length) {
      if(index == 0) {
        return GestureDetector(
            onTap: () {
              Navigator.push(
                  context,
                  ScaleTransitionRoute(
                      page: NewsPostDetails(newsPostList, index)
                  )
              );
            },
            child: Column(
              children: <Widget>[
                Container(
                  padding: EdgeInsets.fromLTRB(10, 0, 0, 0),
                  //constraints: BoxConstraints(minWidth: double.infinity, maxWidth: double.infinity),
                  constraints: BoxConstraints.expand(
                      width: double.infinity,
                      height: 40
                  ),
                  color: const Color(0xFF2b4849),
                  child: Text(
                    this.categoryName,
                    style: TextStyle(
                        fontSize: 33,
                        color: Colors.white
                    ),
                  ),
                ),
                BlockHeadline(newsPost)
              ],
            )
        );
      }
      else {
        return GestureDetector(
          onTap: () {
            Navigator.push(
                context,
                ScaleTransitionRoute(
                    page: NewsPostDetails(newsPostList, index)
                )
            );
          },
          child: ListedNews(newsPost),
        );
      }
    }
    else {
      return Container(
        color: const Color(0xFF2b4849),
        child: index == 3 ? FlatButton(
          child: Text(
            "Load More",
            style: TextStyle(
                color: Colors.white
            ),
          ),
          onPressed: () {
            Navigator.push(
                context,
                MaterialPageRoute(
                    builder: (BuildContext context) => NewsFeedForSpecificCategory(newsPostList)
                )
            );
          },
        ) : Container(),
      );
    }
  }

  openNewsPostDetails(List<NewsPost> newsPostList, int index) {
    Navigator.push(
        context,
        ScaleTransitionRoute(
            page: NewsPostDetails(newsPostList, index)
        )
    );
  }
}

drawer.dart

import 'package:flutter/material.dart';
import '../SizeConfig.dart';
import '../screens/newsfeed_for_other_category.dart';

class SideDrawer extends StatelessWidget {

  @override
  Widget build(BuildContext context) {
    SizeConfig().init(context);
    return SizedBox(
      width: SizeConfig.safeBlockHorizontal*50,
      child: Theme(
        data: Theme.of(context).copyWith(canvasColor: const Color(0xFF2b4849)),
        child: Drawer(
          child: ListView(
            children: <Widget>[
              ListTile(
                title: Text(
                  'Top News',
                  style: TextStyle(
                      fontSize: 20,
                      color: Colors.white
                  ),
                ),
                onTap: () {
                  Navigator.push(
                      context,
                      MaterialPageRoute(
                          builder: (BuildContext context) => NewsfeedForOtherCategory(216, 5, "Top News")
                      )
                  );
                },
              ),
            ],
          ),
        ),
      ),
    );
  }
}

In my home screen which is newsfeed_screen.dart called in the body of AfterSplashState widget in main.dart it looks like below, this is what it should look like.

enter image description here

But in the screen NewsfeedForOtherCategory to which I navigate using drawer looks like below with the black background.

enter image description here

I have tried using Navigator.of(context, rootNavigator: true).pushNamed('/route') and pushReplacementNamed() also instead of MaterialPageRoute. But of no use.

Here is a related question that I found, I tried the solutions they gave, but did not work for me.

Also to mention, the page I'm navigating to does not have MaterialApp widget, only the main.dart has it. So there should not be an issue.

I'm using a Ubuntu 16.04 machine.

Some clue from you would be priceless. Thanks a lot for your time.

Upvotes: 4

Views: 7431

Answers (4)

Dipak Ramoliya
Dipak Ramoliya

Reputation: 687

when we navigate between two screen both screen parent should be scafold

if you don't want to use scaffold u can use container color property also

Try wrapping your container in scaffold in NewsfeedForOtherCategory screen Like this

...
 @override
  Widget build(BuildContext context) {
    return Scaffold(
              body: Container(
               
              ),
            );
}
...

Or u can set container color white like this

...
 @override
  Widget build(BuildContext context) {
    return  Container(
               color: Colors.white,
            child: 
            //enter code here
             
            );
}
...

Upvotes: 0

Crazy Lazy Cat
Crazy Lazy Cat

Reputation: 15103

NewsfeedForOtherCategory page is black because it doesn't have Material container. You can simply wrap it with Material widget or Scaffold(which has some additional features like drawer, floating action button).

And from your screenshot I can see some widgets are overflowed by notification bar. You can use SafeArea inside Material or inside body of the Scaffold to overcome this.

Upvotes: 6

Chibuzc
Chibuzc

Reputation: 174

In the build function of your NewsfeedForOtherCategory widget, try wrapping what you have there in a Scaffold. Like:

    return Scaffold(
              body: Container(
                alignment: Alignment.center,
                child: !_isRequestSent
                    ? CircularProgressIndicator()
                    : Container(
                        child: ListView.builder(
                            itemCount: newsPostList.length,
                            scrollDirection: Axis.vertical,
                            itemBuilder: (BuildContext context, int index) {
                              return _getNewsPostWidgets(index);
                            }),
                      ),
              ),
            ),

Upvotes: 0

user321553125
user321553125

Reputation: 3246

Wrap the main Container in NewsfeedForOtherCategory with a scaffold and you have your solution.

    ...
    return Scaffold(
      body: Container(
          alignment: Alignment.center,
          child: !_isRequestSent
              ? CircularProgressIndicator()
              : Container(
            child: ListView.builder(
                itemCount: newsPostList.length,
                scrollDirection: Axis.vertical,
                itemBuilder: (BuildContext context, int index) {
                  return _getNewsPostWidgets(index);
                }
            ),
          ),
        );
    );
    ...

Upvotes: 3

Related Questions