| View previous topic :: View next topic | 
	
	
		| Author | Message | 
	
		| MCUprogrammer 
 
 
 Joined: 08 Sep 2020
 Posts: 233
 
 
 
			    
 
 | 
			
				| LM35DZ reading |  
				|  Posted: Wed Jan 11, 2023 2:22 am |   |  
				| 
 |  
				| CCS 5.113 Hello
 I want to read temperature with LM35DZ. I'm trying to read fast and print the correct value on the screen. It reads the temperature, but the temperature always increases by 2 degrees. I haven't seen 0.1 precision. But when I look with an avometer, the millivolts are increasing one by one. What should I do?
 
  	  | Code: |  	  | #include <16F886.h>
 #fuses NOWDT
 #device ADC = 8
 #use delay(crystal = 20MHz)
 
 
 #define LCD_ENABLE_PIN     PIN_B1
 #define LCD_RS_PIN         PIN_B0
 #define LCD_RW_PIN           0
 #define LCD_DATA4          PIN_B2
 #define LCD_DATA5          PIN_B3
 #define LCD_DATA6          PIN_B4
 #define LCD_DATA7          PIN_B5
 #include <lcd_rw.c>
 
 #define ADC_VREF_VOLTAGE     4.90
 #define ADC_RESOLUTION       255
 
 
 void main(void)
 {
 
 unsigned int8 LM35Value = 0;
 float LM35Voltage = 0.0;
 float LMtemp = 0.0;
 
 
 lcd_init();
 
 setup_adc_ports(sAN0 | sAN1 | sAN2,VSS_VDD);
 setup_adc(ADC_CLOCK_DIV_32);
 
 
 while(TRUE)
 {
 
 set_adc_channel(0);
 delay_us(20);
 LM35Value = read_adc();
 LM35Voltage = ((ADC_VREF_VOLTAGE / ADC_RESOLUTION )*LM35Value)*1000; //The voltage value of the signal in mV is calculated after the digital conversion process.
 LMtemp = (LM35Voltage / 10); // 1 degree increment every 10mV
 lcd_gotoxy(1,1);
 printf(lcd_putc, "Temp(LM):%2.1f%cC ",LMtemp,223);
 }
 }
 
 | 
 _________________
 Best Regards...
 MCUprogrammer
 _______________________________
 Work Hard
 |  | 
	
		|  | 
	
		| temtronic 
 
 
 Joined: 01 Jul 2010
 Posts: 9589
 Location: Greensville,Ontario
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Wed Jan 11, 2023 6:08 am |   |  
				| 
 |  
				| Wow, someone using my favorite analog temperature sensor ! A 5 volt range / 8 bits gives you .01960 volts per bit.
 
 You need to change a couple of items
 1) configure the ADC to read 10 bits instead of 8
 
 2) change the ADC data variable to 16 bits.
 
 3) change adc resolution variable to 10 bits.
 
 It's hard for me to see light green on white (joys of being 70 this year ? ).
 
 I used of  100s of the LM35DZ for my remote energy control systems, never had any problems with them. Be sure to power from a well filtered supply. I had .68mfd cap on the output to 'smooth' the response. Since 'temperature control' is a slow process,consider using the 'Olympic averaging' method.  You read the sensor 10 times, toss out the highest and lowest reading, then average the 8 remaining. It's both fast and accurate.
 |  | 
	
		|  | 
	
		| Ttelmah 
 
 
 Joined: 11 Mar 2010
 Posts: 19967
 
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Wed Jan 11, 2023 6:27 am |   |  
				| 
 |  
				| and (of course), using the supply for Vref, decreases massively the accuracy you will be able to achieve.
 
 Also, save maths!...
 
  	  | Code: |  	  | LMtemp= ((ADC_VREF_VOLTAGE / ADC_RESOLUTION )*LM35Value)*100; //The voltage value of the signal in mV is calculated after the digital conversion process.
 //LMtemp = (LM35Voltage / 10); // 1 degree increment every 10mV
 
 | 
 
 Pointless to multiply by 1000, then divide by 10. Results in larger code
 and a lot of extra time. Just multiply by 100, and you have the required
 result!...
 |  | 
	
		|  | 
	
		| temtronic 
 
 
 Joined: 01 Jul 2010
 Posts: 9589
 Location: Greensville,Ontario
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Wed Jan 11, 2023 8:29 am |   |  
				| 
 |  
				| hmm...just thought of this using 'scaled integers' instead of 'float point math' is a LOT faster, smaller code and more accurate...
 |  | 
	
		|  | 
	
		| MCUprogrammer 
 
 
 Joined: 08 Sep 2020
 Posts: 233
 
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Thu Jan 12, 2023 7:58 am |   |  
				| 
 |  
				| Hi Yes, I did what you said yesterday. I saw it increase 0.5 degrees. I removed the olympic reading. I threw a 1uf capacitor to the ADC input, it reads very stable. But what I want to do is increase it by 0.1 degree. How can I do that.
 _________________
 Best Regards...
 MCUprogrammer
 _______________________________
 Work Hard
 |  | 
	
		|  | 
	
		| temtronic 
 
 
 Joined: 01 Jul 2010
 Posts: 9589
 Location: Greensville,Ontario
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Thu Jan 12, 2023 8:12 am |   |  
				| 
 |  
				| Please post your program so we 'copy/paste/compile/test. 
 Jay
 |  | 
	
		|  | 
	
		| MCUprogrammer 
 
 
 Joined: 08 Sep 2020
 Posts: 233
 
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Thu Jan 12, 2023 8:16 am |   |  
				| 
 |  
				|  	  | Code: |  	  | #include <16F886.h>
 #fuses NOWDT
 #device ADC = 10
 #use delay(crystal = 20MHz)
 
 #define LCD_ENABLE_PIN     PIN_B1
 #define LCD_RS_PIN         PIN_B0
 #define LCD_RW_PIN           0
 #define LCD_DATA4          PIN_B2
 #define LCD_DATA5          PIN_B3
 #define LCD_DATA6          PIN_B4
 #define LCD_DATA7          PIN_B5
 #include <lcd_rw.c>
 
 #define ADC_VREF_VOLTAGE     4.90
 #define ADC_RESOLUTION       1023
 
 
 #define samples 10
 
 
 
 int16 sum,max,min;
 unsigned int16 LM35_adcvalue;
 float LMtemp = 0.0;
 
 
 void main(void)
 {
 
 lcd_init();
 
 setup_adc_ports(sAN0 | sAN1 | sAN2,VSS_VDD);
 setup_adc(ADC_CLOCK_DIV_32);
 
 while(TRUE)
 {
 
 set_adc_channel(0);
 delay_us(50);
 LM35_adcvalue = read_adc();
 LMtemp = ((ADC_VREF_VOLTAGE / ADC_RESOLUTION )*LM35_adcvalue)*100; //The voltage value of the signal in mV is calculated after the digital conversion process. 1 degree increment every 10mV
 lcd_gotoxy(1,1);
 printf(lcd_putc, "Temp(LM):%2.1f%cC ",LMtemp,223);
 
 }
 
 }
 | 
 _________________
 Best Regards...
 MCUprogrammer
 _______________________________
 Work Hard
 |  | 
	
		|  | 
	
		| temtronic 
 
 
 Joined: 01 Jul 2010
 Posts: 9589
 Location: Greensville,Ontario
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Thu Jan 12, 2023 9:08 am |   |  
				| 
 |  
				| hmm.. LM35 is 10mv/*C so...
 
 21.0*C = 210 mv
 21.1*C = 211 mv
 21.2*C = 212 mv
 
 Vref= 4.90 volts
 10 bit ADC (1024 bits)
 
 4.90 /1024 is .004785 , so really 5 mv resolution ( 1 bit = 5mv )
 
 so...you need to have a .5*C change in temperature before the PIC can compute the change. IE it 'sees' 21.1 the same as 21.2...
 
 You need to feed the LM35 into a x5 opamp to increase the resolution.
 This means a temperature of 21.0*C sends 1.050 volts to the PIC's ADC.
 Now you'll be able to 'see' the small change.
 
 You'll need to do some testing to see what the actual opamp gain is ,even with 1% reisitors, you won't get exactly a gain of 5, so you'll need to multiply by the real gain value.
 |  | 
	
		|  | 
	
		| PrinceNai 
 
 
 Joined: 31 Oct 2016
 Posts: 554
 Location: Montenegro
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Thu Jan 12, 2023 9:43 am |   |  
				| 
 |  
				| As mentioned in a previous post, you can't reach 0,1deg with your current setup. Each step of A/D is 4,78mV and you want to detect 1mV change. Won't happen.One solution was offered with an opamp. Another solution is to use an external voltage reference for ADC, say 1,024V (one point zero two four volts  ). In that case you get exactly 1mV ADC resolution or 0,1deg. The limitation is that you can measure only up to 102 degrees. |  | 
	
		|  | 
	
		| Ttelmah 
 
 
 Joined: 11 Mar 2010
 Posts: 19967
 
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Fri Jan 13, 2023 1:48 am |   |  
				| 
 |  
				| Worth possibly pointing out that though the IC itself has a resolution of 0.1C, it only has an 'accuracy' of 0.5C. The non linearity is also only
 0.25C, so though with a more accurate ADC, he could display 0.1C
 steps, these will really be meaningless.
 He could get a resolution of 0.24C, by switching to using a 2.5v reference.
 This would then give 0.24C/step of the ADC, and with a proper reference
 the result will be much more repeatable and accurate.
 |  | 
	
		|  | 
	
		| MCUprogrammer 
 
 
 Joined: 08 Sep 2020
 Posts: 233
 
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Fri Jan 13, 2023 2:58 am |   |  
				| 
 |  
				| So how do I write a code for VREF 1024 on the PIC18F45K22 processor. I have added the following code of the header file.  	  | Code: |  	  | setup_vref(VREF_1v024);
 setup_adc_ports(sAN0, VSS_FVR);
 | 
 _________________
 Best Regards...
 MCUprogrammer
 _______________________________
 Work Hard
 
 Last edited by MCUprogrammer on Fri Jan 13, 2023 3:50 am; edited 4 times in total
 |  | 
	
		|  | 
	
		| MCUprogrammer 
 
 
 Joined: 08 Sep 2020
 Posts: 233
 
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Fri Jan 13, 2023 3:38 am |   |  
				| 
 |  
				| when i use VDD (4.90 / 1023)*adcval)*100;
 ~23 degrees adcval : 48
 
 It shows ((1.024/1023)*48)*100 = 4.80 degrees. So how do I set this up properly?
 _________________
 Best Regards...
 MCUprogrammer
 _______________________________
 Work Hard
 |  | 
	
		|  | 
	
		| temtronic 
 
 
 Joined: 01 Jul 2010
 Posts: 9589
 Location: Greensville,Ontario
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Fri Jan 13, 2023 7:05 am |   |  
				| 
 |  
				| re: Vref. of 1.024. OK, it took me ahwhile to find this (buried in the AC characteristics pages, not the DC ones....
 According to table 27-21 of the datasheet, parameter A21...
 
 Vrefhigh for the ADC must be a MINIMUM of VDD/2
 Which means for a VDD of 5 volts, Vref to the ADC must be >_ to 2.5 volts, so you can't use 1.024.
 
 you should post the raw ADC numbers(ADCvalue) as well as the calculated temperature.
 it could be a 'math' problem or 'casting'
 |  | 
	
		|  | 
	
		| Ttelmah 
 
 
 Joined: 11 Mar 2010
 Posts: 19967
 
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Fri Jan 13, 2023 7:15 am |   |  
				| 
 |  
				| You cannot use 1.024 as the Vref for the ADC. The minimum Vref for the ADC to work properly is 2.2v. Your chip does not have a proper internal
 Vref. The programmable voltage is just a division of the supply. The
 internal fixed voltage reference cannot be used to feed the ADC, it is
 just a voltage that can be _read_ by the ADC to given a measure of
 the supply voltage. Very low accuracy. You need to add a hardware
 external voltage reference.
 From the data sheet:
 
  	  | Quote: |  	  | The ADC voltage reference is software selectable to
 either VDD or a voltage applied to the external reference
 pins.
 
 | 
 |  | 
	
		|  | 
	
		| MCUprogrammer 
 
 
 Joined: 08 Sep 2020
 Posts: 233
 
 
 
			    
 
 | 
			
				|  |  
				|  Posted: Fri Jan 13, 2023 7:47 am |   |  
				| 
 |  
				| So what do I do to measure with 0.1 precision? _________________
 Best Regards...
 MCUprogrammer
 _______________________________
 Work Hard
 |  | 
	
		|  | 
	
		|  |