diff --git a/src/build_sequences.jl b/src/build_sequences.jl
index 8ae15d65c340943515cc6e45c636cf88a6e425df..13421ba542ed5459b716f9681de13fa954fa5bdc 100644
--- a/src/build_sequences.jl
+++ b/src/build_sequences.jl
@@ -140,6 +140,7 @@ function optimise_with_cost_func!(jump_model::Model, cost_func, n_attempts)
     for _ in num_variables(jump_model):number_equality_constraints(jump_model)
         @variable(jump_model)
     end
+    consistent_minimum = false
     for attempt in 1:n_attempts
         if attempt != 1
             new_values = rand(length(all_variables(jump_model)))
@@ -160,6 +161,9 @@ function optimise_with_cost_func!(jump_model::Model, cost_func, n_attempts)
             #println(solution_summary(jump_model))
             if termination_status(jump_model) in (LOCALLY_SOLVED, OPTIMAL)
                 nsuccess += 1
+                if isapprox(objective_value(jump_model), min_objective, rtol=1e-3)
+                    consistent_minimum = true
+                end
                 if objective_value(jump_model) < min_objective
                     min_objective = objective_value(jump_model)
                     min_values = copy(get_inner_state(jump_model))
@@ -170,11 +174,11 @@ function optimise_with_cost_func!(jump_model::Model, cost_func, n_attempts)
                 sample_error[termination_status(jump_model)] = solution_summary(jump_model)
             end
         end
-        if nsuccess > 2
+        if consistent_minimum
             break
         end
     end
-    if iszero(nsuccess)
+    if !consistent_minimum
         err_string = join(["$(String(Symbol(err))) (x$(sum([e == err for e in errors])))" for err in unique(errors)], ", ", ", and ")
         for msg in values(sample_error)
             println(msg)
diff --git a/src/components/gradient_waveforms/changing_gradient_blocks.jl b/src/components/gradient_waveforms/changing_gradient_blocks.jl
index f670fff3e5dfb65af46f0ed38e9530aafee8e7eb..80b029b7ba12c5c0f07bbc815206e320ba6aef5e 100644
--- a/src/components/gradient_waveforms/changing_gradient_blocks.jl
+++ b/src/components/gradient_waveforms/changing_gradient_blocks.jl
@@ -1,7 +1,7 @@
 module ChangingGradientBlocks
 import StaticArrays: SVector
 import Rotations: RotMatrix3
-import LinearAlgebra: I
+import LinearAlgebra: I, norm
 import ....Variables: @defvar, VariableType, variables, get_free_variable, adjust_internal
 import ...AbstractTypes: GradientWaveform
 
@@ -42,7 +42,14 @@ end
     slew_rate(cgb::ChangingGradient1D) = cgb.slew_rate .* cgb.orientation
     slew_rate(cgb::ChangingGradient3D) = cgb.slew_rate
     grad_end(cgb::ChangingGradient) = variables.grad_start(cgb) .+ variables.slew_rate(cgb) .* variables.duration(cgb)
-    gradient_strength(cgb::ChangingGradient) = max.(variables.grad_start(cgb), variables.grad_end(cgb))
+    gradient_strength_norm(cgb::ChangingGradient1D) = max(
+        abs(cgb.gradient_strength_start),
+        abs(cgb.gradient_strength_start + cgb.slew_rate * cgb.duration)
+    )
+    gradient_strength_norm(cgb::ChangingGradient3D) = max(
+        norm(cgb.grad_start),
+        norm(cgb.grad_end)
+    )
     qvec(cgb::ChangingGradient) = (variables.grad_start(cgb) .+ variables.grad_end(cgb)) .* (variables.duration(cgb) * π)
 
     gradient_strength(cgb::ChangingGradient, time::Number) = variables.slew_rate(cgb) .* time .+ variables.grad_start(cgb)
diff --git a/src/containers/building_blocks.jl b/src/containers/building_blocks.jl
index bac1a8205048f1b704aff00ec3f28879aa7b7d7d..0e18d00efcda77647e2f8252597951737a9a6a72 100644
--- a/src/containers/building_blocks.jl
+++ b/src/containers/building_blocks.jl
@@ -265,8 +265,9 @@ end
 
 function get_pulse(bb::BaseBuildingBlock, time::Number)
     for (key, component) in events(bb)
-        if component isa RFPulseComponent && (start_time(bb, key) <= time <= end_time(bb, key))
-            return (component, time - start_time(bb, key))
+        start = start_time(bb, key)
+        if component isa RFPulseComponent && (start <= time <= (start + variables.duration(component)))
+            return (component, time - start)
         end
     end
     return nothing
@@ -284,10 +285,16 @@ end
 
 
 function get_gradient(bb::BaseBuildingBlock, time::Number)
-    for (key, block) in waveform_sequence(bb)
-        if (start_time(bb, key) <= time <= end_time(bb, key)) || isapprox(time, end_time(bb, key), atol=1e-6)
-            return (block, time - start_time(bb, key))
+    current_time = 0.
+    if time < -1e-6
+        error("$bb does not define a gradient at negative times.")
+    end
+    for (_, block) in waveform_sequence(bb)
+        duration = block.duration
+        if (time - current_time) <= duration || isapprox(time - current_time, duration, atol=1e-6)
+            return (block, time - current_time)
         end
+        current_time = current_time + duration
     end
     error("$bb with duration $(variables.duration(bb)) does not define a gradient at time $time.")
 end
diff --git a/src/variables.jl b/src/variables.jl
index 9f6f0f1b8e716830361ec966172aa4ace88ed174..6973a69131b56baada62aadd02efd14999231c6e 100644
--- a/src/variables.jl
+++ b/src/variables.jl
@@ -163,6 +163,8 @@ Assigns getters to specific variables.
 """
 const getters = Dict{Symbol, Function}()
 
+const SkipGeneric = Ref{Bool}(false)
+
 """
     _get_variable(name, tried_names, args...; kwargs...)
 
@@ -172,14 +174,21 @@ The route through `tried_names` has already been attempted.
 
 This function returns the route to get to the value and the value itself.
 """
-function _get_variable(name::Symbol, tried_names::Set{Symbol}, args...; kwargs...)
-    if hasproperty(variables, name)
-        func = getproperty(variables, name)
-        if variable_defined_for(func, args...; kwargs...)
-            return Any[], func(args...; kwargs...)
+function _get_variable(name::Symbol, tried_names::Set{Symbol}, args...; _is_first_call=false, kwargs...)
+    if !(_is_first_call)
+        try
+            func = getproperty(variables, name)
+            if variable_defined_for(func, args...; kwargs...)
+                return Any[], func(args...; kwargs...)
+            end
+        catch e
+            if !(e isa UndefVarError)
+                rethrow()
+            end
         end
     end
 
+
     # alternative functions
     if name in keys(alternative_variables)
         for (new_name, converter, _) in alternative_variables[name]
@@ -240,8 +249,11 @@ function add_new_variable!(name::Symbol)
     @eval variables function $(name) end
     @eval variables $(Expr(:public, name))
     @eval function variables.$(name)(ab::AbstractBlock, args...; kwargs...) 
+        if :_is_first_call in keys(kwargs)
+            error("Variables function definitions cannot use the keyword `_is_first_call`")
+        end
         try
-            return _get_variable($(QuoteNode(name)), Set{Symbol}(), ab, args...; kwargs...)[2]
+            return _get_variable($(QuoteNode(name)), Set{Symbol}(), ab, args...; _is_first_call=true, kwargs...)[2]
         catch e
             if e isa InvalidRoute
                 string_name = String($(QuoteNode(name)))
diff --git a/test/test_sequences.jl b/test/test_sequences.jl
index b6f6102a6f6e5e39373743593b9c830bcb7ff3d6..c9e924d5d735dd4447458826d6ce3e3fad33aac4 100644
--- a/test/test_sequences.jl
+++ b/test/test_sequences.jl
@@ -59,7 +59,6 @@
             end
             @testset "Set diffusion time Δ" begin
                 seq = DiffusionSpinEcho(TE=80., Δ=70., qval=:max)
-                @show seq
                 @test all(isapprox.(variables.duration.(seq), [0., 0., 10., 30., 0., 30., 10., 0., 0., 0.], atol=1e-4, rtol=1e-4))
                 @test variables.Δ(seq) ≈ 70.
                 @test variables.TE(seq) ≈ 80.
@@ -67,7 +66,6 @@
                 @test 0.72 < variables.bval(seq) < 0.73
                 @test variables.readout_times(seq)[1] ≈ variables.TE(seq)
                 @test variables.rise_time(seq[:gradient]) ≈ min_rise_time rtol=1e-4
-                @show edge_times(seq)
                 @test all(isapprox.(edge_times(seq), [0., min_rise_time, 10. - min_rise_time, 10., 40, 70, 70 + min_rise_time, 80 - min_rise_time, 80.], atol=1e-4))
             end
             @testset "Set gradient duration" begin