diff --git a/docs/tutorials/add-model.rst b/docs/tutorials/add-model.rst
index 3e24fedd1..b72198626 100644
--- a/docs/tutorials/add-model.rst
+++ b/docs/tutorials/add-model.rst
@@ -153,12 +153,13 @@ every model and submodel.
 
 Unit tests for a MyNewModel
 ---------------------------
-We stongly recommend testing your model to ensure that it is behaving correctly. To do this, first create a new file ``test_my_new_model.py`` within ``tests/unit/test_models`` (or the appropriate subdirectory). Within this file, add the following code
+We strongly recommend testing your model to ensure that it is behaving correctly. To do
+this, first create a new file ``test_my_new_model.py`` within
+``tests/integration/test_models`` (or the appropriate subdirectory). Within this file,
+add the following code
 
 .. code-block:: python 
 
-    from __future__ import absolute_import, division
-    from __future__ import print_function, unicode_literals
     import pybamm
     import unittest
 
@@ -178,5 +179,3 @@ We can now add functions such as :meth:`my_first_test` to :class:`TestMyNewModel
 
 Please see the tests of the inbuilt models to get a further idea of how to test the your model.
 
-
-
diff --git a/pybamm/models/simple_ode_model.py b/pybamm/models/simple_ode_model.py
index e3de502e9..9d7ab3969 100644
--- a/pybamm/models/simple_ode_model.py
+++ b/pybamm/models/simple_ode_model.py
@@ -15,6 +15,8 @@ class SimpleODEModel(pybamm.StandardBatteryBaseModel):
 
     def __init__(self):
         super().__init__()
+        self.name = "Simple ODE Model"
+
         whole_cell = ["negative electrode", "separator", "positive electrode"]
         # Create variables: domain is explicitly empty since these variables are only
         # functions of time
diff --git a/pybamm/quick_plot.py b/pybamm/quick_plot.py
index 03db64501..bbf27261b 100644
--- a/pybamm/quick_plot.py
+++ b/pybamm/quick_plot.py
@@ -54,10 +54,14 @@ class QuickPlot(object):
         else:
             raise ValueError("must provide the same number of models and solutions")
 
-        # Scales
+        # Scales (default to 1 if information not in model)
         vars = models[0].variables
-        self.x_scale = (vars["x [m]"] / vars["x"]).evaluate()[-1]
-        self.time_scale = (vars["Time [h]"] / vars["Time"]).evaluate(t=1)
+        self.x_scale = 1
+        self.time_scale = 1
+        if "x [m]" and "x" in vars:
+            self.x_scale = (vars["x [m]"] / vars["x"]).evaluate()[-1]
+        if "Time [m]" and "Time" in vars:
+            self.time_scale = (vars["Time [h]"] / vars["Time"]).evaluate(t=1)
 
         # Time parameters
         self.ts = [solver.t for solver in solvers]
@@ -86,6 +90,10 @@ class QuickPlot(object):
                     "Electrolyte potential [V]",
                     "Terminal voltage [V]",
                 ]
+            # else plot all variables in first model
+            else:
+                output_variables = models[0].variables
+
         self.set_output_variables(output_variables, solvers, models, mesh)
         self.reset_axis()
 

rename convergence tests to "integration"
and put in standard model tests to integration
diff --git a/run-tests.py b/run-tests.py
index 1e5e31165..1549f2fbb 100755
--- a/run-tests.py
+++ b/run-tests.py
@@ -23,7 +23,7 @@ def run_code_tests(executable=None, folder: str = "unit"):
         If given, tests are run in subprocesses using the given executable (e.g.
         'python2' or 'python3').
     folder : str
-        Which folder to run the tests from (unit, convergence or both ('all'))
+        Which folder to run the tests from (unit, integration or both ('all'))
 
     """
     if folder == "all":
@@ -317,7 +317,7 @@ if __name__ == "__main__":
         "--folder",
         nargs=1,
         default=["unit"],
-        choices=["unit", "convergence", "all"],
+        choices=["unit", "integration", "all"],
         help="Which folder to run the tests from.",
     )
     # Notebook tests
@@ -359,7 +359,7 @@ if __name__ == "__main__":
 
     # Run tests
     has_run = False
-    # Unit vs convergence
+    # Unit vs integration
     folder = args.folder[0]
     # Unit tests
     if args.unit:
diff --git a/tests/__init__.py b/tests/__init__.py
index 059bcd295..f2772338d 100644
--- a/tests/__init__.py
+++ b/tests/__init__.py
@@ -2,8 +2,8 @@
 # Root of the tests module.
 # Provides access to all shared functionality
 #
-from .unit.test_models.standard_model_tests import StandardModelTest, OptimisationsTest
-from .unit.test_models.standard_output_tests import StandardOutputTests
+from .integration.test_models.standard_model_tests import StandardModelTest, OptimisationsTest
+from .integration.test_models.standard_output_tests import StandardOutputTests
 from .shared import (
     get_mesh_for_testing,
     get_p2d_mesh_for_testing,
diff --git a/tests/convergence/__init__.py b/tests/integration/__init__.py
similarity index 100%
rename from tests/convergence/__init__.py
rename to tests/integration/__init__.py
diff --git a/tests/convergence/test_models/__init__.py b/tests/integration/test_models/__init__.py
similarity index 100%
rename from tests/convergence/test_models/__init__.py
rename to tests/integration/test_models/__init__.py
diff --git a/tests/unit/test_models/standard_model_tests.py b/tests/integration/test_models/standard_model_tests.py
similarity index 100%
rename from tests/unit/test_models/standard_model_tests.py
rename to tests/integration/test_models/standard_model_tests.py
diff --git a/tests/unit/test_models/standard_output_tests.py b/tests/integration/test_models/standard_output_tests.py
similarity index 100%
rename from tests/unit/test_models/standard_output_tests.py
rename to tests/integration/test_models/standard_output_tests.py
diff --git a/tests/convergence/test_models/test_lead_acid/__init__.py b/tests/integration/test_models/test_lead_acid/__init__.py
similarity index 100%
rename from tests/convergence/test_models/test_lead_acid/__init__.py
rename to tests/integration/test_models/test_lead_acid/__init__.py
diff --git a/tests/convergence/test_models/test_lead_acid/test_asymptotics_convergence.py b/tests/integration/test_models/test_lead_acid/test_asymptotics_convergence.py
similarity index 100%
rename from tests/convergence/test_models/test_lead_acid/test_asymptotics_convergence.py
rename to tests/integration/test_models/test_lead_acid/test_asymptotics_convergence.py
diff --git a/tests/integration/test_models/test_lead_acid/test_composite.py b/tests/integration/test_models/test_lead_acid/test_composite.py
new file mode 100644
index 000000000..d7c3f1c54
--- /dev/null
+++ b/tests/integration/test_models/test_lead_acid/test_composite.py
@@ -0,0 +1,36 @@
+#
+# Tests for the lead-acid composite model
+#
+import pybamm
+import tests
+
+import unittest
+import numpy as np
+
+
+class TestLeadAcidComposite(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.lead_acid.Composite()
+        modeltest = tests.StandardModelTest(model)
+        modeltest.test_all(skip_output_tests=True)
+
+    def test_optimisations(self):
+        model = pybamm.lead_acid.Composite()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known)
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/integration/test_models/test_lead_acid/test_composite_capacitance.py b/tests/integration/test_models/test_lead_acid/test_composite_capacitance.py
new file mode 100644
index 000000000..a79e0f6b6
--- /dev/null
+++ b/tests/integration/test_models/test_lead_acid/test_composite_capacitance.py
@@ -0,0 +1,44 @@
+#
+# Tests for the lead-acid composite model
+#
+import pybamm
+from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
+import tests
+
+import unittest
+import numpy as np
+
+
+class TestLeadAcidCompositeCapacitance(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.lead_acid.CompositeCapacitance()
+        modeltest = tests.StandardModelTest(model)
+        modeltest.test_all(skip_output_tests=True)
+
+    @unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
+    def test_basic_processing_no_capacitance(self):
+        model = pybamm.lead_acid.CompositeCapacitance(use_capacitance=False)
+        modeltest = tests.StandardModelTest(model)
+
+        modeltest.test_all(skip_output_tests=True)
+
+    def test_optimisations(self):
+        model = pybamm.lead_acid.CompositeCapacitance()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known)
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/integration/test_models/test_lead_acid/test_loqs.py b/tests/integration/test_models/test_lead_acid/test_loqs.py
new file mode 100644
index 000000000..1666e2c0d
--- /dev/null
+++ b/tests/integration/test_models/test_lead_acid/test_loqs.py
@@ -0,0 +1,50 @@
+#
+# Tests for the lead-acid LOQS model
+#
+import pybamm
+import tests
+
+import unittest
+import numpy as np
+
+
+class TestLeadAcidLOQS(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.lead_acid.LOQS()
+        modeltest = tests.StandardModelTest(model)
+        modeltest.test_all()
+
+    def test_optimisations(self):
+        model = pybamm.lead_acid.LOQS()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known)
+
+    def test_charge(self):
+        model = pybamm.lead_acid.LOQS()
+        parameter_values = model.default_parameter_values
+        parameter_values.update({"Typical current [A]": -1})
+        modeltest = tests.StandardModelTest(model, parameter_values=parameter_values)
+        modeltest.test_all()
+
+    def test_zero_current(self):
+        model = pybamm.lead_acid.LOQS()
+        parameter_values = model.default_parameter_values
+        parameter_values.update({"Typical current [A]": 0})
+        modeltest = tests.StandardModelTest(model, parameter_values=parameter_values)
+        modeltest.test_all()
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/integration/test_models/test_lead_acid/test_loqs_capacitance.py b/tests/integration/test_models/test_lead_acid/test_loqs_capacitance.py
new file mode 100644
index 000000000..10638cc85
--- /dev/null
+++ b/tests/integration/test_models/test_lead_acid/test_loqs_capacitance.py
@@ -0,0 +1,45 @@
+#
+# Tests for the lead-acid LOQS model
+#
+import pybamm
+from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
+import tests
+
+import unittest
+import numpy as np
+
+
+class TestLeadAcidLOQSCapacitance(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.lead_acid.LOQSCapacitance()
+        modeltest = tests.StandardModelTest(model)
+
+        modeltest.test_all()
+
+    @unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
+    def test_basic_processing_no_capacitance(self):
+        model = pybamm.lead_acid.LOQSCapacitance(use_capacitance=False)
+        modeltest = tests.StandardModelTest(model)
+
+        modeltest.test_all()
+
+    def test_optimisations(self):
+        model = pybamm.lead_acid.LOQSCapacitance()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified, decimal=5)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known, decimal=5)
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/integration/test_models/test_lead_acid/test_newman_tiedemann.py b/tests/integration/test_models/test_lead_acid/test_newman_tiedemann.py
new file mode 100644
index 000000000..fd42ef3e1
--- /dev/null
+++ b/tests/integration/test_models/test_lead_acid/test_newman_tiedemann.py
@@ -0,0 +1,41 @@
+#
+# Tests for the lead-acid Newman-Tiedemann model
+#
+import pybamm
+from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
+import tests
+
+import unittest
+import numpy as np
+
+
+@unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
+class TestLeadAcidNewmanTiedemann(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.lead_acid.NewmanTiedemann()
+        # Make grid very coarse for quick test (note that r domain doesn't matter)
+        var = pybamm.standard_spatial_vars
+        var_pts = {var.x_n: 3, var.x_s: 3, var.x_p: 3}
+        modeltest = tests.StandardModelTest(model, var_pts=var_pts)
+        modeltest.test_all()
+
+    def test_optimisations(self):
+        model = pybamm.lead_acid.NewmanTiedemann()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known)
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/integration/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py b/tests/integration/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py
new file mode 100644
index 000000000..6082648ee
--- /dev/null
+++ b/tests/integration/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py
@@ -0,0 +1,44 @@
+#
+# Tests for the lead-acid Newman-Tiedemann capacitance model
+#
+import pybamm
+from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
+import tests
+
+import unittest
+import numpy as np
+
+
+class TestLeadAcidNewmanTiedemannCapacitance(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.lead_acid.NewmanTiedemannCapacitance()
+        modeltest = tests.StandardModelTest(model)
+        modeltest.test_all(skip_output_tests=True)
+
+    @unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
+    def test_basic_processing_no_capacitance(self):
+        model = pybamm.lead_acid.NewmanTiedemannCapacitance(use_capacitance=False)
+        modeltest = tests.StandardModelTest(model)
+
+        modeltest.test_all(skip_output_tests=True)
+
+    def test_optimisations(self):
+        model = pybamm.lead_acid.NewmanTiedemannCapacitance()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified, decimal=5)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known, decimal=5)
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/convergence/test_spatial_methods/__init__.py b/tests/integration/test_models/test_lithium_ion/__init__.py
similarity index 100%
rename from tests/convergence/test_spatial_methods/__init__.py
rename to tests/integration/test_models/test_lithium_ion/__init__.py
diff --git a/tests/integration/test_models/test_lithium_ion/test_lithium_ion_dfn.py b/tests/integration/test_models/test_lithium_ion/test_lithium_ion_dfn.py
new file mode 100644
index 000000000..7244d211c
--- /dev/null
+++ b/tests/integration/test_models/test_lithium_ion/test_lithium_ion_dfn.py
@@ -0,0 +1,40 @@
+#
+# Tests for the lithium-ion DFN model
+#
+import pybamm
+from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
+import tests
+
+import numpy as np
+import unittest
+
+
+@unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
+class TestDFN(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.lithium_ion.DFN()
+        var = pybamm.standard_spatial_vars
+        var_pts = {var.x_n: 10, var.x_s: 10, var.x_p: 10, var.r_n: 10, var.r_p: 10}
+        modeltest = tests.StandardModelTest(model, var_pts=var_pts)
+        modeltest.test_all()
+
+    def test_optimisations(self):
+        model = pybamm.lithium_ion.DFN()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known)
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/integration/test_models/test_lithium_ion/test_lithium_ion_spm.py b/tests/integration/test_models/test_lithium_ion/test_lithium_ion_spm.py
new file mode 100644
index 000000000..5ab404e2d
--- /dev/null
+++ b/tests/integration/test_models/test_lithium_ion/test_lithium_ion_spm.py
@@ -0,0 +1,49 @@
+#
+# Tests for the lithium-ion SPM model
+#
+import pybamm
+import tests
+import numpy as np
+import unittest
+
+
+class TestSPM(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.lithium_ion.SPM()
+        modeltest = tests.StandardModelTest(model)
+        modeltest.test_all()
+
+    def test_optimisations(self):
+        model = pybamm.lithium_ion.SPM()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known)
+
+    def test_charge(self):
+        model = pybamm.lithium_ion.SPM()
+        parameter_values = model.default_parameter_values
+        parameter_values.update({"Typical current [A]": -1})
+        modeltest = tests.StandardModelTest(model, parameter_values=parameter_values)
+        modeltest.test_all()
+
+    def test_zero_current(self):
+        model = pybamm.lithium_ion.SPM()
+        parameter_values = model.default_parameter_values
+        parameter_values.update({"Typical current [A]": 0})
+        modeltest = tests.StandardModelTest(model, parameter_values=parameter_values)
+        modeltest.test_all()
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/integration/test_models/test_lithium_ion/test_lithium_ion_spme.py b/tests/integration/test_models/test_lithium_ion/test_lithium_ion_spme.py
new file mode 100644
index 000000000..7e207f7d3
--- /dev/null
+++ b/tests/integration/test_models/test_lithium_ion/test_lithium_ion_spme.py
@@ -0,0 +1,36 @@
+#
+# Tests for the lithium-ion SPMe model
+#
+import pybamm
+import tests
+
+import numpy as np
+import unittest
+
+
+class TestSPMe(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.lithium_ion.SPMe()
+        modeltest = tests.StandardModelTest(model)
+        modeltest.test_all()
+
+    def test_optimisations(self):
+        model = pybamm.lithium_ion.SPMe()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known)
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/convergence/test_models/test_reaction_diffusion.py b/tests/integration/test_models/test_reaction_diffusion.py
similarity index 73%
rename from tests/convergence/test_models/test_reaction_diffusion.py
rename to tests/integration/test_models/test_reaction_diffusion.py
index 70b08401f..9574b7807 100644
--- a/tests/convergence/test_models/test_reaction_diffusion.py
+++ b/tests/integration/test_models/test_reaction_diffusion.py
@@ -2,12 +2,31 @@
 # Tests for the Reaction diffusion model
 #
 import pybamm
+import tests
 
 import numpy as np
 import unittest
 
 
 class TestReactionDiffusionModel(unittest.TestCase):
+    def test_basic_processing(self):
+        model = pybamm.ReactionDiffusionModel()
+
+        modeltest = tests.StandardModelTest(model)
+        modeltest.test_all(skip_output_tests=True)
+
+    def test_optimisations(self):
+        model = pybamm.ReactionDiffusionModel()
+        optimtest = tests.OptimisationsTest(model)
+
+        original = optimtest.evaluate_model()
+        simplified = optimtest.evaluate_model(simplify=True)
+        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
+        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
+        np.testing.assert_array_almost_equal(original, simplified)
+        np.testing.assert_array_almost_equal(original, using_known_evals)
+        np.testing.assert_array_almost_equal(original, simp_and_known)
+
     def test_convergence(self):
         # Convergence of c at x=0.5
         model = pybamm.ReactionDiffusionModel()
diff --git a/tests/unit/test_models/test_submodels/__init__.py b/tests/integration/test_models/test_submodels/__init__.py
similarity index 100%
rename from tests/unit/test_models/test_submodels/__init__.py
rename to tests/integration/test_models/test_submodels/__init__.py
diff --git a/tests/unit/test_models/test_submodels/test_electrode.py b/tests/integration/test_models/test_submodels/test_electrode.py
similarity index 100%
rename from tests/unit/test_models/test_submodels/test_electrode.py
rename to tests/integration/test_models/test_submodels/test_electrode.py
diff --git a/tests/unit/test_models/test_submodels/test_electrolyte_current.py b/tests/integration/test_models/test_submodels/test_electrolyte_current.py
similarity index 100%
rename from tests/unit/test_models/test_submodels/test_electrolyte_current.py
rename to tests/integration/test_models/test_submodels/test_electrolyte_current.py
diff --git a/tests/unit/test_models/test_submodels/test_electrolyte_diffusion.py b/tests/integration/test_models/test_submodels/test_electrolyte_diffusion.py
similarity index 100%
rename from tests/unit/test_models/test_submodels/test_electrolyte_diffusion.py
rename to tests/integration/test_models/test_submodels/test_electrolyte_diffusion.py
diff --git a/tests/unit/test_models/test_submodels/test_interface.py b/tests/integration/test_models/test_submodels/test_interface.py
similarity index 100%
rename from tests/unit/test_models/test_submodels/test_interface.py
rename to tests/integration/test_models/test_submodels/test_interface.py
diff --git a/tests/unit/test_models/test_submodels/test_particle.py b/tests/integration/test_models/test_submodels/test_particle.py
similarity index 100%
rename from tests/unit/test_models/test_submodels/test_particle.py
rename to tests/integration/test_models/test_submodels/test_particle.py
diff --git a/tests/integration/test_quick_plot.py b/tests/integration/test_quick_plot.py
new file mode 100644
index 000000000..7d2b19d2d
--- /dev/null
+++ b/tests/integration/test_quick_plot.py
@@ -0,0 +1,99 @@
+import pybamm
+import unittest
+import numpy as np
+
+
+class TestQuickPlot(unittest.TestCase):
+    """
+    Tests that QuickPlot is created correctly
+    """
+
+    def test_plot_lithium_ion(self):
+        spm = pybamm.lithium_ion.SPM()
+        spme = pybamm.lithium_ion.SPMe()
+        geometry = spm.default_geometry
+        param = spm.default_parameter_values
+        param.process_model(spm)
+        param.process_model(spme)
+        param.process_geometry(geometry)
+        mesh = pybamm.Mesh(geometry, spme.default_submesh_types, spme.default_var_pts)
+        disc_spm = pybamm.Discretisation(mesh, spm.default_spatial_methods)
+        disc_spme = pybamm.Discretisation(mesh, spme.default_spatial_methods)
+        disc_spm.process_model(spm)
+        disc_spme.process_model(spme)
+        solver_spm = spm.default_solver
+        solver_spme = spme.default_solver
+        t_eval = np.linspace(0, 2, 100)
+        solver_spm.solve(spm, t_eval)
+        solver_spme.solve(spme, t_eval)
+        quick_plot = pybamm.QuickPlot([spm, spme], mesh, [solver_spm, solver_spme])
+        quick_plot.plot(0)
+
+        # update the axis
+        new_axis = [0, 0.5, 0, 1]
+        quick_plot.axis.update({"Electrolyte concentration": new_axis})
+        self.assertEqual(quick_plot.axis["Electrolyte concentration"], new_axis)
+
+        # and now reset them
+        quick_plot.reset_axis()
+        self.assertNotEqual(quick_plot.axis["Electrolyte concentration"], new_axis)
+
+        # check dynamic plot loads
+        quick_plot.dynamic_plot(testing=True)
+
+        quick_plot.update(0.01)
+
+        # Update parameters, solve, plot again
+        param.update({"Typical current [A]": 0})
+        param.update_model(spm, disc_spm)
+        solver_spm.solve(spm, t_eval)
+        quick_plot = pybamm.QuickPlot(spm, mesh, solver_spm)
+        quick_plot.plot(0)
+
+        # Test with different output variables
+        output_vars = [
+            "Negative particle surface concentration",
+            "Electrolyte concentration",
+            "Positive particle surface concentration",
+        ]
+        quick_plot = pybamm.QuickPlot(spm, mesh, solver_spm, output_vars)
+        self.assertEqual(len(quick_plot.axis), 3)
+        quick_plot.plot(0)
+
+        # update the axis
+        new_axis = [0, 0.5, 0, 1]
+        quick_plot.axis.update({"Electrolyte concentration": new_axis})
+        self.assertEqual(quick_plot.axis["Electrolyte concentration"], new_axis)
+
+        # and now reset them
+        quick_plot.reset_axis()
+        self.assertNotEqual(quick_plot.axis["Electrolyte concentration"], new_axis)
+
+        # check dynamic plot loads
+        quick_plot.dynamic_plot(testing=True)
+
+        quick_plot.update(0.01)
+
+    def test_plot_lead_acid(self):
+        loqs = pybamm.lead_acid.LOQS()
+        geometry = loqs.default_geometry
+        param = loqs.default_parameter_values
+        param.process_model(loqs)
+        param.process_geometry(geometry)
+        mesh = pybamm.Mesh(geometry, loqs.default_submesh_types, loqs.default_var_pts)
+        disc_loqs = pybamm.Discretisation(mesh, loqs.default_spatial_methods)
+        disc_loqs.process_model(loqs)
+        t_eval = np.linspace(0, 1, 100)
+        solver_loqs = loqs.default_solver
+        solver_loqs.solve(loqs, t_eval)
+
+        pybamm.QuickPlot(loqs, mesh, solver_loqs)
+
+
+if __name__ == "__main__":
+    print("Add -v for more debug output")
+    import sys
+
+    if "-v" in sys.argv:
+        debug = True
+    unittest.main()
diff --git a/tests/integration/test_spatial_methods/__init__.py b/tests/integration/test_spatial_methods/__init__.py
new file mode 100644
index 000000000..e69de29bb
diff --git a/tests/convergence/test_spatial_methods/test_finite_volume.py b/tests/integration/test_spatial_methods/test_finite_volume.py
similarity index 100%
rename from tests/convergence/test_spatial_methods/test_finite_volume.py
rename to tests/integration/test_spatial_methods/test_finite_volume.py
diff --git a/tests/unit/test_models/test_lead_acid/test_composite.py b/tests/unit/test_models/test_lead_acid/test_composite.py
index d7c3f1c54..e88aa9eb2 100644
--- a/tests/unit/test_models/test_lead_acid/test_composite.py
+++ b/tests/unit/test_models/test_lead_acid/test_composite.py
@@ -2,29 +2,13 @@
 # Tests for the lead-acid composite model
 #
 import pybamm
-import tests
-
 import unittest
-import numpy as np
 
 
 class TestLeadAcidComposite(unittest.TestCase):
-    def test_basic_processing(self):
-        model = pybamm.lead_acid.Composite()
-        modeltest = tests.StandardModelTest(model)
-        modeltest.test_all(skip_output_tests=True)
-
-    def test_optimisations(self):
+    def test_well_posed(self):
         model = pybamm.lead_acid.Composite()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known)
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_models/test_lead_acid/test_composite_capacitance.py b/tests/unit/test_models/test_lead_acid/test_composite_capacitance.py
index a79e0f6b6..318b5cccf 100644
--- a/tests/unit/test_models/test_lead_acid/test_composite_capacitance.py
+++ b/tests/unit/test_models/test_lead_acid/test_composite_capacitance.py
@@ -2,37 +2,13 @@
 # Tests for the lead-acid composite model
 #
 import pybamm
-from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
-import tests
-
 import unittest
-import numpy as np
 
 
 class TestLeadAcidCompositeCapacitance(unittest.TestCase):
-    def test_basic_processing(self):
-        model = pybamm.lead_acid.CompositeCapacitance()
-        modeltest = tests.StandardModelTest(model)
-        modeltest.test_all(skip_output_tests=True)
-
-    @unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
-    def test_basic_processing_no_capacitance(self):
-        model = pybamm.lead_acid.CompositeCapacitance(use_capacitance=False)
-        modeltest = tests.StandardModelTest(model)
-
-        modeltest.test_all(skip_output_tests=True)
-
-    def test_optimisations(self):
+    def test_well_posed(self):
         model = pybamm.lead_acid.CompositeCapacitance()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known)
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_models/test_lead_acid/test_loqs.py b/tests/unit/test_models/test_lead_acid/test_loqs.py
index 1666e2c0d..07b6f1abc 100644
--- a/tests/unit/test_models/test_lead_acid/test_loqs.py
+++ b/tests/unit/test_models/test_lead_acid/test_loqs.py
@@ -2,43 +2,13 @@
 # Tests for the lead-acid LOQS model
 #
 import pybamm
-import tests
-
 import unittest
-import numpy as np
 
 
 class TestLeadAcidLOQS(unittest.TestCase):
-    def test_basic_processing(self):
-        model = pybamm.lead_acid.LOQS()
-        modeltest = tests.StandardModelTest(model)
-        modeltest.test_all()
-
-    def test_optimisations(self):
-        model = pybamm.lead_acid.LOQS()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known)
-
-    def test_charge(self):
-        model = pybamm.lead_acid.LOQS()
-        parameter_values = model.default_parameter_values
-        parameter_values.update({"Typical current [A]": -1})
-        modeltest = tests.StandardModelTest(model, parameter_values=parameter_values)
-        modeltest.test_all()
-
-    def test_zero_current(self):
+    def test_well_posed(self):
         model = pybamm.lead_acid.LOQS()
-        parameter_values = model.default_parameter_values
-        parameter_values.update({"Typical current [A]": 0})
-        modeltest = tests.StandardModelTest(model, parameter_values=parameter_values)
-        modeltest.test_all()
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_models/test_lead_acid/test_loqs_capacitance.py b/tests/unit/test_models/test_lead_acid/test_loqs_capacitance.py
index 10638cc85..d19ee0bdd 100644
--- a/tests/unit/test_models/test_lead_acid/test_loqs_capacitance.py
+++ b/tests/unit/test_models/test_lead_acid/test_loqs_capacitance.py
@@ -2,38 +2,13 @@
 # Tests for the lead-acid LOQS model
 #
 import pybamm
-from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
-import tests
-
 import unittest
-import numpy as np
 
 
 class TestLeadAcidLOQSCapacitance(unittest.TestCase):
-    def test_basic_processing(self):
+    def test_well_posed(self):
         model = pybamm.lead_acid.LOQSCapacitance()
-        modeltest = tests.StandardModelTest(model)
-
-        modeltest.test_all()
-
-    @unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
-    def test_basic_processing_no_capacitance(self):
-        model = pybamm.lead_acid.LOQSCapacitance(use_capacitance=False)
-        modeltest = tests.StandardModelTest(model)
-
-        modeltest.test_all()
-
-    def test_optimisations(self):
-        model = pybamm.lead_acid.LOQSCapacitance()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified, decimal=5)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known, decimal=5)
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_models/test_lead_acid/test_newman_tiedemann.py b/tests/unit/test_models/test_lead_acid/test_newman_tiedemann.py
index fd42ef3e1..a30d77bd4 100644
--- a/tests/unit/test_models/test_lead_acid/test_newman_tiedemann.py
+++ b/tests/unit/test_models/test_lead_acid/test_newman_tiedemann.py
@@ -2,34 +2,13 @@
 # Tests for the lead-acid Newman-Tiedemann model
 #
 import pybamm
-from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
-import tests
-
 import unittest
-import numpy as np
 
 
-@unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
 class TestLeadAcidNewmanTiedemann(unittest.TestCase):
-    def test_basic_processing(self):
-        model = pybamm.lead_acid.NewmanTiedemann()
-        # Make grid very coarse for quick test (note that r domain doesn't matter)
-        var = pybamm.standard_spatial_vars
-        var_pts = {var.x_n: 3, var.x_s: 3, var.x_p: 3}
-        modeltest = tests.StandardModelTest(model, var_pts=var_pts)
-        modeltest.test_all()
-
-    def test_optimisations(self):
+    def test_well_posed(self):
         model = pybamm.lead_acid.NewmanTiedemann()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known)
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py b/tests/unit/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py
index 6082648ee..55a462360 100644
--- a/tests/unit/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py
+++ b/tests/unit/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py
@@ -2,37 +2,13 @@
 # Tests for the lead-acid Newman-Tiedemann capacitance model
 #
 import pybamm
-from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
-import tests
-
 import unittest
-import numpy as np
 
 
 class TestLeadAcidNewmanTiedemannCapacitance(unittest.TestCase):
-    def test_basic_processing(self):
-        model = pybamm.lead_acid.NewmanTiedemannCapacitance()
-        modeltest = tests.StandardModelTest(model)
-        modeltest.test_all(skip_output_tests=True)
-
-    @unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
-    def test_basic_processing_no_capacitance(self):
-        model = pybamm.lead_acid.NewmanTiedemannCapacitance(use_capacitance=False)
-        modeltest = tests.StandardModelTest(model)
-
-        modeltest.test_all(skip_output_tests=True)
-
-    def test_optimisations(self):
+    def test_well_posed(self):
         model = pybamm.lead_acid.NewmanTiedemannCapacitance()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified, decimal=5)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known, decimal=5)
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_models/test_lithium_ion/test_lithium_ion_dfn.py b/tests/unit/test_models/test_lithium_ion/test_lithium_ion_dfn.py
index 7244d211c..862bf9245 100644
--- a/tests/unit/test_models/test_lithium_ion/test_lithium_ion_dfn.py
+++ b/tests/unit/test_models/test_lithium_ion/test_lithium_ion_dfn.py
@@ -2,33 +2,13 @@
 # Tests for the lithium-ion DFN model
 #
 import pybamm
-from pybamm.solvers.scikits_ode_solver import scikits_odes_spec
-import tests
-
-import numpy as np
 import unittest
 
 
-@unittest.skipIf(scikits_odes_spec is None, "scikits.odes not installed")
 class TestDFN(unittest.TestCase):
-    def test_basic_processing(self):
-        model = pybamm.lithium_ion.DFN()
-        var = pybamm.standard_spatial_vars
-        var_pts = {var.x_n: 10, var.x_s: 10, var.x_p: 10, var.r_n: 10, var.r_p: 10}
-        modeltest = tests.StandardModelTest(model, var_pts=var_pts)
-        modeltest.test_all()
-
-    def test_optimisations(self):
+    def test_well_posed(self):
         model = pybamm.lithium_ion.DFN()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known)
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_models/test_lithium_ion/test_lithium_ion_spm.py b/tests/unit/test_models/test_lithium_ion/test_lithium_ion_spm.py
index 5ab404e2d..951e93c93 100644
--- a/tests/unit/test_models/test_lithium_ion/test_lithium_ion_spm.py
+++ b/tests/unit/test_models/test_lithium_ion/test_lithium_ion_spm.py
@@ -2,42 +2,13 @@
 # Tests for the lithium-ion SPM model
 #
 import pybamm
-import tests
-import numpy as np
 import unittest
 
 
 class TestSPM(unittest.TestCase):
-    def test_basic_processing(self):
+    def test_well_posed(self):
         model = pybamm.lithium_ion.SPM()
-        modeltest = tests.StandardModelTest(model)
-        modeltest.test_all()
-
-    def test_optimisations(self):
-        model = pybamm.lithium_ion.SPM()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known)
-
-    def test_charge(self):
-        model = pybamm.lithium_ion.SPM()
-        parameter_values = model.default_parameter_values
-        parameter_values.update({"Typical current [A]": -1})
-        modeltest = tests.StandardModelTest(model, parameter_values=parameter_values)
-        modeltest.test_all()
-
-    def test_zero_current(self):
-        model = pybamm.lithium_ion.SPM()
-        parameter_values = model.default_parameter_values
-        parameter_values.update({"Typical current [A]": 0})
-        modeltest = tests.StandardModelTest(model, parameter_values=parameter_values)
-        modeltest.test_all()
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_models/test_lithium_ion/test_lithium_ion_spme.py b/tests/unit/test_models/test_lithium_ion/test_lithium_ion_spme.py
index 7e207f7d3..9b2424ee2 100644
--- a/tests/unit/test_models/test_lithium_ion/test_lithium_ion_spme.py
+++ b/tests/unit/test_models/test_lithium_ion/test_lithium_ion_spme.py
@@ -2,29 +2,13 @@
 # Tests for the lithium-ion SPMe model
 #
 import pybamm
-import tests
-
-import numpy as np
 import unittest
 
 
 class TestSPMe(unittest.TestCase):
-    def test_basic_processing(self):
-        model = pybamm.lithium_ion.SPMe()
-        modeltest = tests.StandardModelTest(model)
-        modeltest.test_all()
-
-    def test_optimisations(self):
+    def test_well_posed(self):
         model = pybamm.lithium_ion.SPMe()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known)
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_models/test_reaction_diffusion.py b/tests/unit/test_models/test_reaction_diffusion.py
index a9786436a..a0922e200 100644
--- a/tests/unit/test_models/test_reaction_diffusion.py
+++ b/tests/unit/test_models/test_reaction_diffusion.py
@@ -2,30 +2,13 @@
 # Tests for the Reaction diffusion model
 #
 import pybamm
-import tests
-
-import numpy as np
 import unittest
 
 
 class TestReactionDiffusionModel(unittest.TestCase):
-    def test_basic_processing(self):
+    def test_well_posed(self):
         model = pybamm.ReactionDiffusionModel()
-
-        modeltest = tests.StandardModelTest(model)
-        modeltest.test_all(skip_output_tests=True)
-
-    def test_optimisations(self):
-        model = pybamm.ReactionDiffusionModel()
-        optimtest = tests.OptimisationsTest(model)
-
-        original = optimtest.evaluate_model()
-        simplified = optimtest.evaluate_model(simplify=True)
-        using_known_evals = optimtest.evaluate_model(use_known_evals=True)
-        simp_and_known = optimtest.evaluate_model(simplify=True, use_known_evals=True)
-        np.testing.assert_array_almost_equal(original, simplified)
-        np.testing.assert_array_almost_equal(original, using_known_evals)
-        np.testing.assert_array_almost_equal(original, simp_and_known)
+        model.check_well_posedness()
 
 
 if __name__ == "__main__":
diff --git a/tests/unit/test_quick_plot.py b/tests/unit/test_quick_plot.py
index b375f5ad0..56656bba7 100644
--- a/tests/unit/test_quick_plot.py
+++ b/tests/unit/test_quick_plot.py
@@ -4,91 +4,56 @@ import numpy as np
 
 
 class TestQuickPlot(unittest.TestCase):
-    """
-    Tests that QuickPlot is created correctly
-    """
-
-    def test_plot_lithium_ion(self):
-        spm = pybamm.lithium_ion.SPM()
-        spme = pybamm.lithium_ion.SPMe()
-        geometry = spm.default_geometry
-        param = spm.default_parameter_values
-        param.process_model(spm)
-        param.process_model(spme)
+    def test_simple_ode_model(self):
+        model = pybamm.SimpleODEModel()
+        geometry = model.default_geometry
+        param = model.default_parameter_values
+        param.process_model(model)
         param.process_geometry(geometry)
-        mesh = pybamm.Mesh(geometry, spme.default_submesh_types, spme.default_var_pts)
-        disc_spm = pybamm.Discretisation(mesh, spm.default_spatial_methods)
-        disc_spme = pybamm.Discretisation(mesh, spme.default_spatial_methods)
-        disc_spm.process_model(spm)
-        disc_spme.process_model(spme)
-        solver_spm = spm.default_solver
-        solver_spme = spme.default_solver
+        mesh = pybamm.Mesh(geometry, model.default_submesh_types, model.default_var_pts)
+        disc = pybamm.Discretisation(mesh, model.default_spatial_methods)
+        disc.process_model(model)
+        solver = model.default_solver
         t_eval = np.linspace(0, 2, 100)
-        solver_spm.solve(spm, t_eval)
-        solver_spme.solve(spme, t_eval)
-        quick_plot = pybamm.QuickPlot([spm, spme], mesh, [solver_spm, solver_spme])
+        solver.solve(model, t_eval)
+        quick_plot = pybamm.QuickPlot(model, mesh, solver)
         quick_plot.plot(0)
 
         # update the axis
         new_axis = [0, 0.5, 0, 1]
-        quick_plot.axis.update({"Electrolyte concentration": new_axis})
-        self.assertEqual(quick_plot.axis["Electrolyte concentration"], new_axis)
+        quick_plot.axis.update({"a": new_axis})
+        self.assertEqual(quick_plot.axis["a"], new_axis)
 
         # and now reset them
         quick_plot.reset_axis()
-        self.assertNotEqual(quick_plot.axis["Electrolyte concentration"], new_axis)
+        self.assertNotEqual(quick_plot.axis["a"], new_axis)
 
         # check dynamic plot loads
         quick_plot.dynamic_plot(testing=True)
 
         quick_plot.update(0.01)
 
-        # Update parameters, solve, plot again
-        param.update({"Typical current [A]": 0})
-        param.update_model(spm, disc_spm)
-        solver_spm.solve(spm, t_eval)
-        quick_plot = pybamm.QuickPlot(spm, mesh, solver_spm)
-        quick_plot.plot(0)
-
         # Test with different output variables
-        output_vars = [
-            "Negative particle surface concentration",
-            "Electrolyte concentration",
-            "Positive particle surface concentration",
-        ]
-        quick_plot = pybamm.QuickPlot(spm, mesh, solver_spm, output_vars)
-        self.assertEqual(len(quick_plot.axis), 3)
+        quick_plot = pybamm.QuickPlot(model, mesh, solver,
+                                      ["b broadcasted", "c broadcasted"])
+        self.assertEqual(len(quick_plot.axis), 2)
         quick_plot.plot(0)
 
         # update the axis
         new_axis = [0, 0.5, 0, 1]
-        quick_plot.axis.update({"Electrolyte concentration": new_axis})
-        self.assertEqual(quick_plot.axis["Electrolyte concentration"], new_axis)
+        var = "c broadcasted"
+        quick_plot.axis.update({var: new_axis})
+        self.assertEqual(quick_plot.axis[var], new_axis)
 
         # and now reset them
         quick_plot.reset_axis()
-        self.assertNotEqual(quick_plot.axis["Electrolyte concentration"], new_axis)
+        self.assertNotEqual(quick_plot.axis[var], new_axis)
 
         # check dynamic plot loads
         quick_plot.dynamic_plot(testing=True)
 
         quick_plot.update(0.01)
 
-    def test_plot_lead_acid(self):
-        loqs = pybamm.lead_acid.LOQS()
-        geometry = loqs.default_geometry
-        param = loqs.default_parameter_values
-        param.process_model(loqs)
-        param.process_geometry(geometry)
-        mesh = pybamm.Mesh(geometry, loqs.default_submesh_types, loqs.default_var_pts)
-        disc_loqs = pybamm.Discretisation(mesh, loqs.default_spatial_methods)
-        disc_loqs.process_model(loqs)
-        t_eval = np.linspace(0, 1, 100)
-        solver_loqs = loqs.default_solver
-        solver_loqs.solve(loqs, t_eval)
-
-        pybamm.QuickPlot(loqs, mesh, solver_loqs)
-
     def test_failure(self):
         with self.assertRaisesRegex(TypeError, "'models' must be"):
             pybamm.QuickPlot(1, None, None)

pip install -e .[dev,docs]
parse_log_pytest
pytest
pytest
3.6
pytest --no-header -rA --tb=line --color=no -p no:cacheprovider -W ignore::DeprecationWarning
alabaster==0.7.13
anyio==3.6.2
anytree==2.8.0
argon2-cffi==21.3.0
argon2-cffi-bindings==21.2.0
async-generator==1.10
attrs @ file:///opt/conda/conda-bld/attrs_1642510447205/work
autograd==1.6.2
Babel==2.11.0
backcall==0.2.0
bleach==4.1.0
certifi==2021.5.30
cffi==1.15.1
charset-normalizer==2.0.12
comm==0.1.4
contextvars==2.4
cycler==0.11.0
dataclasses==0.8
decorator==5.1.1
defusedxml==0.7.1
docutils==0.17.1
entrypoints==0.4
flake8==5.0.4
future==1.0.0
guzzle-sphinx-theme==0.7.11
idna==3.10
imagesize==1.4.1
immutables==0.19
importlib-metadata==4.2.0
iniconfig @ file:///home/linux1/recipes/ci/iniconfig_1610983019677/work
ipykernel==5.5.6
ipython==7.16.3
ipython-genutils==0.2.0
ipywidgets==7.8.5
jedi==0.17.2
Jinja2==3.0.3
json5==0.9.16
jsonschema==3.2.0
jupyter==1.1.1
jupyter-client==7.1.2
jupyter-console==6.4.3
jupyter-core==4.9.2
jupyter-server==1.13.1
jupyterlab==3.2.9
jupyterlab-pygments==0.1.2
jupyterlab-server==2.10.3
jupyterlab_widgets==1.1.11
kiwisolver==1.3.1
MarkupSafe==2.0.1
matplotlib==3.3.4
mccabe==0.7.0
mistune==0.8.4
more-itertools @ file:///tmp/build/80754af9/more-itertools_1637733554872/work
nbclassic==0.3.5
nbclient==0.5.9
nbconvert==6.0.7
nbformat==5.1.3
nest-asyncio==1.6.0
notebook==6.4.10
numpy==1.19.5
packaging @ file:///tmp/build/80754af9/packaging_1637314298585/work
pandas==1.1.5
pandocfilters==1.5.1
parso==0.7.1
pexpect==4.9.0
pickleshare==0.7.5
Pillow==8.4.0
pluggy @ file:///tmp/build/80754af9/pluggy_1615976315926/work
prometheus-client==0.17.1
prompt-toolkit==3.0.36
ptyprocess==0.7.0
py @ file:///opt/conda/conda-bld/py_1644396412707/work
-e git+https://github.com/pybamm-team/PyBaMM.git@dea0fbdf08b6864355a6f08cb0df7bf12b0c21f9#egg=pybamm
pycodestyle==2.9.1
pycparser==2.21
pyflakes==2.5.0
Pygments==2.14.0
pyparsing @ file:///tmp/build/80754af9/pyparsing_1635766073266/work
pyrsistent==0.18.0
pytest==6.2.4
python-dateutil==2.9.0.post0
pytz==2025.2
pyzmq==25.1.2
requests==2.27.1
scipy==1.5.4
Send2Trash==1.8.3
six==1.17.0
sniffio==1.2.0
snowballstemmer==2.2.0
Sphinx==4.3.2
sphinxcontrib-applehelp==1.0.2
sphinxcontrib-devhelp==1.0.2
sphinxcontrib-htmlhelp==2.0.0
sphinxcontrib-jsmath==1.0.1
sphinxcontrib-qthelp==1.0.3
sphinxcontrib-serializinghtml==1.1.5
terminado==0.12.1
testpath==0.6.0
toml @ file:///tmp/build/80754af9/toml_1616166611790/work
tornado==6.1
traitlets==4.3.3
typing_extensions @ file:///opt/conda/conda-bld/typing_extensions_1647553014482/work
urllib3==1.26.20
wcwidth==0.2.13
webencodings==0.5.1
websocket-client==1.3.1
widgetsnbextension==3.6.10
zipp @ file:///tmp/build/80754af9/zipp_1633618647012/work

name: PyBaMM
channels:
  - defaults
  - https://repo.anaconda.com/pkgs/main
  - https://repo.anaconda.com/pkgs/r
  - conda-forge
dependencies:
  - _libgcc_mutex=0.1=main
  - _openmp_mutex=5.1=1_gnu
  - attrs=21.4.0=pyhd3eb1b0_0
  - ca-certificates=2025.2.25=h06a4308_0
  - certifi=2021.5.30=py36h06a4308_0
  - importlib_metadata=4.8.1=hd3eb1b0_0
  - iniconfig=1.1.1=pyhd3eb1b0_0
  - ld_impl_linux-64=2.40=h12ee557_0
  - libffi=3.3=he6710b0_2
  - libgcc-ng=11.2.0=h1234567_1
  - libgomp=11.2.0=h1234567_1
  - libstdcxx-ng=11.2.0=h1234567_1
  - more-itertools=8.12.0=pyhd3eb1b0_0
  - ncurses=6.4=h6a678d5_0
  - openssl=1.1.1w=h7f8727e_0
  - packaging=21.3=pyhd3eb1b0_0
  - pip=21.2.2=py36h06a4308_0
  - pluggy=0.13.1=py36h06a4308_0
  - py=1.11.0=pyhd3eb1b0_0
  - pyparsing=3.0.4=pyhd3eb1b0_0
  - pytest=6.2.4=py36h06a4308_2
  - python=3.6.13=h12debd9_1
  - readline=8.2=h5eee18b_0
  - setuptools=58.0.4=py36h06a4308_0
  - sqlite=3.45.3=h5eee18b_0
  - tk=8.6.14=h39e8969_0
  - toml=0.10.2=pyhd3eb1b0_0
  - typing_extensions=4.1.1=pyh06a4308_0
  - wheel=0.37.1=pyhd3eb1b0_0
  - xz=5.6.4=h5eee18b_1
  - zipp=3.6.0=pyhd3eb1b0_0
  - zlib=1.2.13=h5eee18b_1
  - pip:
      - alabaster==0.7.13
      - anyio==3.6.2
      - anytree==2.8.0
      - argon2-cffi==21.3.0
      - argon2-cffi-bindings==21.2.0
      - async-generator==1.10
      - autograd==1.6.2
      - babel==2.11.0
      - backcall==0.2.0
      - bleach==4.1.0
      - cffi==1.15.1
      - charset-normalizer==2.0.12
      - comm==0.1.4
      - contextvars==2.4
      - cycler==0.11.0
      - dataclasses==0.8
      - decorator==5.1.1
      - defusedxml==0.7.1
      - docutils==0.17.1
      - entrypoints==0.4
      - flake8==5.0.4
      - future==1.0.0
      - guzzle-sphinx-theme==0.7.11
      - idna==3.10
      - imagesize==1.4.1
      - immutables==0.19
      - importlib-metadata==4.2.0
      - ipykernel==5.5.6
      - ipython==7.16.3
      - ipython-genutils==0.2.0
      - ipywidgets==7.8.5
      - jedi==0.17.2
      - jinja2==3.0.3
      - json5==0.9.16
      - jsonschema==3.2.0
      - jupyter==1.1.1
      - jupyter-client==7.1.2
      - jupyter-console==6.4.3
      - jupyter-core==4.9.2
      - jupyter-server==1.13.1
      - jupyterlab==3.2.9
      - jupyterlab-pygments==0.1.2
      - jupyterlab-server==2.10.3
      - jupyterlab-widgets==1.1.11
      - kiwisolver==1.3.1
      - markupsafe==2.0.1
      - matplotlib==3.3.4
      - mccabe==0.7.0
      - mistune==0.8.4
      - nbclassic==0.3.5
      - nbclient==0.5.9
      - nbconvert==6.0.7
      - nbformat==5.1.3
      - nest-asyncio==1.6.0
      - notebook==6.4.10
      - numpy==1.19.5
      - pandas==1.1.5
      - pandocfilters==1.5.1
      - parso==0.7.1
      - pexpect==4.9.0
      - pickleshare==0.7.5
      - pillow==8.4.0
      - prometheus-client==0.17.1
      - prompt-toolkit==3.0.36
      - ptyprocess==0.7.0
      - pycodestyle==2.9.1
      - pycparser==2.21
      - pyflakes==2.5.0
      - pygments==2.14.0
      - pyrsistent==0.18.0
      - python-dateutil==2.9.0.post0
      - pytz==2025.2
      - pyzmq==25.1.2
      - requests==2.27.1
      - scipy==1.5.4
      - send2trash==1.8.3
      - six==1.17.0
      - sniffio==1.2.0
      - snowballstemmer==2.2.0
      - sphinx==4.3.2
      - sphinxcontrib-applehelp==1.0.2
      - sphinxcontrib-devhelp==1.0.2
      - sphinxcontrib-htmlhelp==2.0.0
      - sphinxcontrib-jsmath==1.0.1
      - sphinxcontrib-qthelp==1.0.3
      - sphinxcontrib-serializinghtml==1.1.5
      - terminado==0.12.1
      - testpath==0.6.0
      - tornado==6.1
      - traitlets==4.3.3
      - urllib3==1.26.20
      - wcwidth==0.2.13
      - webencodings==0.5.1
      - websocket-client==1.3.1
      - widgetsnbextension==3.6.10
prefix: /opt/conda/envs/PyBaMM

tests/unit/test_quick_plot.py::TestQuickPlot::test_simple_ode_model
tests/integration/test_models/test_lead_acid/test_composite_capacitance.py::TestLeadAcidCompositeCapacitance::test_basic_processing tests/integration/test_models/test_lead_acid/test_composite_capacitance.py::TestLeadAcidCompositeCapacitance::test_optimisations tests/integration/test_models/test_lead_acid/test_loqs_capacitance.py::TestLeadAcidLOQSCapacitance::test_basic_processing tests/integration/test_models/test_lead_acid/test_loqs_capacitance.py::TestLeadAcidLOQSCapacitance::test_optimisations tests/integration/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py::TestLeadAcidNewmanTiedemannCapacitance::test_basic_processing tests/integration/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py::TestLeadAcidNewmanTiedemannCapacitance::test_optimisations tests/integration/test_models/test_lead_acid/test_asymptotics_convergence.py::TestAsymptoticConvergence::test_leading_order_convergence tests/unit/test_models/test_lead_acid/test_composite_capacitance.py::TestLeadAcidCompositeCapacitance::test_well_posed tests/unit/test_models/test_lead_acid/test_loqs_capacitance.py::TestLeadAcidLOQSCapacitance::test_well_posed tests/unit/test_models/test_lead_acid/test_newman_tiedemann.py::TestLeadAcidNewmanTiedemann::test_well_posed tests/unit/test_models/test_lead_acid/test_newman_tiedemann_capacitance.py::TestLeadAcidNewmanTiedemannCapacitance::test_well_posed tests/unit/test_models/test_lithium_ion/test_lithium_ion_dfn.py::TestDFN::test_well_posed
tests/integration/test_models/test_reaction_diffusion.py::TestReactionDiffusionModel::test_basic_processing tests/integration/test_models/test_reaction_diffusion.py::TestReactionDiffusionModel::test_convergence tests/integration/test_models/test_reaction_diffusion.py::TestReactionDiffusionModel::test_optimisations tests/integration/test_models/test_lead_acid/test_composite.py::TestLeadAcidComposite::test_basic_processing tests/integration/test_models/test_lead_acid/test_composite.py::TestLeadAcidComposite::test_optimisations tests/integration/test_models/test_lead_acid/test_loqs.py::TestLeadAcidLOQS::test_basic_processing tests/integration/test_models/test_lead_acid/test_loqs.py::TestLeadAcidLOQS::test_charge tests/integration/test_models/test_lead_acid/test_loqs.py::TestLeadAcidLOQS::test_optimisations tests/integration/test_models/test_lead_acid/test_loqs.py::TestLeadAcidLOQS::test_zero_current tests/integration/test_models/test_lithium_ion/test_lithium_ion_spm.py::TestSPM::test_basic_processing tests/integration/test_models/test_lithium_ion/test_lithium_ion_spm.py::TestSPM::test_charge tests/integration/test_models/test_lithium_ion/test_lithium_ion_spm.py::TestSPM::test_optimisations tests/integration/test_models/test_lithium_ion/test_lithium_ion_spm.py::TestSPM::test_zero_current tests/integration/test_models/test_lithium_ion/test_lithium_ion_spme.py::TestSPMe::test_basic_processing tests/integration/test_models/test_lithium_ion/test_lithium_ion_spme.py::TestSPMe::test_optimisations tests/integration/test_models/test_submodels/test_electrolyte_diffusion.py::TestStefanMaxwellDiffusion::test_basic_processing tests/integration/test_models/test_submodels/test_electrolyte_diffusion.py::TestStefanMaxwellDiffusion::test_basic_processing_different_bcs tests/integration/test_models/test_submodels/test_electrolyte_diffusion.py::TestStefanMaxwellDiffusion::test_make_tree tests/integration/test_models/test_submodels/test_interface.py::TestHomogeneousReaction::test_discretisation tests/integration/test_models/test_submodels/test_interface.py::TestHomogeneousReaction::test_failure tests/integration/test_models/test_submodels/test_interface.py::TestHomogeneousReaction::test_set_parameters tests/integration/test_models/test_submodels/test_interface.py::TestHomogeneousReaction::test_simplify_constant_current tests/integration/test_models/test_submodels/test_interface.py::TestButlerVolmer::test_creation tests/integration/test_models/test_submodels/test_interface.py::TestButlerVolmer::test_discretisation tests/integration/test_models/test_submodels/test_interface.py::TestButlerVolmer::test_failure tests/integration/test_models/test_submodels/test_interface.py::TestButlerVolmer::test_set_parameters tests/integration/test_models/test_submodels/test_interface.py::TestExchangeCurrentDensity::test_creation_lead_acid tests/integration/test_models/test_submodels/test_interface.py::TestExchangeCurrentDensity::test_creation_lithium_ion tests/integration/test_models/test_submodels/test_interface.py::TestExchangeCurrentDensity::test_discretisation_lead_acid tests/integration/test_models/test_submodels/test_interface.py::TestExchangeCurrentDensity::test_discretisation_lithium_ion tests/integration/test_models/test_submodels/test_interface.py::TestExchangeCurrentDensity::test_failure tests/integration/test_models/test_submodels/test_interface.py::TestExchangeCurrentDensity::test_set_parameters_lead_acid tests/integration/test_models/test_submodels/test_interface.py::TestExchangeCurrentDensity::test_set_parameters_lithium_ion tests/integration/test_models/test_submodels/test_particle.py::TestStandardParticle::test_basic_processing tests/integration/test_models/test_submodels/test_particle.py::TestStandardParticle::test_make_tree tests/integration/test_quick_plot.py::TestQuickPlot::test_plot_lead_acid tests/integration/test_quick_plot.py::TestQuickPlot::test_plot_lithium_ion tests/integration/test_spatial_methods/test_finite_volume.py::TestFiniteVolumeConvergence::test_cartesian_div_convergence tests/integration/test_spatial_methods/test_finite_volume.py::TestFiniteVolumeConvergence::test_cartesian_spherical_grad_convergence tests/integration/test_spatial_methods/test_finite_volume.py::TestFiniteVolumeConvergence::test_p2d_spherical_convergence_quadratic tests/integration/test_spatial_methods/test_finite_volume.py::TestFiniteVolumeConvergence::test_p2d_with_x_dep_bcs_spherical_convergence tests/integration/test_spatial_methods/test_finite_volume.py::TestFiniteVolumeConvergence::test_spherical_div_convergence_linear tests/integration/test_spatial_methods/test_finite_volume.py::TestFiniteVolumeConvergence::test_spherical_div_convergence_quadratic tests/unit/test_models/test_lead_acid/test_composite.py::TestLeadAcidComposite::test_well_posed tests/unit/test_models/test_lead_acid/test_loqs.py::TestLeadAcidLOQS::test_well_posed tests/unit/test_models/test_lithium_ion/test_lithium_ion_spm.py::TestSPM::test_well_posed tests/unit/test_models/test_lithium_ion/test_lithium_ion_spme.py::TestSPMe::test_well_posed tests/unit/test_models/test_reaction_diffusion.py::TestReactionDiffusionModel::test_well_posed tests/unit/test_quick_plot.py::TestQuickPlot::test_failure
docs/tutorials/add-model.rst pybamm/quick_plot.py pybamm/models/simple_ode_model.py
docs/tutorials/add-model.rst pybamm/quick_plot.py pybamm/models/simple_ode_model.py