diff --git a/lbmpy/creationfunctions.py b/lbmpy/creationfunctions.py
index 936ec0dd4ddd88c55655385b041552683a0c24e8..3e7474dc3732d1ab2341d6a19a6108bc2b6406e4 100644
--- a/lbmpy/creationfunctions.py
+++ b/lbmpy/creationfunctions.py
@@ -75,9 +75,8 @@ LES methods:
 
 Fluctuating LB:
 
-- ``fluctuating=(variance1, variance2, )``: enables fluctuating lattice Boltzmann by randomizing collision process.
-  Pass sequence of variances for each moment, or `True` to use symbolic variances
-
+- ``fluctuating``: enables fluctuating lattice Boltzmann by randomizing collision process.
+  Pass dictionary with parameters to  ``lbmpy.fluctuatinglb.add_fluctuations_to_collision_rule``
 
 
 Optimization Parameters
@@ -175,11 +174,12 @@ import sympy as sp
 
 import lbmpy.forcemodels as forcemodels
 from lbmpy.fieldaccess import (
-    AAEvenTimeStepAccessor, AAOddTimeStepAccessor, CollideOnlyInplaceAccessor, EsoTwistEvenTimeStepAccessor,
-    EsoTwistOddTimeStepAccessor, PdfFieldAccessor, PeriodicTwoFieldsAccessor, StreamPullTwoFieldsAccessor,
-    StreamPushTwoFieldsAccessor)
-from lbmpy.fluctuatinglb import fluctuation_correction, fluctuating_variance_equations
-from lbmpy.methods import create_mrt3, create_mrt_orthogonal, create_mrt_raw, create_srt, create_trt, create_trt_kbc
+    AAEvenTimeStepAccessor, AAOddTimeStepAccessor, CollideOnlyInplaceAccessor,
+    EsoTwistEvenTimeStepAccessor, EsoTwistOddTimeStepAccessor, PdfFieldAccessor,
+    PeriodicTwoFieldsAccessor, StreamPullTwoFieldsAccessor, StreamPushTwoFieldsAccessor)
+from lbmpy.fluctuatinglb import add_fluctuations_to_collision_rule, method_with_rescaled_equilibrium_values
+from lbmpy.methods import (
+    create_mrt3, create_mrt_orthogonal, create_mrt_raw, create_srt, create_trt, create_trt_kbc)
 from lbmpy.methods.creationfunctions import create_generic_mrt
 from lbmpy.methods.cumulantbased import CumulantBasedLbMethod
 from lbmpy.methods.entropic import add_entropy_condition, add_iterative_entropy_condition
@@ -193,8 +193,6 @@ from pystencils import Assignment, AssignmentCollection, create_kernel
 from pystencils.cache import disk_cache_no_fallback
 from pystencils.data_types import collate_types
 from pystencils.field import Field, get_layout_of_array
-from pystencils.rng import random_symbol
-from pystencils.simp.assignment_collection import SymbolGen
 from pystencils.stencil import have_same_entries
 
 
@@ -309,6 +307,9 @@ def create_lb_collision_rule(lb_method=None, optimization={}, **kwargs):
     if rho_in is not None and isinstance(rho_in, Field):
         rho_in = rho_in.center
 
+    if params['fluctuating']:
+        lb_method = method_with_rescaled_equilibrium_values(lb_method)
+
     if u_in is not None:
         density_rhs = sum(lb_method.pre_collision_pdf_symbols) if rho_in is None else rho_in
         eqs = [Assignment(cqc.zeroth_order_moment_symbol, density_rhs)]
@@ -323,25 +324,7 @@ def create_lb_collision_rule(lb_method=None, optimization={}, **kwargs):
     collision_rule = simplification(collision_rule)
 
     if params['fluctuating']:
-        variances = params["fluctuating"]
-        if params["fluctuating"] is True:
-            variances = [v for v, _ in zip(iter(SymbolGen("variance")), lb_method.moments)]
-
-        correction = fluctuation_correction(lb_method, random_symbol(collision_rule.subexpressions, dim=lb_method.dim),
-                                            variances)
-
-        for i, corr in enumerate(correction):
-            collision_rule.main_assignments[i] = Assignment(collision_rule.main_assignments[i].lhs,
-                                                            collision_rule.main_assignments[i].rhs + corr)
-
-        if params["temperature"] is not None:
-            temperature = sp.Symbol("temperature") if params["temperature"] is True else params["temperature"]
-            variance_equations = fluctuating_variance_equations(method=lb_method,
-                                                                temperature=temperature,
-                                                                c_s_sq=params["c_s_sq"],
-                                                                variances=variances)
-            collision_rule.subexpressions += variance_equations
-            collision_rule.topological_sort(sort_subexpressions=True, sort_main_assignments=False)
+        add_fluctuations_to_collision_rule(collision_rule, **params['fluctuating'])
 
     if params['entropic']:
         if params['smagorinsky']:
diff --git a/lbmpy/fieldaccess.py b/lbmpy/fieldaccess.py
index a82384968ec3a7802a7db0f607598211c8b736e6..571db5845ac328c6bdb10c185875baecab7f436f 100644
--- a/lbmpy/fieldaccess.py
+++ b/lbmpy/fieldaccess.py
@@ -9,6 +9,7 @@ from pystencils.stencil import inverse_direction
 
 __all__ = ['PdfFieldAccessor', 'CollideOnlyInplaceAccessor', 'StreamPullTwoFieldsAccessor',
            'AAEvenTimeStepAccessor', 'AAOddTimeStepAccessor',
+           'PeriodicTwoFieldsAccessor', 'StreamPushTwoFieldsAccessor',
            'EsoTwistEvenTimeStepAccessor', 'EsoTwistOddTimeStepAccessor',
            'visualize_pdf_field_accessor', 'visualize_field_mapping']
 
diff --git a/lbmpy/fluctuatinglb.py b/lbmpy/fluctuatinglb.py
index 076e063948c446657c59c7fe2d19005aecb3581b..caa7009983984bcce70e5f67671e99a31060ca99 100644
--- a/lbmpy/fluctuatinglb.py
+++ b/lbmpy/fluctuatinglb.py
@@ -2,41 +2,45 @@
 
 to generate a fluctuating LBM the equilibrium moment values have to be scaled and an additive (random)
 correction term is added to the collision rule
-
-
-Usage example:
-
-    >>> from lbmpy.session import *
-    >>> from pystencils.rng import random_symbol
-    >>> method = create_lb_method(stencil='D2Q9', method='MRT')
-    >>> rescaled_method = method_with_rescaled_equilibrium_values(method)
-    >>> cr = create_lb_collision_rule(lb_method=rescaled_method)
-    >>> correction = fluctuation_correction(rescaled_method,
-    ...                                     rng_generator=random_symbol(cr.subexpressions, dim=method.dim))
-    >>> for i, corr in enumerate(correction):
-    ...     cr.main_assignments[i] = ps.Assignment(cr.main_assignments[i].lhs,
-    ...                                            cr.main_assignments[i].rhs + corr)
-    >>>
-
 """
+import numpy as np
 import sympy as sp
 
 from lbmpy.moments import MOMENT_SYMBOLS
+from pystencils import Assignment, TypedSymbol
+from pystencils.rng import PhiloxFourFloats, random_symbol
 from pystencils.simp.assignment_collection import SymbolGen
-from pystencils import Assignment
 
 
-def fluctuating_variance_equations(method, temperature=sp.Symbol("fluctuating_temperature"),
-                                   c_s_sq=sp.Symbol("c_s") ** 2,
-                                   variances=SymbolGen("variance")):
+def add_fluctuations_to_collision_rule(collision_rule, temperature=None, variances=(),
+                                       block_offsets=(0, 0, 0), seed=TypedSymbol("seed", np.uint32),
+                                       rng_node=PhiloxFourFloats, c_s_sq=sp.Rational(1, 3)):
+    """"""
+    if not (temperature and not variances) or (temperature and variances):
+        raise ValueError("Fluctuating LBM: Pass either 'temperature' or 'variances'.")
+
+    method = collision_rule.method
+    if not variances:
+        variances = fluctuating_variance_from_temperature(method, temperature, c_s_sq)
+
+    rng_symbol_gen = random_symbol(collision_rule.subexpressions, seed,
+                                   rng_node=rng_node, dim=method.dim, offsets=block_offsets)
+    correction = fluctuation_correction(method, rng_symbol_gen, variances)
+
+    for i, corr in enumerate(correction):
+        collision_rule.main_assignments[i] = Assignment(collision_rule.main_assignments[i].lhs,
+                                                        collision_rule.main_assignments[i].rhs + corr)
+
+
+def fluctuating_variance_from_temperature(method, temperature, c_s_sq=sp.Symbol("c_s") ** 2):
     """Produces variance equations according to (3.54) in Schiller08"""
     normalization_factors = abs(method.moment_matrix) * sp.Matrix(method.weights)
-    relaxation_rates_sqr = [r ** 2 for r in method.relaxation_rates]
     density = method.zeroth_order_equilibrium_moment_symbol
+    if method.conserved_quantity_computation.zero_centered_pdfs:
+        density += 1
     mu = temperature * density / c_s_sq
-
-    return [Assignment(v, sp.sqrt(mu * norm * (1 - rr)))
-            for v, norm, rr in zip(iter(variances), normalization_factors, relaxation_rates_sqr)]
+    return [sp.sqrt(mu * norm * (1 - (1 - rr) ** 2))
+            for norm, rr in zip(normalization_factors, method.relaxation_rates)]
 
 
 def method_with_rescaled_equilibrium_values(base_method):
diff --git a/lbmpy/methods/conservedquantitycomputation.py b/lbmpy/methods/conservedquantitycomputation.py
index 180a2f6b170204322ec2984887d0485e99db9a97..d34939b7e89477ebe2b2f4f531978a9bc2acb184 100644
--- a/lbmpy/methods/conservedquantitycomputation.py
+++ b/lbmpy/methods/conservedquantitycomputation.py
@@ -243,10 +243,11 @@ def get_equations_for_zeroth_and_first_order_moment(stencil, symbolic_pdfs,
         \rho = \sum_{d \in S} f_d
         u_j = \sum_{d \in S} f_d u_jd
 
-    :param stencil: called :math:`S` above
-    :param symbolic_pdfs: called :math:`f` above
-    :param symbolic_zeroth_moment:  called :math:`\rho` above
-    :param symbolic_first_moments: called :math:`u` above
+    Args:
+        stencil: called :math:`S` above
+        symbolic_pdfs: called :math:`f` above
+        symbolic_zeroth_moment:  called :math:`\rho` above
+        symbolic_first_moments: called :math:`u` above
     """
     def filter_out_plus_terms(expr):
         result = 0
diff --git a/lbmpy_tests/test_fluctuation.py b/lbmpy_tests/test_fluctuation.py
index 88b01cad2b3b6b29237a39ab46748490d38b37b3..be886c280189da7fb460891501cf88322eed20c6 100644
--- a/lbmpy_tests/test_fluctuation.py
+++ b/lbmpy_tests/test_fluctuation.py
@@ -1,9 +1,13 @@
+import numpy as np
+
 from lbmpy.scenarios import create_channel
 
+
 def test_fluctuating_generation_pipeline():
     ch = create_channel((40, 10), method='mrt3', relaxation_rates=[1.5, 1, 1], force=1e-5,
-                        fluctuating=True,
-                        temperature=1e-9,
-                        kernel_params={'time_step': 1})
+                        fluctuating={'temperature': 1e-9},
+                        kernel_params={'time_step': 1, 'seed': 312},
+                        optimization={'cse_global': True})
 
     ch.run(10)
+    assert np.max(ch.velocity[:, :]) < 0.1