137

I have this container:

  new Container(
    width: 500.0,
    padding: new EdgeInsets.fromLTRB(20.0, 40.0, 20.0, 40.0),
    color: Colors.green,
    child: new Column(
      children: [
        new Text("Ableitungen"),
      ]
    ),
  ),

When the user clicks on the Container, I want an onPressed() method to be fired (like it can be done with IconButton for example). How can I achieve this behaviour with Container?

11 Answers 11

261

You can use a GestureDetector widget like this:

new GestureDetector(
        onTap: (){
          print("Container clicked");
        },
        child: new Container(
          width: 500.0,
          padding: new EdgeInsets.fromLTRB(20.0, 40.0, 20.0, 40.0),
          color: Colors.green,
          child: new Column(
              children: [
                new Text("Ableitungen"),
              ]
          ),
        )
    );
1
  • I want to add on tap functionality to container .... have tried both inkwell and gesture detector as well but both are not working !!! Jun 7, 2021 at 6:03
155

Don't use GestureDetector, it doesn't show ripple effect. Use InkWell instead.

InkWell(
  onTap: () {}, // Handle your callback
  child: Ink(height: 100, width: 100, color: Colors.blue),
)

Output:

enter image description here

4
  • 6
    FYI: If you use Container inside the InkWell then ripple may not appear if you also have the decoration. See stackoverflow.com/questions/51463515/…. As shown by @CopsOnRoad use Ink, it supports almost all features as Container. Jan 2, 2021 at 17:08
  • I want to add on tap functionality to container .... have tried both inkwell and gesture detector as well but both are not working !!! Jun 7, 2021 at 6:04
  • ripple is not shown for me using container + decration Oct 20, 2022 at 14:16
  • @KristiJorgji Yes, that's why you should use Ink and not a Container. However, you can set a color with some opacity in your container to see the ripple effect but it's more of a workaround and may not always fit your needs. So, better to use Ink as shown above.
    – CopsOnRoad
    Oct 20, 2022 at 15:24
22

The simplest solution is to wrap the Container in a GestureRecognizer, but consider using an InkWell or FlatButton if you are building a Material design app. These widgets will show a visual splash response when touched.

0
16

The container itself doesn't have any click event, so to do that there are two ways

  1. InkWell widget
  2. GestureDetector

In Flutter, InkWell is a material widget that responds to touch action.

InkWell(
    child: Container(......),
    onTap: () { 
        print("Click event on Container"); 
    },
);

GestureDetector is a widget that detects the gestures.

GestureDetector(
    onTap: () { 
        print("Click event on Container"); 
    },
    child: Container(.......),
)

Difference

InkWell is a material widget and it can show you a Ripple Effect whenever a touch was received.

GestureDetector is more general-purpose, not only for touch but also for other gestures.

5

Heading

GestureDetector vs InkWell

You can use two widget

1) GestureDetector

    GestureDetector(

        onTap: (){
          print("Container clicked");
        },
        child: new Container(child: ...)          
    );

This widget, doesn't have any effect.

2) InkWell

    InkWell(

        child: Container(......),
        onTap: () { 
            print("Click event on Container"); 
        },
    );

This widget has animation effect.

4

Just wanted to add on to The Dumbfounds answer(accepted ans above)

If you are using GestureDetector or InkWell to handle the click of a group of icon and text, then use Icon widget instead of IconButton to display the icon as the onPressed method of IconButton will take over the onTap method of GestureDetector/InkWell and as a result the onTap then will only work if you click on the text.

Example -

@override
  Widget build(BuildContext context) {
    return Row(mainAxisSize: MainAxisSize.min, children: [
      GestureDetector(
        onTap: () {
          _toggleFavorite();
        },
        child: Row(
          children: [
            Container(
              padding: EdgeInsets.all(0.0),
              child: _isFavorited ? Icon(Icons.star, color: Colors.red[500]) : Icon(Icons.star_border),
            ),
            SizedBox(
              width: 18.0,
              child: Container(
                child: Text('$_favoriteCount'),
              ),
            )
          ],
        ),
      )
    ]);
  }
}
2
InkWell(
    child: Container(
    width: 500.0,
    padding: new EdgeInsets.fromLTRB(20.0, 40.0, 20.0, 40.0),
    color: Colors.green,
    child: new Column(
        children: [
            new Text("Ableitungen"),
            ]
        ),
    ),
    onTap: () { 
        print("Tapped on container"); 
    },
);
1

User can make button of any widget using Inkwell and GestureDetector.

InkWell(
    onTap: () { 
        print("Tapped"); 
    },
    child: Container(/* ... */),
);
GestureDetector(
    onTap: () { 
        print("Tapped"); 
    },
    child: Container(/* ... */),
)
1

Actual Answer of the question

InkWell is the best from user experience.

 Container(            
        child: InkWell(
          onTap: () { //handle your callback   },
          child: Ink(
            color: Colors.amber,
            child: Padding(
                  padding: EdgeInsets.all(16.0),
                  child: Text('Click on me'),
            ),                  
          ),
        ),
      );
0

Use GestureDetector to give ontap on Container. Wrap Container with GestureDetector Widget:

GestureDetector(
    onTap: () { 
        print("Please tap here."); 
    },
    child: Container(
        width: 500.0,
        padding: new EdgeInsets.fromLTRB(20.0, 40.0, 20.0, 40.0),
        color: Colors.green,
        child: new Column(
          children: [
            new Text("Hello"),
          ]
        ),
    ),
),
0
InkWell(
    child: Container(/* ... */),
    onTap: () { 
        print("Add your on tap event in this block"); 
    },
);

Use InkWell because it will provide you a nice material ripple effect.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.