Файл: Interfacing with C plus plus-programing communication with microcontrolers (K. Bentley, 2006).pdf

ВУЗ: Не указан

Категория: Не указан

Дисциплина: Не указана

Добавлен: 14.06.2025

Просмотров: 3579

Скачиваний: 1

ВНИМАНИЕ! Если данный файл нарушает Ваши авторские права, то обязательно сообщите нам.

320 10 VOLTAGE AND TEMPERATURE MEASUREMENT

Positive x

y

Origin (0,0)

Screen

-75

Positive

Boundary

getmaxy()/2

Viewport

getmaxy()/2 +75

Origin (0,0)

Viewport

Displayed

getmaxx()*1/4

Waveform

getmaxx()*3/4

Figure 10-6 Arrangement to display the VCO output.

The program will use half of the x pixel-range and one hundred and fifty pixels in the vertical direction for its Viewport, centred on-screen in both the horizontal and vertical directions. We have separated the high and low levels of the waveform by 50 pixels in the vertical direction. The functions getmaxx() and getmaxy() are functions that can be used to determine the number of pixels in the x and y directions. The Viewport is now established (with its origin located at its upper left-most corner).

The waveform can be plotted as a line joining sequential points, explained as follows (note: the positive y direction is down). When the port is read; if the signal level is high, the Y coordinate of the current point will be 50 pixels in the y direction from the Viewport Origin. If the signal level is low, the Y coordinate will be 100 pixels in the y direction from the Viewport Origin. The first VCO value read will be plotted 0 pixels from the Viewport Origin in the x direction. The next point will be plotted at x=1, the following at 2, and so on. When we reach the end in the x direction, we must re-start plotting from x=0, but not before erasing the current waveform being displayed. This plotting process will repeat continuously until the program detects a keypress and then terminates.

The required program steps can be listed as follows:

1.Initialise graphics and set the graphics mode.

2.Determine the maximum number of pixels in the x and y directions.

3.Configure the Viewport.

4.Enter a while loop conditioned on !kbhit(). If any key is pressed, terminate the program.


10 VOLTAGE AND TEMPERATURE MEASUREMENT 321

5.Read the port and obtain the output signal level of the VCO.

6.Plot the pixel according to the signal level (high or low) and increment the x pixel count.

7.If the x pixel count has not reached the end of its range, return to step 4. Else, reset the x pixel count to restart plotting, clear the view port, and return to step 4.

A program that carries out the above set of tasks is given in Listing 10-11. The appearance of the program’s display is basic and could be improved by adding some finishing touches.

Listing 10-11 Graphically display the VCO output – trace.cpp.

/***************************************************** The frequency of the pulse-train being output by the voltage-controlled oscillator will change as we change the analog input voltage to the VCO circuit. The Potentiometer (POT1) on the interface board generates the input voltage to the VCO and the program reads the pulse-train being output by the VCO. This pulse-train is graphically displayed on-screen.

*****************************************************/

#include <graphics.h> #include <stdlib.h> #include <iostream.h> #include <conio.h> #include <dos.h>

#include "vco.h"

void main()

{

VCO Vco;

int i=0; // controls plotting in the x range int SignalLevel;

int Driver = DETECT, GraphicsMode, ErrorCode; int X, Y;

//set to graphics mode initgraph(&Driver, &GraphicsMode, "");

//check for error codes

ErrorCode = graphresult(); if (ErrorCode != grOk)

{

322 10 VOLTAGE AND TEMPERATURE MEASUREMENT

cout << "Graphics error: "

<< grapherrormsg(ErrorCode) << endl; cout << "Press any key to halt:" << endl; getch();

exit(1);

}

X = getmaxx(); Y = getmaxy();

rectangle(X/4-1, Y/2-76,X*3/4+1,Y/2+76); // border setviewport(X/4, Y/2-75,X/4*3,Y/2+75,1);

while(!kbhit())

{

SignalLevel = Vco.SignalLevel(); if(SignalLevel == 0) // low level

lineto(i,100);

else // high level lineto(i,50);

i++;

delay(2);

if(i > X/2) // half screen = Viewport width

{

i = 0;

while(Vco.SignalLevel()); // wait for low level

// wait for signal level to go high again while(!Vco.SignalLevel()); clearviewport();

}

}

}

Executable File Generation

Required Files

Listing No.

Project File Contents

pport.cpp

Listing 10-8

pport.cpp

pport.h

Listing 10-7

vco.cpp

vco.cpp

Listing 10-4

vco.h

Listing 10-1

trace.cpp

Listing 10-11

trace.cpp


10 VOLTAGE AND TEMPERATURE MEASUREMENT 323

The file graphics.h is needed for all graphics-related routines such as initgraph(), grapherror(), moveto(), lineto(), etc, and for use of the constants DETECT and grOk. The class VCO is used to create an instance of VCO named Vco as in the previous program. Several variables of type int are declared inside main(). Variables X and Y will initially be used to store the maximum number of pixels in x and y directions respectively. At later stages in the program they will be used for other purposes. Variable i is used to control plotting of pixels in the Viewport’s x range. It will be reset to 0 for the start of a new plot when the trace reaches the end of the Viewport range.

The variables Driver and GraphicsMode are explained together with the initgraph() function. The first parameter to initgraph() must specify the type of graphics driver. The driver could be for the Colour Graphics Adapter (CGA), Enhanced Graphics Adapter (EGA), Video Graphics Array (VGA), etc. If the value of Driver is set to 1, then CGA is specified; if it is set to 2, EGA is specified. A description of these constants should be found in the documentation for initgraph(). A number of graphics modes will be available for each driver to generate the resolution (number of pixels) and the colour palette used. For example; 16 colour, 640 x 480 screen resolution is specified by assigning GraphicsMode the value 2. If GraphicsMode is assigned the value 1, the screen will use 16 colours and a resolution of 640 x 320. However, when the value of Driver is set to DETECT (predefined to be 0), the program will automatically detect the driver suitable for the computer’s graphics card and set the resolution to the highest available. In this situation, GraphicsMode does not need to be assigned a value. The third parameter to initgraph() is a string specifying the path to the graphics driver, in this case the location of the file EGAVGA.BGI. If the graphics driver is in your current directory (the directory where you have your executable file) then this field can have an empty string. Note that, when the call to initgraph() is made, the first two arguments are preceded by the & character. This is needed because initgraph() takes these arguments as pointers (i.e. an address value).

To determine if initgraph() has successfully completed its task, we call graphresult() and store the value returned by graphresult() in ErrorCode. If ErrorCode is not equal to the predefined constant grOk, then an error has occurred. A message corresponding to the value in ErrorCode can be generated by calling grapherrormsg(). The true clause of the if statement will display the error messages and then call the exit() function to terminate the program. If no errors occurred, program execution will proceed to carry out the next task – to determine the maximum number of pixels in x and y directions. A rectangle will be drawn just one pixel outside the chosen Viewport followed by configuration of the Viewport. As explained previously, the Viewport is the area where the waveform will be displayed. Once the Viewport is established, the origin (0,0) becomes the upper left-corner of the Viewport.

The while loop, conditioned on !kbhit(), is used to continuously display the waveform on-screen. The lineto() function uses the new coordinate frame of


324 10 VOLTAGE AND TEMPERATURE MEASUREMENT

the Viewport. The value of i will be zero when beginning to plot a new trace. A line will be drawn from the previous screen position to the new vertical position determined by the signal level. The x plot position is then incremented for the next plot. When the value of i reaches the end of its range in the x direction (Viewport width = X/2), i is reset to zero for a new plot. The remaining code synchronises the plotting so the next trace will always begin on a low level. The Viewport is then cleared to erase the current trace.

Note that since interrupts are enabled, some of the pulses displayed on-screen may have wider widths due to time consumed by interrupt service routines.

10.7 Temperature Measurement

We measure temperature indirectly by using the analog voltage generated by the thermistor resistive-divider circuit. The voltage being generated drops in a nonlinear manner as the temperature increases whan a negative temperature coefficient thermistor is used in the resistive-divider circuit (as shown in Figure 10-3). To simplify our programming let us approximate the curve by a straight line. We can develop a program that will measure the actual temperature using the same wiring as described in Section 10.6 (except the POT output is replaced with the Thermistor output, VTH). A typical thermistor/VCO relationship is shown in Figure 10-7.

10.7.1 Thermistor Calibration

The program needs to measure the cycle time of the VCO output and interpret this value as temperature. The first task is to calibrate the thermistor. This is done by subjecting the thermistor to known temperatures such as that of ice, the body, and say boiling water to obtain measures of corresponding cycle times. Then we can establish a calibration equation or calibration table which can be used to extrapolate or interpolate values of temperature (within linearity limits of the thermistor/VCO circuit response). Note that the output of the thermistor circuit may extend well beyond the linearity range of the VCO (approximately 1.5V to 3.5V). If the voltage applied to the VCO input is outside its linear range, the output from the VCO will be a distorted measure of the thermistor output. However, the temperature measuring system made up of the thermistor and VCO can still be calibrated and used, but with less accuracy.

The calibration equation can be determined as follows (refer to Figure 10-7). We can add a few extra statements to the program in Listing 10-6 to include a means of entering an upper temperature and a lower temperature. The corresponding cycle times can then be read and a calibration equation can be established. If no upper and lower temperatures are entered (HiTemp and LoTemp), the program will display the cycle time as did the program in Listing 10-6. If calibration has been performed correctly, the program will display the actual temperatures. This feature requires some logic to be built into the program. We can use flags to detect whether

10 VOLTAGE AND TEMPERATURE MEASUREMENT 325

upper and lower temperatures have been entered. If both flags are set; that is, if both temperatures have been entered, we can establish the calibration equation. Then we can display temperature instead of cycle times. We will adhere to using the same keys as for Listing 10-6; Alt-X to quit the program, up arrow to enter an upper temperature, and down arrow to enter a lower temperature.

Temperature

HiCount - LoCount

HiTemp

HiTemp - LoTemp

Temp

LoTemp

LoCount

i

HiCount

Period in Counts

Figure 10-7 Typical curve - Thermistor circuit/VCO output (calibration).

The program steps can be listed as follows:

1.Initialise a counter to zero.

2.Repeatedly check the signal level until a change is detected.

3.Repeatedly check the signal level until the second change is detected while incrementing the counter after each read.

4.Repeatedly check the signal level until the third change is detected while incrementing the counter after each read.

5.Check if the calibration temperature for upper temperature and lower temperature has been entered (respective flags are both set).

If they are both entered, use the calibration equation and display the temperature, else display the cycle time.

6.Check if a key has been pressed. If no key has been pressed return to step 1.

7.If the pressed key is Alt-X, exit the program.

8.If the up arrow key is pressed, read upper temperature. Return to step 1.

9.If the down arrow key is pressed, read lower temperature. Return to step 1.

Some of these steps can be expanded further as shown below:

8.1Ask user to enter the upper temperature and store value entered.

8.2Store the cycle time.

8.3Set the flag confirming the upper calibration temperature has been read.