<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
	<channel>
		<title><![CDATA[SoliForum - 3D Printing Community — Help with Ramps 1.4 firmware]]></title>
		<link>https://www.soliforum.com/topic/13244/help-with-ramps-14-firmware/</link>
		<atom:link href="https://www.soliforum.com/feed/rss/topic/13244/" rel="self" type="application/rss+xml" />
		<description><![CDATA[The most recent posts in Help with Ramps 1.4 firmware.]]></description>
		<lastBuildDate>Thu, 31 Dec 2015 21:06:10 +0000</lastBuildDate>
		<generator>PunBB</generator>
		<item>
			<title><![CDATA[Re: Help with Ramps 1.4 firmware]]></title>
			<link>https://www.soliforum.com/post/112995/#p112995</link>
			<description><![CDATA[<p>Glad to help..</p>]]></description>
			<author><![CDATA[null@example.com (carl_m1968)]]></author>
			<pubDate>Thu, 31 Dec 2015 21:06:10 +0000</pubDate>
			<guid>https://www.soliforum.com/post/112995/#p112995</guid>
		</item>
		<item>
			<title><![CDATA[Re: Help with Ramps 1.4 firmware]]></title>
			<link>https://www.soliforum.com/post/112994/#p112994</link>
			<description><![CDATA[<p>I got it now. I had to removve // and add #define to save and compile.</p><p>Thank you very much Carl!</p>]]></description>
			<author><![CDATA[null@example.com (AZERATE)]]></author>
			<pubDate>Thu, 31 Dec 2015 21:02:02 +0000</pubDate>
			<guid>https://www.soliforum.com/post/112994/#p112994</guid>
		</item>
		<item>
			<title><![CDATA[Re: Help with Ramps 1.4 firmware]]></title>
			<link>https://www.soliforum.com/post/112992/#p112992</link>
			<description><![CDATA[<div class="quotebox"><cite>AZERATE wrote:</cite><blockquote><p>Downloaded. This is the windows error code I get.<br />&quot;The library u8glib-master cannot be used.</p><p>Library names must contain only basic letters and numbers.</p><p>(ASCII only and no spaces, and it cannot start with a number)&quot;</p></blockquote></div><br /><p>How are you trying to install it? </p><p>All I did was unpacked it then in Arduino selected add library. From there I pointed it to the root of the unpacked folder.</p>]]></description>
			<author><![CDATA[null@example.com (carl_m1968)]]></author>
			<pubDate>Thu, 31 Dec 2015 20:58:17 +0000</pubDate>
			<guid>https://www.soliforum.com/post/112992/#p112992</guid>
		</item>
		<item>
			<title><![CDATA[Re: Help with Ramps 1.4 firmware]]></title>
			<link>https://www.soliforum.com/post/112991/#p112991</link>
			<description><![CDATA[<p>Downloaded. This is the windows error code I get.<br />&quot;The library u8glib-master cannot be used.</p><p>Library names must contain only basic letters and numbers.</p><p>(ASCII only and no spaces, and it cannot start with a number)&quot;</p>]]></description>
			<author><![CDATA[null@example.com (AZERATE)]]></author>
			<pubDate>Thu, 31 Dec 2015 20:49:22 +0000</pubDate>
			<guid>https://www.soliforum.com/post/112991/#p112991</guid>
		</item>
		<item>
			<title><![CDATA[Re: Help with Ramps 1.4 firmware]]></title>
			<link>https://www.soliforum.com/post/112989/#p112989</link>
			<description><![CDATA[<p>All you should have to do is uncomment this line in your config.h tab.</p><br /><p>//#define REPRAP_DISCOUNT_SMART_CONTROLLER</p><p>so it looks like this.</p><p>#define REPRAP_DISCOUNT_SMART_CONTROLLER</p><p>This is all that is needed to activate a controller and as the config.h files says you also need to install the library for LCD support..</p><br /><p>// ==&gt; REMEMBER TO INSTALL U8glib to your ARDUINO library folder: <a href="http://code.google.com/p/u8glib/wiki/u8glib">http://code.google.com/p/u8glib/wiki/u8glib</a></p>]]></description>
			<author><![CDATA[null@example.com (carl_m1968)]]></author>
			<pubDate>Thu, 31 Dec 2015 19:44:41 +0000</pubDate>
			<guid>https://www.soliforum.com/post/112989/#p112989</guid>
		</item>
		<item>
			<title><![CDATA[Re: Help with Ramps 1.4 firmware]]></title>
			<link>https://www.soliforum.com/post/112988/#p112988</link>
			<description><![CDATA[<p>Also, I have no jumpers in place....figured I should point that out.</p>]]></description>
			<author><![CDATA[null@example.com (AZERATE)]]></author>
			<pubDate>Thu, 31 Dec 2015 19:32:13 +0000</pubDate>
			<guid>https://www.soliforum.com/post/112988/#p112988</guid>
		</item>
		<item>
			<title><![CDATA[Re: Help with Ramps 1.4 firmware]]></title>
			<link>https://www.soliforum.com/post/112987/#p112987</link>
			<description><![CDATA[<div class="codebox"><pre><code>#ifndef CONFIGURATION_H
#define CONFIGURATION_H

// This configuration file contains the basic settings.
// Advanced settings can be found in Configuration_adv.h
// BASIC SETTINGS: select your board type, temperature sensor type, axis scaling, and endstop configuration

//===========================================================================
//============================= DELTA Printer ===============================
//===========================================================================
// For a Delta printer rplace the configuration files wilth the files in the 
// example_configurations/delta directory.
// 

// User-specified version info of this build to display in [Pronterface, etc] terminal window during
// startup. Implementation of an idea by Prof Braino to inform user that any changes made to this
// build by the user have been successfully uploaded into firmware.
#define STRING_VERSION_CONFIG_H __DATE__ &quot; &quot; __TIME__ // build date and time
#define STRING_CONFIG_H_AUTHOR &quot;Adrian/Lawsy/Rincewind/Tealvince&quot; // Who made the changes.

// change to 3 for SD3 //{SD Patch}
#define SOLIDOODLE_VERSION 3 //{SD Patch}

// Enable support for either of the Z-Wobble Solutions
//#define ZWOBBLE_PATCH //{SD Patch} (+5528 Bytes)
//#define HYSTERESIS_PATCH //{SD Patch}(+1592 Bytes)

// SERIAL_PORT selects which serial port should be used for communication with the host.
// This allows the connection of wireless adapters (for instance) to non-default port pins.
// Serial port 0 is still used by the Arduino bootloader regardless of this setting.
#define SERIAL_PORT 0

// This determines the communication speed of the printer
// This determines the communication speed of the printer
#define BAUDRATE 250000

// This enables the serial port associated to the Bluetooth interface
//#define BTENABLED              // Enable BT interface on AT90USB devices


//// The following define selects which electronics board you have. Please choose the one that matches your setup
// 10 = Gen7 custom (Alfons3 Version) &quot;https://github.com/Alfons3/Generation_7_Electronics&quot;
// 11 = Gen7 v1.1, v1.2 = 11
// 12 = Gen7 v1.3
// 13 = Gen7 v1.4
// 20 = Sethi 3D_1 
// 3  = MEGA/RAMPS up to 1.2 = 3
// 33 = RAMPS 1.3 / 1.4 (Power outputs: Extruder, Fan, Bed)
// 34 = RAMPS 1.3 / 1.4 (Power outputs: Extruder0, Extruder1, Bed)
// 35 = RAMPS 1.3 / 1.4 (Power outputs: Extruder, Fan, Fan)
// 4  = Duemilanove w/ ATMega328P pin assignment
// 5  = Gen6
// 51 = Gen6 deluxe
// 6  = Sanguinololu &lt; 1.2
// 62 = Sanguinololu 1.2 and above
// 63 = Melzi
// 64 = STB V1.1
// 65 = Azteeg X1
// 66 = Melzi with ATmega1284 (MaKr3d version)
// 67 = Azteeg X3
// 7  = Ultimaker
// 71 = Ultimaker (Older electronics. Pre 1.5.4. This is rare)
// 77 = 3Drag Controller
// 8  = Teensylu
// 80 = Rumba
// 81 = Printrboard (AT90USB1286)
// 82 = Brainwave (AT90USB646)
// 83 = SAV Mk-I (AT90USB1286)
// 9  = Gen3+
// 70 = Megatronics
// 701= Megatronics v2.0
// 702= Minitronics v1.0
// 90 = Alpha OMCA board
// 91 = Final OMCA board
// 301 = Rambo
// 21 = Elefu Ra Board (v3)

// Original Solidoodle w/ Sanguinololu shipped pre June 2013 - Choose 62
// Solidoodle w/ Printrboard shipped post June 2013 - Choose 81
#ifndef MOTHERBOARD
#define MOTHERBOARD 34
#endif

// Define this to set a custom name for your generic Mendel,
// #define CUSTOM_MENDEL_NAME &quot;Rumba 8-22-14&quot;

// Define this to set a unique identifier for this printer, (Used by some programs to differentiate between machines)
// You can use an online service to generate a random UUID. (eg http://www.uuidgenerator.net/version4)
// #define MACHINE_UUID &quot;00000000-0000-0000-0000-000000000000&quot;

// This defines the number of extruders
#define EXTRUDERS 1

//// The following define selects which power supply you have. Please choose the one that matches your setup
// 1 = ATX
// 2 = X-Box 360 203Watts (the blue wire connected to PS_ON and the red wire to VCC)

#define POWER_SUPPLY 2

// Define this to have the electronics keep the powersupply off on startup. If you don&#039;t know what this is leave it.
// #define PS_DEFAULT_OFF

//===========================================================================
//=============================Thermal Settings  ============================
//===========================================================================
//
//--NORMAL IS 4.7kohm PULLUP!-- 1kohm pullup can be used on hotend sensor, using correct resistor and table
//
//// Temperature sensor settings:
// -2 is thermocouple with MAX6675 (only for sensor 0)
// -1 is thermocouple with AD595
// 0 is not used
// 1 is 100k thermistor - best choice for EPCOS 100k (4.7k pullup)
// 2 is 200k thermistor - ATC Semitec 204GT-2 (4.7k pullup)
// 3 is mendel-parts thermistor (4.7k pullup)
// 4 is 10k thermistor !! do not use it for a hotend. It gives bad resolution at high temp. !!
// 5 is 100K thermistor - ATC Semitec 104GT-2 (Used in ParCan &amp; J-Head) (4.7k pullup)
// 6 is 100k EPCOS - Not as accurate as table 1 (created using a fluke thermocouple) (4.7k pullup)
// 7 is 100k Honeywell thermistor 135-104LAG-J01 (4.7k pullup)
// 71 is 100k Honeywell thermistor 135-104LAF-J01 (4.7k pullup)
// 8 is 100k 0603 SMD Vishay NTCS0603E3104FXT (4.7k pullup)
// 9 is 100k GE Sensing AL03006-58.2K-97-G1 (4.7k pullup)
// 10 is 100k RS thermistor 198-961 (4.7k pullup)
// 60 is 100k Maker&#039;s Tool Works Kapton Bed Thermister
//
//    1k ohm pullup tables - This is not normal, you would have to have changed out your 4.7k for 1k
//                          (but gives greater accuracy and more stable PID)
// 51 is 100k thermistor - EPCOS (1k pullup)
// 52 is 200k thermistor - ATC Semitec 204GT-2 (1k pullup)
// 55 is 100k thermistor - ATC Semitec 104GT-2 (Used in ParCan &amp; J-Head) (1k pullup)

#define TEMP_SENSOR_0 5        //{SD Patch}
#define TEMP_SENSOR_1 -1
#define TEMP_SENSOR_2 0
#define TEMP_SENSOR_BED 1    //{SD Patch}

// This makes temp sensor 1 a redundant sensor for sensor 0. If the temperatures difference between these sensors is to high the print will be aborted.
//#define TEMP_SENSOR_1_AS_REDUNDANT
#define MAX_REDUNDANT_TEMP_SENSOR_DIFF 10

// This makes temp sensor 1 a redundant sensor for sensor 0. If the temperatures difference between these sensors is to high the print will be aborted.
//#define TEMP_SENSOR_1_AS_REDUNDANT
#define MAX_REDUNDANT_TEMP_SENSOR_DIFF 10

// Actual temperature must be close to target for this long before M109 returns success
#define TEMP_RESIDENCY_TIME 5  // (seconds) {SD Patch}
#define TEMP_HYSTERESIS 3       // (degC) range of +/- temperatures considered &quot;close&quot; to the target one
#define TEMP_WINDOW     1       // (degC) Window around target to start the residency timer x degC early.

// The minimal temperature defines the temperature below which the heater will not be enabled It is used
// to check that the wiring to the thermistor is not broken.
// Otherwise this would lead to the heater being powered on all the time.
#define HEATER_0_MINTEMP 5
#define HEATER_1_MINTEMP 5
#define HEATER_2_MINTEMP 5
#define BED_MINTEMP 5

// When temperature exceeds max temp, your heater will be switched off.
// This feature exists to protect your hotend from overheating accidentally, but *NOT* from thermistor short/failure!
// You should use MINTEMP for thermistor short/failure protection.
#define HEATER_0_MAXTEMP 310    //{SD Patch}
#define HEATER_1_MAXTEMP 275
#define HEATER_2_MAXTEMP 275
#define BED_MAXTEMP 115    //{SD Patch}

// If your bed has low resistance e.g. .6 ohm and throws the fuse you can duty cycle it to reduce the
// average current. The value should be an integer and the heat bed will be turned on for 1 interval of
// HEATER_BED_DUTY_CYCLE_DIVIDER intervals.
//#define HEATER_BED_DUTY_CYCLE_DIVIDER 4

// PID settings:
// Comment the following line to disable PID and enable bang-bang.
#define PIDTEMP
#define BANG_MAX 255 // limits current to nozzle while in bang-bang mode; 255=full current
#define PID_MAX 255 // limits current to nozzle while PID is active (see PID_FUNCTIONAL_RANGE below); 255=full current
#ifdef PIDTEMP
  //#define PID_DEBUG // Sends debug data to the serial port.
  //#define PID_OPENLOOP 1 // Puts PID in open loop. M104/M140 sets the output power from 0 to PID_MAX
  #define PID_FUNCTIONAL_RANGE 30 // If the temperature difference between the target temperature and the actual temperature
                                  // is more then PID_FUNCTIONAL_RANGE then the PID will be shut off and the heater will be set to min/max.
  #define PID_INTEGRAL_DRIVE_MAX 255  //limit for the integral term
  #define K1 0.95 //smoothing factor within the PID
  #define PID_dT ((16.0 * 8.0)/(F_CPU / 64.0 / 256.0)) //sampling period of the temperature routine

// If you are using a preconfigured hotend then you can use one of the value sets by uncommenting it
// Ultimaker
//    #define  DEFAULT_Kp 22.2
//    #define  DEFAULT_Ki 1.08
//    #define  DEFAULT_Kd 114
//
// Solidoodle
    #define  DEFAULT_Kp 15.44
    #define  DEFAULT_Ki 0.51
    #define  DEFAULT_Kd 116.62
//
// Makergear
//    #define  DEFAULT_Kp 7.0
//    #define  DEFAULT_Ki 0.1
//    #define  DEFAULT_Kd 12

// Mendel Parts V9 on 12V
//    #define  DEFAULT_Kp 63.0
//    #define  DEFAULT_Ki 2.25
//    #define  DEFAULT_Kd 440
#endif // PIDTEMP

// Bed Temperature Control
// Select PID or bang-bang with PIDTEMPBED. If bang-bang, BED_LIMIT_SWITCHING will enable hysteresis
//
// Uncomment this to enable PID on the bed. It uses the same frequency PWM as the extruder.
// If your PID_dT above is the default, and correct for your hardware/configuration, that means 7.689Hz,
// which is fine for driving a square wave into a resistive load and does not significantly impact you FET heating.
// This also works fine on a Fotek SSR-10DA Solid State Relay into a 250W heater.
// If your configuration is significantly different than this and you don&#039;t understand the issues involved, you probably
// shouldn&#039;t use bed PID until someone else verifies your hardware works.
// If this is enabled, find your own PID constants below.
//#define PIDTEMPBED
//
//#define BED_LIMIT_SWITCHING

// This sets the max power delivered to the bed, and replaces the HEATER_BED_DUTY_CYCLE_DIVIDER option.
// all forms of bed control obey this (PID, bang-bang, bang-bang with hysteresis)
// setting this to anything other than 255 enables a form of PWM to the bed just like HEATER_BED_DUTY_CYCLE_DIVIDER did,
// so you shouldn&#039;t use it unless you are OK with PWM on your bed.  (see the comment on enabling PIDTEMPBED)
#define MAX_BED_POWER 255 // limits duty cycle to bed; 255=full current

#ifdef PIDTEMPBED
//120v 250W silicone heater into 4mm borosilicate (MendelMax 1.5+)
//from FOPDT model - kp=.39 Tp=405 Tdead=66, Tc set to 79.2, aggressive factor of .15 (vs .1, 1, 10)
//    #define  DEFAULT_bedKp 10.00
//    #define  DEFAULT_bedKi .023
//    #define  DEFAULT_bedKd 305.4

//120v 250W silicone heater into 4mm borosilicate (MendelMax 1.5+)
//from pidautotune
//    #define  DEFAULT_bedKp 97.1
//    #define  DEFAULT_bedKi 1.41
//    #define  DEFAULT_bedKd 1675.16
//Solidoodle3 Standard Bed //{SD Patch}
//from pidautotune //{SD Patch}
    #define  DEFAULT_bedKp 100.15 //{SD Patch}
    #define  DEFAULT_bedKi 7.65 //{SD Patch}
    #define  DEFAULT_bedKd 327.90 //{SD Patch}

//Replicator MK2B Heat Bed //{SD Patch}
//from pidautotune //{SD Patch}
//    #define  DEFAULT_bedKp 367.89 //{SD Patch}
//    #define  DEFAULT_bedKi 36.68 //{SD Patch}
//    #define  DEFAULT_bedKd 922.06 //{SD Patch}

//QU-BD Silicone Bed 200x200 Square //{SD Patch}
//from pidautotune //{SD Patch}
//    #define  DEFAULT_bedKp 304.87 //{SD Patch}
//    #define  DEFAULT_bedKi 47.49 //{SD Patch}
//    #define  DEFAULT_bedKd 489.67 //{SD Patch}


// FIND YOUR OWN: &quot;M303 E-1 C8 S90&quot; to run autotune on the bed at 90 degreesC for 8 cycles.
#endif // PIDTEMPBED



//this prevents dangerous Extruder moves, i.e. if the temperature is under the limit
//can be software-disabled for whatever purposes by
#define PREVENT_DANGEROUS_EXTRUDE
//if PREVENT_DANGEROUS_EXTRUDE is on, you can still disable (uncomment) very long bits of extrusion separately.
#define PREVENT_LENGTHY_EXTRUDE

#define EXTRUDE_MINTEMP 145    //{SD Patch}
#define EXTRUDE_MAXLENGTH (X_MAX_LENGTH+Y_MAX_LENGTH) //prevent extrusion of very large distances.

//===========================================================================
//=============================Mechanical Settings===========================
//===========================================================================

// Uncomment the following line to enable CoreXY kinematics
// #define COREXY

// coarse Endstop Settings
#define ENDSTOPPULLUPS // Comment this out (using // at the start of the line) to disable the endstop pullup resistors

#ifndef ENDSTOPPULLUPS
  // fine Enstop settings: Individual Pullups. will be ignored if ENDSTOPPULLUPS is defined
  // #define ENDSTOPPULLUP_XMAX
  // #define ENDSTOPPULLUP_YMAX
  // #define ENDSTOPPULLUP_ZMAX
  // #define ENDSTOPPULLUP_XMIN
  // #define ENDSTOPPULLUP_YMIN
  // #define ENDSTOPPULLUP_ZMIN
#endif

#ifdef ENDSTOPPULLUPS
  #define ENDSTOPPULLUP_XMAX
  #define ENDSTOPPULLUP_YMAX
  #define ENDSTOPPULLUP_ZMAX
  #define ENDSTOPPULLUP_XMIN
  #define ENDSTOPPULLUP_YMIN
  #define ENDSTOPPULLUP_ZMIN
#endif

// The pullups are needed if you directly connect a mechanical endswitch between the signal and ground pins.
const bool X_MIN_ENDSTOP_INVERTING = false; // set to true to invert the logic of the endstop. {SD Patch}
const bool Y_MIN_ENDSTOP_INVERTING = false; // set to true to invert the logic of the endstop. {SD Patch}
const bool Z_MIN_ENDSTOP_INVERTING = false; // set to true to invert the logic of the endstop. {SD Patch}
const bool X_MAX_ENDSTOP_INVERTING = false; // set to true to invert the logic of the endstop. {SD Patch}
const bool Y_MAX_ENDSTOP_INVERTING = false; // set to true to invert the logic of the endstop. {SD Patch}
const bool Z_MAX_ENDSTOP_INVERTING = false; // set to true to invert the logic of the endstop. {SD Patch}
//#define DISABLE_MAX_ENDSTOPS
//#define DISABLE_MIN_ENDSTOPS

// Disable max endstops for compatibility with endstop checking routine
#if defined(COREXY) &amp;&amp; !defined(DISABLE_MAX_ENDSTOPS)
  #define DISABLE_MAX_ENDSTOPS
#endif

// For Inverting Stepper Enable Pins (Active Low) use 0, Non Inverting (Active High) use 1
#define X_ENABLE_ON 0
#define Y_ENABLE_ON 0
#define Z_ENABLE_ON 0
#define E_ENABLE_ON 0 // For all extruders

// Disables axis when it&#039;s not being used.
#define DISABLE_X false
#define DISABLE_Y false
#define DISABLE_Z false
#define DISABLE_E false // For all extruders

#define INVERT_X_DIR false    // for Mendel set to false, for Orca set to true {SD Patch}
#define INVERT_Y_DIR false    // for Mendel set to true, for Orca set to false
#define INVERT_Z_DIR false     // for Mendel set to false, for Orca set to true {SD Patch}
#define INVERT_E0_DIR false   // for direct drive extruder v9 set to true, for geared extruder set to false
#define INVERT_E1_DIR false    // for direct drive extruder v9 set to true, for geared extruder set to false
#define INVERT_E2_DIR false   // for direct drive extruder v9 set to true, for geared extruder set to false

// ENDSTOP SETTINGS:
// Sets direction of endstops when homing; 1=MAX, -1=MIN
#define X_HOME_DIR 1
#define Y_HOME_DIR 1
#define Z_HOME_DIR -1

#define min_software_endstops false // If true, axis won&#039;t move to coordinates less than HOME_POS. {SD Patch}
#define max_software_endstops false  // If true, axis won&#039;t move to coordinates greater than the defined lengths below. {SD Patch}

//============================= Bed Auto Leveling ===========================

//#define ENABLE_AUTO_BED_LEVELING // Delete the comment to enable (remove // at the start of the line)

#ifdef ENABLE_AUTO_BED_LEVELING

  // these are the positions on the bed to do the probing
  #define LEFT_PROBE_BED_POSITION 15
  #define RIGHT_PROBE_BED_POSITION 170
  #define BACK_PROBE_BED_POSITION 180
  #define FRONT_PROBE_BED_POSITION 20

  // these are the offsets to the prob relative to the extruder tip (Hotend - Probe)
  #define X_PROBE_OFFSET_FROM_EXTRUDER -25
  #define Y_PROBE_OFFSET_FROM_EXTRUDER -29
  #define Z_PROBE_OFFSET_FROM_EXTRUDER -12.35

  #define Z_RAISE_BEFORE_HOMING 4       // (in mm) Raise Z before homing (G28) for Probe Clearance.
                                        // Be sure you have this distance over your Z_MAX_POS in case
    
  #define XY_TRAVEL_SPEED 8000         // X and Y axis travel speed between probes, in mm/min
  
  #define Z_RAISE_BEFORE_PROBING 15    //How much the extruder will be raised before traveling to the first probing point.
  #define Z_RAISE_BETWEEN_PROBINGS 5  //How much the extruder will be raised when traveling from between next probing points


  //If defined, the Probe servo will be turned on only during movement and then turned off to avoid jerk
  //The value is the delay to turn the servo off after powered on - depends on the servo speed; 300ms is good value, but you can try lower it.
  // You MUST HAVE the SERVO_ENDSTOPS defined to use here a value higher than zero otherwise your code will not compile.

  #define PROBE_SERVO_DEACTIVATION_DELAY 300  


//If you have enabled the Bed Auto Levelling and are using the same Z Probe for Z Homing, 
//it is highly recommended you let this Z_SAFE_HOMING enabled!!!

  #define Z_SAFE_HOMING   // This feature is meant to avoid Z homing with probe outside the bed area. 
                          // When defined, it will:
                          // - Allow Z homing only after X and Y homing AND stepper drivers still enabled
                          // - If stepper drivers timeout, it will need X and Y homing again before Z homing
                          // - Position the probe in a defined XY point before Z Homing when homing all axis (G28)
                          // - Block Z homing only when the probe is outside bed area.
  
  #ifdef Z_SAFE_HOMING
    
    #define Z_SAFE_HOMING_X_POINT (X_MAX_LENGTH/2)    // X point for Z homing when homing all axis (G28)
    #define Z_SAFE_HOMING_Y_POINT (Y_MAX_LENGTH/2)    // Y point for Z homing when homing all axis (G28)
    
  #endif
  
  // with accurate bed leveling, the bed is sampled in a ACCURATE_BED_LEVELING_POINTSxACCURATE_BED_LEVELING_POINTS grid and least squares solution is calculated
  // Note: this feature occupies 10&#039;206 byte
  #define ACCURATE_BED_LEVELING
  
  #ifdef ACCURATE_BED_LEVELING
     // I wouldn&#039;t see a reason to go above 3 (=9 probing points on the bed)
    #define ACCURATE_BED_LEVELING_POINTS 2
  #endif
  
#endif

// {SD Patch} Start
// ###############################

// Model-independent endstop logic

#ifndef ENABLE_AUTO_BED_LEVELING
  #define Z_MIN_POS 0
#else
  #define Z_MIN_POS (-1*Z_PROBE_OFFSET_FROM_EXTRUDER)  //With Auto Bed Leveling, the Z_MIN MUST have the same distance as Z_PROBE
#endif

#define MANUAL_HOME_POSITIONS  // If defined, MANUAL_*_HOME_POS below will be used
#define MANUAL_Z_HOME_POS Z_MIN_POS

#if SOLIDOODLE_VERSION == 3
  #define X_MAX_POS 205
  #define X_MIN_POS 0
  #define Y_MAX_POS 200
  #define Y_MIN_POS 0
  #define Z_MAX_POS 195

// The position of the homing switches
  //#define BED_CENTER_AT_0_0  // If defined, the center of the bed is at (X=0, Y=0)
//Manual homing switch locations:
  #define MANUAL_X_HOME_POS 205
  #define MANUAL_Y_HOME_POS 200

#else //assume SD2
  #define X_MAX_POS 155
  #define X_MIN_POS 0
  #define Y_MAX_POS 150
  #define Y_MIN_POS 0
  #define Z_MAX_POS 150

  
// The position of the homing switches
  //#define BED_CENTER_AT_0_0  // If defined, the center of the bed is at (X=0, Y=0)
//Manual homing switch locations:
  #define MANUAL_X_HOME_POS 155
  #define MANUAL_Y_HOME_POS 150
#endif

#define X_MAX_LENGTH (X_MAX_POS - X_MIN_POS)
#define Y_MAX_LENGTH (Y_MAX_POS - Y_MIN_POS)
#define Z_MAX_LENGTH (Z_MAX_POS - Z_MIN_POS)

//###############################
//{SD Patch} END

//// MOVEMENT SETTINGS
#define NUM_AXIS 4 // The axis order in all axis related arrays is X, Y, Z, E
#define HOMING_FEEDRATE {50*60, 50*60, 4*60, 0}  // set the homing speeds (mm/min)

// default settings

#define DEFAULT_AXIS_STEPS_PER_UNIT   {88,88,2268,138}  // default steps per unit for Ultimaker {SD Patch}
//#define AXIS_STEPS_NEGATIVE           {88,88,2268,138} // Step values to be used when travelling in the negative direction. Useful for threadless ball screws. Comment out if not needed
#define DEFAULT_MAX_FEEDRATE          {500, 500, 5, 45}    // (mm/sec) {SD Patch}
#define DEFAULT_MAX_ACCELERATION      {1200,1200,100,10000}    // X, Y, Z, E maximum start speed for accelerated moves. E default values are good for skeinforge 40+, for older versions raise them a lot. {SD Patch}

#define DEFAULT_ACCELERATION          1000    // X, Y, Z and E max acceleration in mm/s^2 for printing moves {SD Patch}
#define DEFAULT_RETRACT_ACCELERATION  1000   // X, Y, Z and E max acceleration in mm/s^2 for retracts {SD Patch}

// Offset of the extruders (uncomment if using more than one and relying on firmware to position when changing).
// The offset has to be X=0, Y=0 for the extruder 0 hotend (default extruder).
// For the other hotends it is their distance from the extruder 0 hotend.
// #define EXTRUDER_OFFSET_X {0.0, 20.00} // (in mm) for each extruder, offset of the hotend on the X axis
// #define EXTRUDER_OFFSET_Y {0.0, 5.00}  // (in mm) for each extruder, offset of the hotend on the Y axis

// The speed change that does not require acceleration (i.e. the software might assume it can be done instantaneously)
#define DEFAULT_XYJERK                20.0    // (mm/sec)
#define DEFAULT_ZJERK                 0.4     // (mm/sec)
#define DEFAULT_EJERK                 5.0    // (mm/sec)

//===========================================================================
//=============================Additional Features===========================
//===========================================================================

// EEPROM
// the microcontroller can store settings in the EEPROM, e.g. max velocity...
// M500 - stores paramters in EEPROM
// M501 - reads parameters from EEPROM (if you need reset them after you changed them temporarily).
// M502 - reverts to the default &quot;factory settings&quot;.  You still need to store them in EEPROM afterwards if you want to.
//define this to enable eeprom support
#define EEPROM_SETTINGS //{SD Patch}
//to disable EEPROM Serial responses and decrease program space by ~1700 byte: comment this out:
// please keep turned on if you can.
#define EEPROM_CHITCHAT //{SD Patch}

// Preheat Constants
#define PLA_PREHEAT_HOTEND_TEMP 160 //{SD Patch}
#define PLA_PREHEAT_HPB_TEMP 70 //{SD Patch}
#define PLA_PREHEAT_FAN_SPEED 255        // Insert Value between 0 and 255

#define ABS_PREHEAT_HOTEND_TEMP 190 //{SD Patch}
#define ABS_PREHEAT_HPB_TEMP 95 //{SD Patch}
#define ABS_PREHEAT_FAN_SPEED 255        // Insert Value between 0 and 255

// Preheat Constants
#define PLA_PREHEAT_HOTEND_TEMP 180
#define PLA_PREHEAT_HPB_TEMP 70
#define PLA_PREHEAT_FAN_SPEED 255   // Insert Value between 0 and 255

#define ABS_PREHEAT_HOTEND_TEMP 240
#define ABS_PREHEAT_HPB_TEMP 100
#define ABS_PREHEAT_FAN_SPEED 255   // Insert Value between 0 and 255

//LCD and SD support
//#define ULTRA_LCD  //general lcd support, also 16x2
//#define DOGLCD  // Support for SPI LCD 128x64 (Controller ST7565R graphic Display Family)
//#define SDSUPPORT // Enable SD Card Support in Hardware Console
//#define SDSLOW // Use slower SD transfer mode (not normally needed - uncomment if you&#039;re getting volume init error)
//#define ENCODER_PULSES_PER_STEP 1 // Increase if you have a high resolution encoder
//#define ULTIMAKERCONTROLLER //as available from the ultimaker online store.
//#define ULTIPANEL  //the ultipanel as on thingiverse

// The MaKr3d Makr-Panel with graphic controller and SD support
// http://reprap.org/wiki/MaKr3d_MaKrPanel
//#define MAKRPANEL

// The RepRapDiscount Smart Controller (white PCB)
// http://reprap.org/wiki/RepRapDiscount_Smart_Controller
//#define REPRAP_DISCOUNT_SMART_CONTROLLER

// The GADGETS3D G3D LCD/SD Controller (blue PCB)
// http://reprap.org/wiki/RAMPS_1.3/1.4_GADGETS3D_Shield_with_Panel
//#define G3D_PANEL

// The RepRapDiscount FULL GRAPHIC Smart Controller (quadratic white PCB)
// http://reprap.org/wiki/RepRapDiscount_Full_Graphic_Smart_Controller
//
// ==&gt; REMEMBER TO INSTALL U8glib to your ARDUINO library folder: http://code.google.com/p/u8glib/wiki/u8glib
//#define REPRAP_DISCOUNT_FULL_GRAPHIC_SMART_CONTROLLER

// The RepRapWorld REPRAPWORLD_KEYPAD v1.1
// http://reprapworld.com/?products_details&amp;products_id=202&amp;cPath=1591_1626
//#define REPRAPWORLD_KEYPAD
//#define REPRAPWORLD_KEYPAD_MOVE_STEP 10.0 // how much should be moved when a key is pressed, eg 10.0 means 10mm per click

// The Elefu RA Board Control Panel
// http://www.elefu.com/index.php?route=product/product&amp;product_id=53
// REMEMBER TO INSTALL LiquidCrystal_I2C.h in your ARUDINO library folder: https://github.com/kiyoshigawa/LiquidCrystal_I2C
#define RA_CONTROL_PANEL

//automatic expansion
#if defined (MAKRPANEL)
 #define DOGLCD
 #define SDSUPPORT
 #define ULTIPANEL
 #define NEWPANEL
 #define DEFAULT_LCD_CONTRAST 17
#endif

#if defined (REPRAP_DISCOUNT_FULL_GRAPHIC_SMART_CONTROLLER)
 #define DOGLCD
 #define U8GLIB_ST7920
 #define REPRAP_DISCOUNT_SMART_CONTROLLER
#endif

#if defined(ULTIMAKERCONTROLLER) || defined(REPRAP_DISCOUNT_SMART_CONTROLLER) || defined(G3D_PANEL)
 #define ULTIPANEL
 #define NEWPANEL
#endif

#if defined(REPRAPWORLD_KEYPAD)
  #define NEWPANEL
  #define ULTIPANEL
#endif
#if defined(RA_CONTROL_PANEL)
 #define ULTIPANEL
 #define NEWPANEL
 #define LCD_I2C_TYPE_PCA8574
 #define LCD_I2C_ADDRESS 0x27   // I2C Address of the port expander
#endif

//I2C PANELS

//#define LCD_I2C_SAINSMART_YWROBOT
#ifdef LCD_I2C_SAINSMART_YWROBOT
  // This uses the LiquidCrystal_I2C library ( https://bitbucket.org/fmalpartida/new-liquidcrystal/wiki/Home )
  // Make sure it is placed in the Arduino libraries directory.
  #define LCD_I2C_TYPE_PCF8575
  #define LCD_I2C_ADDRESS 0x27   // I2C Address of the port expander
  #define NEWPANEL
  #define ULTIPANEL
#endif

// PANELOLU2 LCD with status LEDs, separate encoder and click inputs
//#define LCD_I2C_PANELOLU2
#ifdef LCD_I2C_PANELOLU2
  // This uses the LiquidTWI2 library v1.2.3 or later ( https://github.com/lincomatic/LiquidTWI2 )
  // Make sure the LiquidTWI2 directory is placed in the Arduino or Sketchbook libraries subdirectory.
  // (v1.2.3 no longer requires you to define PANELOLU in the LiquidTWI2.h library header file)
  // Note: The PANELOLU2 encoder click input can either be directly connected to a pin
  //       (if BTN_ENC defined to != -1) or read through I2C (when BTN_ENC == -1).
  #define LCD_I2C_TYPE_MCP23017
  #define LCD_I2C_ADDRESS 0x20 // I2C Address of the port expander
  #define LCD_USE_I2C_BUZZER //comment out to disable buzzer on LCD
  #define NEWPANEL
  #define ULTIPANEL
#endif

// Panucatt VIKI LCD with status LEDs, integrated click &amp; L/R/U/P buttons, separate encoder inputs
//#define LCD_I2C_VIKI
#ifdef LCD_I2C_VIKI
  // This uses the LiquidTWI2 library v1.2.3 or later ( https://github.com/lincomatic/LiquidTWI2 )
  // Make sure the LiquidTWI2 directory is placed in the Arduino or Sketchbook libraries subdirectory.
  // Note: The pause/stop/resume LCD button pin should be connected to the Arduino
  //       BTN_ENC pin (or set BTN_ENC to -1 if not used)
  #define LCD_I2C_TYPE_MCP23017
  #define LCD_I2C_ADDRESS 0x20 // I2C Address of the port expander
  #define LCD_USE_I2C_BUZZER //comment out to disable buzzer on LCD (requires LiquidTWI2 v1.2.3 or later)
  #define NEWPANEL
  #define ULTIPANEL
#endif

// Shift register panels
// ---------------------
// 2 wire Non-latching LCD SR from:
// https://bitbucket.org/fmalpartida/new-liquidcrystal/wiki/schematics#!shiftregister-connection 
//#define SR_LCD
#ifdef SR_LCD
   #define SR_LCD_2W_NL    // Non latching 2 wire shiftregister
   //#define NEWPANEL
#endif

// Panucatt VIKI LCD with status LEDs, integrated click &amp; L/R/U/P buttons, separate encoder inputs
//#define LCD_I2C_VIKI
#ifdef LCD_I2C_VIKI
  // This uses the LiquidTWI2 library v1.2.3 or later ( https://github.com/lincomatic/LiquidTWI2 )
  // Make sure the LiquidTWI2 directory is placed in the Arduino or Sketchbook libraries subdirectory.
  // Note: The pause/stop/resume LCD button pin should be connected to the Arduino
  //       BTN_ENC pin (or set BTN_ENC to -1 if not used)
  #define LCD_I2C_TYPE_MCP23017
  #define LCD_I2C_ADDRESS 0x20 // I2C Address of the port expander
  #define LCD_USE_I2C_BUZZER //comment out to disable buzzer on LCD (requires LiquidTWI2 v1.2.3 or later)
  #define NEWPANEL
  #define ULTIPANEL
#endif

#ifdef ULTIPANEL
//  #define NEWPANEL  //enable this if you have a click-encoder panel
  #define SDSUPPORT
  #define ULTRA_LCD
  #ifdef DOGLCD // Change number of lines to match the DOG graphic display
    #define LCD_WIDTH 20
    #define LCD_HEIGHT 5
  #else
    #define LCD_WIDTH 20
    #define LCD_HEIGHT 4
  #endif
#else //no panel but just lcd
  #ifdef ULTRA_LCD
  #ifdef DOGLCD // Change number of lines to match the 128x64 graphics display
    #define LCD_WIDTH 20
    #define LCD_HEIGHT 5
  #else
    #define LCD_WIDTH 16
    #define LCD_HEIGHT 2
  #endif
  #endif
#endif

// default LCD contrast for dogm-like LCD displays
#ifdef DOGLCD
# ifndef DEFAULT_LCD_CONTRAST
#  define DEFAULT_LCD_CONTRAST 32
# endif
#endif

// Increase the FAN pwm frequency. Removes the PWM noise but increases heating in the FET/Arduino
//#define FAST_PWM_FAN

// Temperature status leds that display the hotend and bet temperature.
// If alle hotends and bed temperature and temperature setpoint are &lt; 54C then the BLUE led is on.
// Otherwise the RED led is on. There is 1C hysteresis.
//#define TEMP_STAT_LEDS

// Use software PWM to drive the fan, as for the heaters. This uses a very low frequency
// which is not ass annoying as with the hardware PWM. On the other hand, if this frequency
// is too low, you should also increment SOFT_PWM_SCALE.
//#define FAN_SOFT_PWM

// Incrementing this by 1 will double the software PWM frequency,
// affecting heaters, and the fan if FAN_SOFT_PWM is enabled.
// However, control resolution will be halved for each increment;
// at zero value, there are 128 effective control positions.
#define SOFT_PWM_SCALE 0

// M240  Triggers a camera by emulating a Canon RC-1 Remote
// Data from: http://www.doc-diy.net/photo/rc-1_hacked/
// #define PHOTOGRAPH_PIN     23

// SF send wrong arc g-codes when using Arc Point as fillet procedure
//#define SF_ARC_FIX

// Support for the BariCUDA Paste Extruder.
//#define BARICUDA

//define BlinkM/CyzRgb Support
//#define BLINKM

/*********************************************************************\
* R/C SERVO support
* Sponsored by TrinityLabs, Reworked by codexmas
**********************************************************************/

// Number of servos
//
// If you select a configuration below, this will receive a default value and does not need to be set manually
// set it manually if you have more servos than extruders and wish to manually control some
// leaving it undefined or defining as 0 will disable the servo subsystem
// If unsure, leave commented / disabled
//
//#define NUM_SERVOS 3 // Servo index starts with 0 for M280 command

// Servo Endstops
//
// This allows for servo actuated endstops, primary usage is for the Z Axis to eliminate calibration or bed height changes.
// Use M206 command to correct for switch height offset to actual nozzle height. Store that setting with M500.
//
//#define SERVO_ENDSTOPS {-1, -1, 0} // Servo index for X, Y, Z. Disable with -1
//#define SERVO_ENDSTOP_ANGLES {0,0, 0,0, 70,0} // X,Y,Z Axis Extend and Retract angles

#include &quot;Configuration_adv.h&quot;
#include &quot;thermistortables.h&quot;

#endif //__CONFIGURATION_H </code></pre></div><p> </p><div class="codebox"><pre><code> 
#ifndef ULTRA_LCD_IMPLEMENTATION_HITACHI_HD44780_H
#define ULTRA_LCD_IMPLEMENTATION_HITACHI_HD44780_H

/**
* Implementation of the LCD display routines for a hitachi HD44780 display. These are common LCD character displays.
* When selecting the rusian language, a slightly different LCD implementation is used to handle UTF8 characters.
**/

#ifndef REPRAPWORLD_KEYPAD
extern volatile uint8_t buttons;  //the last checked buttons in a bit array.
#else
extern volatile uint16_t buttons;  //an extended version of the last checked buttons in a bit array.
#endif

////////////////////////////////////
// Setup button and encode mappings for each panel (into &#039;buttons&#039; variable
//
// This is just to map common functions (across different panels) onto the same 
// macro name. The mapping is independent of whether the button is directly connected or 
// via a shift/i2c register.

#ifdef ULTIPANEL
// All Ultipanels might have an encoder - so this is always be mapped onto first two bits
#define BLEN_B 1
#define BLEN_A 0

#define EN_B (1&lt;&lt;BLEN_B) // The two encoder pins are connected through BTN_EN1 and BTN_EN2
#define EN_A (1&lt;&lt;BLEN_A)

#if defined(BTN_ENC) &amp;&amp; BTN_ENC &gt; -1
  // encoder click is directly connected
  #define BLEN_C 2 
  #define EN_C (1&lt;&lt;BLEN_C) 
#endif 
  
//
// Setup other button mappings of each panel
//
#if defined(LCD_I2C_VIKI)
  #define B_I2C_BTN_OFFSET 3 // (the first three bit positions reserved for EN_A, EN_B, EN_C)
  
  // button and encoder bit positions within &#039;buttons&#039;
  #define B_LE (BUTTON_LEFT&lt;&lt;B_I2C_BTN_OFFSET)    // The remaining normalized buttons are all read via I2C
  #define B_UP (BUTTON_UP&lt;&lt;B_I2C_BTN_OFFSET)
  #define B_MI (BUTTON_SELECT&lt;&lt;B_I2C_BTN_OFFSET)
  #define B_DW (BUTTON_DOWN&lt;&lt;B_I2C_BTN_OFFSET)
  #define B_RI (BUTTON_RIGHT&lt;&lt;B_I2C_BTN_OFFSET)

  #if defined(BTN_ENC) &amp;&amp; BTN_ENC &gt; -1 
    // the pause/stop/restart button is connected to BTN_ENC when used
    #define B_ST (EN_C)                            // Map the pause/stop/resume button into its normalized functional name 
    #define LCD_CLICKED (buttons&amp;(B_MI|B_RI|B_ST)) // pause/stop button also acts as click until we implement proper pause/stop.
  #else
    #define LCD_CLICKED (buttons&amp;(B_MI|B_RI))
  #endif  

  // I2C buttons take too long to read inside an interrupt context and so we read them during lcd_update
  #define LCD_HAS_SLOW_BUTTONS

#elif defined(LCD_I2C_PANELOLU2)
  // encoder click can be read through I2C if not directly connected
  #if BTN_ENC &lt;= 0 
    #define B_I2C_BTN_OFFSET 3 // (the first three bit positions reserved for EN_A, EN_B, EN_C)
  
    #define B_MI (PANELOLU2_ENCODER_C&lt;&lt;B_I2C_BTN_OFFSET) // requires LiquidTWI2 library v1.2.3 or later

    #define LCD_CLICKED (buttons&amp;B_MI)

    // I2C buttons take too long to read inside an interrupt context and so we read them during lcd_update
    #define LCD_HAS_SLOW_BUTTONS
  #else
    #define LCD_CLICKED (buttons&amp;EN_C)  
  #endif

#elif defined(REPRAPWORLD_KEYPAD)
    // define register bit values, don&#039;t change it
    #define BLEN_REPRAPWORLD_KEYPAD_F3 0
    #define BLEN_REPRAPWORLD_KEYPAD_F2 1
    #define BLEN_REPRAPWORLD_KEYPAD_F1 2
    #define BLEN_REPRAPWORLD_KEYPAD_UP 3
    #define BLEN_REPRAPWORLD_KEYPAD_RIGHT 4
    #define BLEN_REPRAPWORLD_KEYPAD_MIDDLE 5
    #define BLEN_REPRAPWORLD_KEYPAD_DOWN 6
    #define BLEN_REPRAPWORLD_KEYPAD_LEFT 7
    
    #define REPRAPWORLD_BTN_OFFSET 3 // bit offset into buttons for shift register values

    #define EN_REPRAPWORLD_KEYPAD_F3 (1&lt;&lt;(BLEN_REPRAPWORLD_KEYPAD_F3+REPRAPWORLD_BTN_OFFSET))
    #define EN_REPRAPWORLD_KEYPAD_F2 (1&lt;&lt;(BLEN_REPRAPWORLD_KEYPAD_F2+REPRAPWORLD_BTN_OFFSET))
    #define EN_REPRAPWORLD_KEYPAD_F1 (1&lt;&lt;(BLEN_REPRAPWORLD_KEYPAD_F1+REPRAPWORLD_BTN_OFFSET))
    #define EN_REPRAPWORLD_KEYPAD_UP (1&lt;&lt;(BLEN_REPRAPWORLD_KEYPAD_UP+REPRAPWORLD_BTN_OFFSET))
    #define EN_REPRAPWORLD_KEYPAD_RIGHT (1&lt;&lt;(BLEN_REPRAPWORLD_KEYPAD_RIGHT+REPRAPWORLD_BTN_OFFSET))
    #define EN_REPRAPWORLD_KEYPAD_MIDDLE (1&lt;&lt;(BLEN_REPRAPWORLD_KEYPAD_MIDDLE+REPRAPWORLD_BTN_OFFSET))
    #define EN_REPRAPWORLD_KEYPAD_DOWN (1&lt;&lt;(BLEN_REPRAPWORLD_KEYPAD_DOWN+REPRAPWORLD_BTN_OFFSET))
    #define EN_REPRAPWORLD_KEYPAD_LEFT (1&lt;&lt;(BLEN_REPRAPWORLD_KEYPAD_LEFT+REPRAPWORLD_BTN_OFFSET))

    #define LCD_CLICKED ((buttons&amp;EN_C) || (buttons&amp;EN_REPRAPWORLD_KEYPAD_F1))
    #define REPRAPWORLD_KEYPAD_MOVE_Y_DOWN (buttons&amp;EN_REPRAPWORLD_KEYPAD_DOWN)
    #define REPRAPWORLD_KEYPAD_MOVE_Y_UP (buttons&amp;EN_REPRAPWORLD_KEYPAD_UP)
    #define REPRAPWORLD_KEYPAD_MOVE_HOME (buttons&amp;EN_REPRAPWORLD_KEYPAD_MIDDLE)

#elif defined(NEWPANEL)
  #define LCD_CLICKED (buttons&amp;EN_C)
  
#else // old style ULTIPANEL
  //bits in the shift register that carry the buttons for:
  // left up center down right red(stop)
  #define BL_LE 7
  #define BL_UP 6
  #define BL_MI 5
  #define BL_DW 4
  #define BL_RI 3
  #define BL_ST 2

  //automatic, do not change
  #define B_LE (1&lt;&lt;BL_LE)
  #define B_UP (1&lt;&lt;BL_UP)
  #define B_MI (1&lt;&lt;BL_MI)
  #define B_DW (1&lt;&lt;BL_DW)
  #define B_RI (1&lt;&lt;BL_RI)
  #define B_ST (1&lt;&lt;BL_ST)
  
  #define LCD_CLICKED (buttons&amp;(B_MI|B_ST))
#endif

////////////////////////
// Setup Rotary Encoder Bit Values (for two pin encoders to indicate movement)
// These values are independent of which pins are used for EN_A and EN_B indications
// The rotary encoder part is also independent to the chipset used for the LCD
#if defined(EN_A) &amp;&amp; defined(EN_B)
    #define encrot0 0
    #define encrot1 2
    #define encrot2 3
    #define encrot3 1
#endif 

#endif //ULTIPANEL

////////////////////////////////////
// Create LCD class instance and chipset-specific information
#if defined(LCD_I2C_TYPE_PCF8575)
  // note: these are register mapped pins on the PCF8575 controller not Arduino pins
  #define LCD_I2C_PIN_BL  3
  #define LCD_I2C_PIN_EN  2
  #define LCD_I2C_PIN_RW  1
  #define LCD_I2C_PIN_RS  0
  #define LCD_I2C_PIN_D4  4
  #define LCD_I2C_PIN_D5  5
  #define LCD_I2C_PIN_D6  6
  #define LCD_I2C_PIN_D7  7

  #include &lt;Wire.h&gt;
  #include &lt;LCD.h&gt;
  #include &lt;LiquidCrystal_I2C.h&gt;
  #define LCD_CLASS LiquidCrystal_I2C
  LCD_CLASS lcd(LCD_I2C_ADDRESS,LCD_I2C_PIN_EN,LCD_I2C_PIN_RW,LCD_I2C_PIN_RS,LCD_I2C_PIN_D4,LCD_I2C_PIN_D5,LCD_I2C_PIN_D6,LCD_I2C_PIN_D7);
  
#elif defined(LCD_I2C_TYPE_MCP23017)
  //for the LED indicators (which maybe mapped to different things in lcd_implementation_update_indicators())
  #define LED_A 0x04 //100
  #define LED_B 0x02 //010
  #define LED_C 0x01 //001

  #define LCD_HAS_STATUS_INDICATORS

  #include &lt;Wire.h&gt;
  #include &lt;LiquidTWI2.h&gt;
  #define LCD_CLASS LiquidTWI2
  LCD_CLASS lcd(LCD_I2C_ADDRESS);
  
#elif defined(LCD_I2C_TYPE_MCP23008)
  #include &lt;Wire.h&gt;
  #include &lt;LiquidTWI2.h&gt;
  #define LCD_CLASS LiquidTWI2
  LCD_CLASS lcd(LCD_I2C_ADDRESS);  

#elif defined(LCD_I2C_TYPE_PCA8574)
    #include &lt;LiquidCrystal_I2C.h&gt;
    #define LCD_CLASS LiquidCrystal_I2C
    LCD_CLASS lcd(LCD_I2C_ADDRESS, LCD_WIDTH, LCD_HEIGHT);
    
// 2 wire Non-latching LCD SR from:
// https://bitbucket.org/fmalpartida/new-liquidcrystal/wiki/schematics#!shiftregister-connection 
#elif defined(SR_LCD_2W_NL)
   
  #include &lt;LCD.h&gt;
  #include &lt;LiquidCrystal_SR.h&gt;
  #define LCD_CLASS LiquidCrystal_SR
  LCD_CLASS lcd(SR_DATA_PIN, SR_CLK_PIN);

#else
  // Standard directly connected LCD implementations
  #if LANGUAGE_CHOICE == 6
    #include &quot;LiquidCrystalRus.h&quot;
    #define LCD_CLASS LiquidCrystalRus
  #else 
    #include &lt;LiquidCrystal.h&gt;
    #define LCD_CLASS LiquidCrystal
  #endif  
  LCD_CLASS lcd(LCD_PINS_RS, LCD_PINS_ENABLE, LCD_PINS_D4, LCD_PINS_D5,LCD_PINS_D6,LCD_PINS_D7);  //RS,Enable,D4,D5,D6,D7
#endif

/* Custom characters defined in the first 8 characters of the LCD */
#define LCD_STR_BEDTEMP     &quot;\x00&quot;
#define LCD_STR_DEGREE      &quot;\x01&quot;
#define LCD_STR_THERMOMETER &quot;\x02&quot;
#define LCD_STR_UPLEVEL     &quot;\x03&quot;
#define LCD_STR_REFRESH     &quot;\x04&quot;
#define LCD_STR_FOLDER      &quot;\x05&quot;
#define LCD_STR_FEEDRATE    &quot;\x06&quot;
#define LCD_STR_CLOCK       &quot;\x07&quot;
#define LCD_STR_ARROW_RIGHT &quot;\x7E&quot;  /* from the default character set */

static void lcd_implementation_init()
{
    byte bedTemp[8] =
    {
        B00000,
        B11111,
        B10101,
        B10001,
        B10101,
        B11111,
        B00000,
        B00000
    }; //thanks Sonny Mounicou
    byte degree[8] =
    {
        B01100,
        B10010,
        B10010,
        B01100,
        B00000,
        B00000,
        B00000,
        B00000
    };
    byte thermometer[8] =
    {
        B00100,
        B01010,
        B01010,
        B01010,
        B01010,
        B10001,
        B10001,
        B01110
    };
    byte uplevel[8]={
        B00100,
        B01110,
        B11111,
        B00100,
        B11100,
        B00000,
        B00000,
        B00000
    }; //thanks joris
    byte refresh[8]={
        B00000,
        B00110,
        B11001,
        B11000,
        B00011,
        B10011,
        B01100,
        B00000,
    }; //thanks joris
    byte folder [8]={
        B00000,
        B11100,
        B11111,
        B10001,
        B10001,
        B11111,
        B00000,
        B00000
    }; //thanks joris
    byte feedrate [8]={
        B11100,
        B10000,
        B11000,
        B10111,
        B00101,
        B00110,
        B00101,
        B00000
    }; //thanks Sonny Mounicou
    byte clock [8]={
        B00000,
        B01110,
        B10011,
        B10101,
        B10001,
        B01110,
        B00000,
        B00000
    }; //thanks Sonny Mounicou

#if defined(LCDI2C_TYPE_PCF8575)
    lcd.begin(LCD_WIDTH, LCD_HEIGHT);
  #ifdef LCD_I2C_PIN_BL
    lcd.setBacklightPin(LCD_I2C_PIN_BL,POSITIVE);
    lcd.setBacklight(HIGH);
  #endif
  
#elif defined(LCD_I2C_TYPE_MCP23017)
    lcd.setMCPType(LTI_TYPE_MCP23017);
    lcd.begin(LCD_WIDTH, LCD_HEIGHT);
    lcd.setBacklight(0); //set all the LEDs off to begin with
    
#elif defined(LCD_I2C_TYPE_MCP23008)
    lcd.setMCPType(LTI_TYPE_MCP23008);
    lcd.begin(LCD_WIDTH, LCD_HEIGHT);

#elif defined(LCD_I2C_TYPE_PCA8574)
      lcd.init();
      lcd.backlight();
    
#else
    lcd.begin(LCD_WIDTH, LCD_HEIGHT);
#endif

    lcd.createChar(LCD_STR_BEDTEMP[0], bedTemp);
    lcd.createChar(LCD_STR_DEGREE[0], degree);
    lcd.createChar(LCD_STR_THERMOMETER[0], thermometer);
    lcd.createChar(LCD_STR_UPLEVEL[0], uplevel);
    lcd.createChar(LCD_STR_REFRESH[0], refresh);
    lcd.createChar(LCD_STR_FOLDER[0], folder);
    lcd.createChar(LCD_STR_FEEDRATE[0], feedrate);
    lcd.createChar(LCD_STR_CLOCK[0], clock);
    lcd.clear();
}
static void lcd_implementation_clear()
{
    lcd.clear();
}
/* Arduino &lt; 1.0.0 is missing a function to print PROGMEM strings, so we need to implement our own */
static void lcd_printPGM(const char* str)
{
    char c;
    while((c = pgm_read_byte(str++)) != &#039;\0&#039;)
    {
        lcd.write(c);
    }
}
/*
Possible status screens:
16x2   |0123456789012345|
       |000/000 B000/000|
       |Status line.....|

16x4   |0123456789012345|
       |000/000 B000/000|
       |SD100%    Z000.0|
       |F100%     T--:--|
       |Status line.....|

20x2   |01234567890123456789|
       |T000/000D B000/000D |
       |Status line.........|

20x4   |01234567890123456789|
       |T000/000D B000/000D |
       |X+000.0 Y+000.0 Z+000.0|
       |F100%  SD100% T--:--|
       |Status line.........|

20x4   |01234567890123456789|
       |T000/000D B000/000D |
       |T000/000D     Z000.0|
       |F100%  SD100% T--:--|
       |Status line.........|
*/
static void lcd_implementation_status_screen()
{
    int tHotend=int(degHotend(0) + 0.5);
    int tTarget=int(degTargetHotend(0) + 0.5);

#if LCD_WIDTH &lt; 20
    lcd.setCursor(0, 0);
    lcd.print(itostr3(tHotend));
    lcd.print(&#039;/&#039;);
    lcd.print(itostr3left(tTarget));

# if EXTRUDERS &gt; 1 || TEMP_SENSOR_BED != 0
    //If we have an 2nd extruder or heated bed, show that in the top right corner
    lcd.setCursor(8, 0);
#  if EXTRUDERS &gt; 1
    tHotend = int(degHotend(1) + 0.5);
    tTarget = int(degTargetHotend(1) + 0.5);
    lcd.print(LCD_STR_THERMOMETER[0]);
#  else//Heated bed
    tHotend=int(degBed() + 0.5);
    tTarget=int(degTargetBed() + 0.5);
    lcd.print(LCD_STR_BEDTEMP[0]);
#  endif
    lcd.print(itostr3(tHotend));
    lcd.print(&#039;/&#039;);
    lcd.print(itostr3left(tTarget));
# endif//EXTRUDERS &gt; 1 || TEMP_SENSOR_BED != 0

#else//LCD_WIDTH &gt; 19
    lcd.setCursor(0, 0);
    lcd.print(LCD_STR_THERMOMETER[0]);
    lcd.print(itostr3(tHotend));
    lcd.print(&#039;/&#039;);
    lcd.print(itostr3left(tTarget));
    lcd_printPGM(PSTR(LCD_STR_DEGREE &quot; &quot;));
    if (tTarget &lt; 10)
        lcd.print(&#039; &#039;);

# if EXTRUDERS &gt; 1 || TEMP_SENSOR_BED != 0
    //If we have an 2nd extruder or heated bed, show that in the top right corner
    lcd.setCursor(10, 0);
#  if EXTRUDERS &gt; 1
    tHotend = int(degHotend(1) + 0.5);
    tTarget = int(degTargetHotend(1) + 0.5);
    lcd.print(LCD_STR_THERMOMETER[0]);
#  else//Heated bed
    tHotend=int(degBed() + 0.5);
    tTarget=int(degTargetBed() + 0.5);
    lcd.print(LCD_STR_BEDTEMP[0]);
#  endif
    lcd.print(itostr3(tHotend));
    lcd.print(&#039;/&#039;);
    lcd.print(itostr3left(tTarget));
    lcd_printPGM(PSTR(LCD_STR_DEGREE &quot; &quot;));
    if (tTarget &lt; 10)
        lcd.print(&#039; &#039;);
# endif//EXTRUDERS &gt; 1 || TEMP_SENSOR_BED != 0
#endif//LCD_WIDTH &gt; 19

#if LCD_HEIGHT &gt; 2
//Lines 2 for 4 line LCD
# if LCD_WIDTH &lt; 20
#  ifdef SDSUPPORT
    lcd.setCursor(0, 2);
    lcd_printPGM(PSTR(&quot;SD&quot;));
    if (IS_SD_PRINTING)
        lcd.print(itostr3(card.percentDone()));
    else
        lcd_printPGM(PSTR(&quot;---&quot;));
    lcd.print(&#039;%&#039;);
#  endif//SDSUPPORT
# else//LCD_WIDTH &gt; 19
#  if EXTRUDERS &gt; 1 &amp;&amp; TEMP_SENSOR_BED != 0
    //If we both have a 2nd extruder and a heated bed, show the heated bed temp on the 2nd line on the left, as the first line is filled with extruder temps
    tHotend=int(degBed() + 0.5);
    tTarget=int(degTargetBed() + 0.5);

    lcd.setCursor(0, 1);
    lcd.print(LCD_STR_BEDTEMP[0]);
    lcd.print(itostr3(tHotend));
    lcd.print(&#039;/&#039;);
    lcd.print(itostr3left(tTarget));
    lcd_printPGM(PSTR(LCD_STR_DEGREE &quot; &quot;));
    if (tTarget &lt; 10)
        lcd.print(&#039; &#039;);
#  else
    lcd.setCursor(0,1);
    lcd.print(&#039;X&#039;);
    lcd.print(ftostr3(current_position[X_AXIS]));
    lcd_printPGM(PSTR(&quot; Y&quot;));
    lcd.print(ftostr3(current_position[Y_AXIS]));
#  endif//EXTRUDERS &gt; 1 || TEMP_SENSOR_BED != 0
# endif//LCD_WIDTH &gt; 19
    lcd.setCursor(LCD_WIDTH - 8, 1);
    lcd.print(&#039;Z&#039;);
    lcd.print(ftostr32(current_position[Z_AXIS]));
#endif//LCD_HEIGHT &gt; 2

#if LCD_HEIGHT &gt; 3
    lcd.setCursor(0, 2);
    lcd.print(LCD_STR_FEEDRATE[0]);
    lcd.print(itostr3(feedmultiply));
    lcd.print(&#039;%&#039;);
# if LCD_WIDTH &gt; 19
#  ifdef SDSUPPORT
    lcd.setCursor(7, 2);
    lcd_printPGM(PSTR(&quot;SD&quot;));
    if (IS_SD_PRINTING)
        lcd.print(itostr3(card.percentDone()));
    else
        lcd_printPGM(PSTR(&quot;---&quot;));
    lcd.print(&#039;%&#039;);
#  endif//SDSUPPORT
# endif//LCD_WIDTH &gt; 19
    lcd.setCursor(LCD_WIDTH - 6, 2);
    lcd.print(LCD_STR_CLOCK[0]);
    if(starttime != 0)
    {
        uint16_t time = millis()/60000 - starttime/60000;
        lcd.print(itostr2(time/60));
        lcd.print(&#039;:&#039;);
        lcd.print(itostr2(time%60));
    }else{
        lcd_printPGM(PSTR(&quot;--:--&quot;));
    }
#endif

    //Status message line on the last line
    lcd.setCursor(0, LCD_HEIGHT - 1);
    lcd.print(lcd_status_message);
}
static void lcd_implementation_drawmenu_generic(uint8_t row, const char* pstr, char pre_char, char post_char)
{
    char c;
    //Use all characters in narrow LCDs
  #if LCD_WIDTH &lt; 20
      uint8_t n = LCD_WIDTH - 1 - 1;
    #else
      uint8_t n = LCD_WIDTH - 1 - 2;
  #endif
    lcd.setCursor(0, row);
    lcd.print(pre_char);
    while( ((c = pgm_read_byte(pstr)) != &#039;\0&#039;) &amp;&amp; (n&gt;0) )
    {
        lcd.print(c);
        pstr++;
        n--;
    }
    while(n--)
        lcd.print(&#039; &#039;);
    lcd.print(post_char);
    lcd.print(&#039; &#039;);
}
static void lcd_implementation_drawmenu_setting_edit_generic(uint8_t row, const char* pstr, char pre_char, char* data)
{
    char c;
    //Use all characters in narrow LCDs
  #if LCD_WIDTH &lt; 20
      uint8_t n = LCD_WIDTH - 1 - 1 - strlen(data);
    #else
      uint8_t n = LCD_WIDTH - 1 - 2 - strlen(data);
  #endif
    lcd.setCursor(0, row);
    lcd.print(pre_char);
    while( ((c = pgm_read_byte(pstr)) != &#039;\0&#039;) &amp;&amp; (n&gt;0) )
    {
        lcd.print(c);
        pstr++;
        n--;
    }
    lcd.print(&#039;:&#039;);
    while(n--)
        lcd.print(&#039; &#039;);
    lcd.print(data);
}
static void lcd_implementation_drawmenu_setting_edit_generic_P(uint8_t row, const char* pstr, char pre_char, const char* data)
{
    char c;
    //Use all characters in narrow LCDs
  #if LCD_WIDTH &lt; 20
      uint8_t n = LCD_WIDTH - 1 - 1 - strlen_P(data);
    #else
      uint8_t n = LCD_WIDTH - 1 - 2 - strlen_P(data);
  #endif
    lcd.setCursor(0, row);
    lcd.print(pre_char);
    while( ((c = pgm_read_byte(pstr)) != &#039;\0&#039;) &amp;&amp; (n&gt;0) )
    {
        lcd.print(c);
        pstr++;
        n--;
    }
    lcd.print(&#039;:&#039;);
    while(n--)
        lcd.print(&#039; &#039;);
    lcd_printPGM(data);
}
#define lcd_implementation_drawmenu_setting_edit_int3_selected(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, itostr3(*(data)))
#define lcd_implementation_drawmenu_setting_edit_int3(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, itostr3(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float3_selected(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr3(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float3(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr3(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float32_selected(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr32(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float32(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr32(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float5_selected(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr5(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float5(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr5(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float52_selected(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr52(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float52(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr52(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float51_selected(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr51(*(data)))
#define lcd_implementation_drawmenu_setting_edit_float51(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr51(*(data)))
#define lcd_implementation_drawmenu_setting_edit_long5_selected(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr5(*(data)))
#define lcd_implementation_drawmenu_setting_edit_long5(row, pstr, pstr2, data, minValue, maxValue) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr5(*(data)))
#define lcd_implementation_drawmenu_setting_edit_bool_selected(row, pstr, pstr2, data) lcd_implementation_drawmenu_setting_edit_generic_P(row, pstr, &#039;&gt;&#039;, (*(data))?PSTR(MSG_ON):PSTR(MSG_OFF))
#define lcd_implementation_drawmenu_setting_edit_bool(row, pstr, pstr2, data) lcd_implementation_drawmenu_setting_edit_generic_P(row, pstr, &#039; &#039;, (*(data))?PSTR(MSG_ON):PSTR(MSG_OFF))

//Add version for callback functions
#define lcd_implementation_drawmenu_setting_edit_callback_int3_selected(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, itostr3(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_int3(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, itostr3(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float3_selected(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr3(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float3(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr3(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float32_selected(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr32(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float32(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr32(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float5_selected(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr5(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float5(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr5(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float52_selected(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr52(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float52(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr52(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float51_selected(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr51(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_float51(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr51(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_long5_selected(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039;&gt;&#039;, ftostr5(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_long5(row, pstr, pstr2, data, minValue, maxValue, callback) lcd_implementation_drawmenu_setting_edit_generic(row, pstr, &#039; &#039;, ftostr5(*(data)))
#define lcd_implementation_drawmenu_setting_edit_callback_bool_selected(row, pstr, pstr2, data, callback) lcd_implementation_drawmenu_setting_edit_generic_P(row, pstr, &#039;&gt;&#039;, (*(data))?PSTR(MSG_ON):PSTR(MSG_OFF))
#define lcd_implementation_drawmenu_setting_edit_callback_bool(row, pstr, pstr2, data, callback) lcd_implementation_drawmenu_setting_edit_generic_P(row, pstr, &#039; &#039;, (*(data))?PSTR(MSG_ON):PSTR(MSG_OFF))


void lcd_implementation_drawedit(const char* pstr, char* value)
{
    lcd.setCursor(1, 1);
    lcd_printPGM(pstr);
    lcd.print(&#039;:&#039;);
   #if LCD_WIDTH &lt; 20
      lcd.setCursor(LCD_WIDTH - strlen(value), 1);
    #else
      lcd.setCursor(LCD_WIDTH -1 - strlen(value), 1);
   #endif
    lcd.print(value);
}
static void lcd_implementation_drawmenu_sdfile_selected(uint8_t row, const char* pstr, const char* filename, char* longFilename)
{
    char c;
    uint8_t n = LCD_WIDTH - 1;
    lcd.setCursor(0, row);
    lcd.print(&#039;&gt;&#039;);
    if (longFilename[0] != &#039;\0&#039;)
    {
        filename = longFilename;
        longFilename[LCD_WIDTH-1] = &#039;\0&#039;;
    }
    while( ((c = *filename) != &#039;\0&#039;) &amp;&amp; (n&gt;0) )
    {
        lcd.print(c);
        filename++;
        n--;
    }
    while(n--)
        lcd.print(&#039; &#039;);
}
static void lcd_implementation_drawmenu_sdfile(uint8_t row, const char* pstr, const char* filename, char* longFilename)
{
    char c;
    uint8_t n = LCD_WIDTH - 1;
    lcd.setCursor(0, row);
    lcd.print(&#039; &#039;);
    if (longFilename[0] != &#039;\0&#039;)
    {
        filename = longFilename;
        longFilename[LCD_WIDTH-1] = &#039;\0&#039;;
    }
    while( ((c = *filename) != &#039;\0&#039;) &amp;&amp; (n&gt;0) )
    {
        lcd.print(c);
        filename++;
        n--;
    }
    while(n--)
        lcd.print(&#039; &#039;);
}
static void lcd_implementation_drawmenu_sddirectory_selected(uint8_t row, const char* pstr, const char* filename, char* longFilename)
{
    char c;
    uint8_t n = LCD_WIDTH - 2;
    lcd.setCursor(0, row);
    lcd.print(&#039;&gt;&#039;);
    lcd.print(LCD_STR_FOLDER[0]);
    if (longFilename[0] != &#039;\0&#039;)
    {
        filename = longFilename;
        longFilename[LCD_WIDTH-2] = &#039;\0&#039;;
    }
    while( ((c = *filename) != &#039;\0&#039;) &amp;&amp; (n&gt;0) )
    {
        lcd.print(c);
        filename++;
        n--;
    }
    while(n--)
        lcd.print(&#039; &#039;);
}
static void lcd_implementation_drawmenu_sddirectory(uint8_t row, const char* pstr, const char* filename, char* longFilename)
{
    char c;
    uint8_t n = LCD_WIDTH - 2;
    lcd.setCursor(0, row);
    lcd.print(&#039; &#039;);
    lcd.print(LCD_STR_FOLDER[0]);
    if (longFilename[0] != &#039;\0&#039;)
    {
        filename = longFilename;
        longFilename[LCD_WIDTH-2] = &#039;\0&#039;;
    }
    while( ((c = *filename) != &#039;\0&#039;) &amp;&amp; (n&gt;0) )
    {
        lcd.print(c);
        filename++;
        n--;
    }
    while(n--)
        lcd.print(&#039; &#039;);
}
#define lcd_implementation_drawmenu_back_selected(row, pstr, data) lcd_implementation_drawmenu_generic(row, pstr, LCD_STR_UPLEVEL[0], LCD_STR_UPLEVEL[0])
#define lcd_implementation_drawmenu_back(row, pstr, data) lcd_implementation_drawmenu_generic(row, pstr, &#039; &#039;, LCD_STR_UPLEVEL[0])
#define lcd_implementation_drawmenu_submenu_selected(row, pstr, data) lcd_implementation_drawmenu_generic(row, pstr, &#039;&gt;&#039;, LCD_STR_ARROW_RIGHT[0])
#define lcd_implementation_drawmenu_submenu(row, pstr, data) lcd_implementation_drawmenu_generic(row, pstr, &#039; &#039;, LCD_STR_ARROW_RIGHT[0])
#define lcd_implementation_drawmenu_gcode_selected(row, pstr, gcode) lcd_implementation_drawmenu_generic(row, pstr, &#039;&gt;&#039;, &#039; &#039;)
#define lcd_implementation_drawmenu_gcode(row, pstr, gcode) lcd_implementation_drawmenu_generic(row, pstr, &#039; &#039;, &#039; &#039;)
#define lcd_implementation_drawmenu_function_selected(row, pstr, data) lcd_implementation_drawmenu_generic(row, pstr, &#039;&gt;&#039;, &#039; &#039;)
#define lcd_implementation_drawmenu_function(row, pstr, data) lcd_implementation_drawmenu_generic(row, pstr, &#039; &#039;, &#039; &#039;)

static void lcd_implementation_quick_feedback()
{
#ifdef LCD_USE_I2C_BUZZER
    lcd.buzz(60,1000/6);
#elif defined(BEEPER) &amp;&amp; BEEPER &gt; -1
    SET_OUTPUT(BEEPER);
    for(int8_t i=0;i&lt;10;i++)
    {
      WRITE(BEEPER,HIGH);
      delayMicroseconds(100);
      WRITE(BEEPER,LOW);
      delayMicroseconds(100);
    }
#endif
}

#ifdef LCD_HAS_STATUS_INDICATORS
static void lcd_implementation_update_indicators()
{
  #if defined(LCD_I2C_PANELOLU2) || defined(LCD_I2C_VIKI)
    //set the LEDS - referred to as backlights by the LiquidTWI2 library 
    static uint8_t ledsprev = 0;
    uint8_t leds = 0;
    if (target_temperature_bed &gt; 0) leds |= LED_A;
    if (target_temperature[0] &gt; 0) leds |= LED_B;
    if (fanSpeed) leds |= LED_C;
    #if EXTRUDERS &gt; 1  
      if (target_temperature[1] &gt; 0) leds |= LED_C;
    #endif
    if (leds != ledsprev) {
      lcd.setBacklight(leds);
      ledsprev = leds;
    }
  #endif
}
#endif

#ifdef LCD_HAS_SLOW_BUTTONS
extern uint32_t blocking_enc;

static uint8_t lcd_implementation_read_slow_buttons()
{
  #ifdef LCD_I2C_TYPE_MCP23017
  uint8_t slow_buttons;
    // Reading these buttons this is likely to be too slow to call inside interrupt context
    // so they are called during normal lcd_update
    slow_buttons = lcd.readButtons() &lt;&lt; B_I2C_BTN_OFFSET; 
    #if defined(LCD_I2C_VIKI)
    if(slow_buttons &amp; (B_MI|B_RI)) { //LCD clicked
       if(blocking_enc &gt; millis()) {
         slow_buttons &amp;= ~(B_MI|B_RI); // Disable LCD clicked buttons if screen is updated
       }
    }
    #endif
    return slow_buttons; 
  #endif
}
#endif

#endif//ULTRA_LCD_IMPLEMENTATION_HITACHI_HD44780_H </code></pre></div><p>The former code gives me this error then kicks me to the latter.<br /><span class="postimg"><img src="http://i.imgur.com/mddqkGO.jpg" alt="http://i.imgur.com/mddqkGO.jpg" /></span></p>]]></description>
			<author><![CDATA[null@example.com (AZERATE)]]></author>
			<pubDate>Thu, 31 Dec 2015 19:31:07 +0000</pubDate>
			<guid>https://www.soliforum.com/post/112987/#p112987</guid>
		</item>
		<item>
			<title><![CDATA[Re: Help with Ramps 1.4 firmware]]></title>
			<link>https://www.soliforum.com/post/112986/#p112986</link>
			<description><![CDATA[<div class="quotebox"><cite>AZERATE wrote:</cite><blockquote><p>I&#039;m basing this flash off my Rumba which works wonders. The only difference is that I now have added an LCD Smart Controller and wonder what I have to do in the firmware to get the screen to work.</p><p>I&#039;m trying to get this right the first time, so I while I have saved and compiled as a test, I have not uploaded.</p><p>Thanks in advance and happy new year!</p></blockquote></div><p>Near the end of the configuration.h tab there is a list of supported LCD controllers. All you have to do is make sure the correct one is defined as the one in use.</p>]]></description>
			<author><![CDATA[null@example.com (carl_m1968)]]></author>
			<pubDate>Thu, 31 Dec 2015 19:12:12 +0000</pubDate>
			<guid>https://www.soliforum.com/post/112986/#p112986</guid>
		</item>
		<item>
			<title><![CDATA[Help with Ramps 1.4 firmware]]></title>
			<link>https://www.soliforum.com/post/112984/#p112984</link>
			<description><![CDATA[<p>I&#039;m basing this flash off my Rumba which works wonders. The only difference is that I now have added an LCD Smart Controller and wonder what I have to do in the firmware to get the screen to work.</p><p>I&#039;m trying to get this right the first time, so I while I have saved and compiled as a test, I have not uploaded.</p><p>Thanks in advance and happy new year!</p>]]></description>
			<author><![CDATA[null@example.com (AZERATE)]]></author>
			<pubDate>Thu, 31 Dec 2015 18:46:15 +0000</pubDate>
			<guid>https://www.soliforum.com/post/112984/#p112984</guid>
		</item>
	</channel>
</rss>
