📄 touchpdd.c
字号:
/*
* Copyright (C) NEC Electronics Inc. 1998, 1999.
*
* File: Touchpdd.c
*
*
*/
const int MIN_CAL_COUNT = 10;
#include <windows.h>
#include <tchar.h>
#include <types.h>
#include <excpt.h>
#include <memory.h>
//#include <nkintr.h>
//#include <oalintr.h>
#include <kfuncs.h>
#include <tchddsi.h>
#include <drvlib.h>
#include <vrc4173.h>
#include "piu_hw.h"
INT CurrentSampleRateSetting = 0; // Low sample rate set ting
UINT16 g_SamplingPeriod;
BOOL Enabled = FALSE;
static UINT16 Xbuf[5];
static UINT16 Ybuf[5];
static int nsample;
static int cursample;
//extern DWORD gIntrTouch;// = SYSINTR_TOUCH;
//extern DWORD gIntrTouchChanged;// = SYSINTR_TOUCH_CHANGED;
//
// PDD internal support routines
//
static BOOL
EvaluateSampleVs(int p1, int p2, int p3)
{
int VsX, VsY;
int ExX, ExY;
VsX = ABS(Xbuf[p2] - Xbuf[p1]);
VsY = ABS(Ybuf[p2] - Ybuf[p1]);
ExX = Xbuf[p2]*2 - Xbuf[p1];
ExY = Ybuf[p2]*2 - Ybuf[p1];
return ABS(ExX-Xbuf[p3])<DELTA_X_COORD_VARIANCE && ABS(ExY-Ybuf[p3])<DELTA_Y_COORD_VARIANCE;
}
/*++
Routine Description:
Gathers the most recent sample and evaluates the sample returing
the determined tip state and the `best guess' for the X and Y coordinates.
Note: Determined empirically that the variance of the X coordinate of the
first sample from all other samples is large enough that in order
to keep the nominal variance small, we discard the first sample.
Cases of a light touch that locks the ADC into
seeing X and Y coordinate samples of 0x277 regardless of how the pen
moves or presses have been seen. XXXXX
Arguments:
pTipState Pointer to where the tip state information will be returned.
pUnCalX Pointer to where the x coordinate will be returned.
pUnCalY Pointer to where the y coordinate will be returned.
Return Value:
None.
Autodoc Information:
@doc IN_TOUCH_DDI INTERNAL DRIVERS PDD TOUCH_PANEL
@func VOID | PddpTouchPanelEvaluateSamples |
Gathers the most recent sample and evaluates the sample returing
the determined tip state and the `best guess' for the X and Y coordinates.
@devnote
Determined empirically that the variance of the X coordinate of the
first 2 samples from all other samples is large enough that in order
to keep the nominal variance small, we discard the first samples.
--*/
static void
PddpTouchPanelEvaluateSamples(
TOUCH_PANEL_SAMPLE_FLAGS *pSampleFlags, //@PARM Pointer to where the tip state information will be returned.
INT *pUncalX, //@PARM Pointer to where the x coordinate will be returned.
INT *pUncalY, //@PARM Pointer to where the y coordinate will be returned.
UINT PageNumber //@PARM Number of Page buffer
)
{
PIU_PENSAMPLE rgPointSamples;
PPIU_PENSAMPLE ioPenPointer;
INT p1, p2, p3, p4, p5;
INT ev;
if (PageNumber == 0) {
ioPenPointer = (PPIU_PENSAMPLE)(pVRC4173+PIUPB00REG);
} else {
ioPenPointer = (PPIU_PENSAMPLE)(pVRC4173+PIUPB10REG);
}
rgPointSamples.XSample0 = ioPenPointer->XSample0 & penDataFormatValidMask16;
rgPointSamples.XSample1 = ioPenPointer->XSample1 & penDataFormatValidMask16;
rgPointSamples.YSample0 = ioPenPointer->YSample0 & penDataFormatValidMask16;
rgPointSamples.YSample1 = ioPenPointer->YSample1 & penDataFormatValidMask16;
cursample = (cursample+1) % 5;
Xbuf[cursample] = (rgPointSamples.YSample1 + (0xFFF-rgPointSamples.YSample0)) >> 1;
Ybuf[cursample] = (rgPointSamples.XSample1 + (0xFFF-rgPointSamples.XSample0)) >> 1;
if (nsample < 5)
nsample++;
p1 = (cursample+1) % 5;
p2 = (cursample+2) % 5;
p3 = (cursample+3) % 5;
p4 = (cursample+4) % 5;
p5 = cursample;
switch (nsample) {
case 1:
*pSampleFlags = TouchSampleIgnore;
break;
case 2:
p3 = p4;
p4 = p5;
// fall through
case 3:
p2 = p3;
// fall through
case 4:
p1 = p2;
// fall through
case 5:
// Evaluate linearity of samples for large noise
ev = 0;
if (EvaluateSampleVs(p1, p2, p3)) ev |= 1;
if (EvaluateSampleVs(p2, p3, p4)) ev |= 2;
if (EvaluateSampleVs(p3, p4, p5)) ev |= 4;
switch (ev) {
case 0: // 000 reject
*pSampleFlags = TouchSampleIgnore;
break;
case 4: // 100 reject
*pSampleFlags = TouchSampleIgnore;
break;
case 1: // 001 reject
*pSampleFlags = TouchSampleIgnore;
break;
case 3: // 011 use
// OK, but don't use p1,p5
// maybe p5 is bad sample
*pSampleFlags |= TouchSampleDownFlag;
*pUncalX = (Xbuf[p2] + Xbuf[p3]*2 + Xbuf[p4]) >> 2;
*pUncalY = (Ybuf[p2] + Ybuf[p3]*2 + Ybuf[p4]) >> 2;
break;
case 6: // 110 use
// OK, but don't use p1,p5
// maybe p1 is bad sample
*pSampleFlags |= TouchSampleDownFlag;
*pUncalX = (Xbuf[p2] + Xbuf[p3]*2 + Xbuf[p4]) >> 2;
*pUncalY = (Ybuf[p2] + Ybuf[p3]*2 + Ybuf[p4]) >> 2;
break;
case 2: // 010 use
// OK, but don't use p1,p5
*pSampleFlags |= TouchSampleDownFlag;
*pUncalX = (Xbuf[p2] + Xbuf[p3]*2 + Xbuf[p4]) >> 2;
*pUncalY = (Ybuf[p2] + Ybuf[p3]*2 + Ybuf[p4]) >> 2;
break;
case 5: // 101 use
case 7: // 111 use
// OK
*pSampleFlags |= TouchSampleDownFlag;
*pUncalX = (Xbuf[p1] + Xbuf[p2]*4 + Xbuf[p3]*6 + Xbuf[p4]*4 + Xbuf[p5]) >> 4;
*pUncalY = (Ybuf[p1] + Ybuf[p2]*4 + Ybuf[p3]*6 + Ybuf[p4]*4 + Ybuf[p5]) >> 4;
break;
}
#if 0
if (*pSampleFlags & TouchSampleIgnore) {
RETAILMSG(1, (TEXT("rej\r\n")));
}
#endif
}
#if 0
if (*pSampleFlags & TouchSampleDownFlag) {
RETAILMSG(1, (TEXT("x=%d y=%d\r\n"), *pUncalX, *pUncalY));
}
#endif
}
//
// DDSI Implementation
//
// @DOC EX_TOUCH_DDSI EXTERNAL DRIVERS TOUCH_DRIVER
/* @FUNC BOOL | TouchDriverCalibrationPointGet |
Gives a single calibration point.
@XREF
<l TouchPanelReadCalibrationPoint.TouchPanelReadCalibrationPoint>
<l TouchPanelSetCalibration.TouchPanelSetCalibration>
<l TouchPanelReadCalibrationAbort.TouchPanelReadCalibrationAbort>
@COMM
This function is called to get a single calibration point, in screen
coordinates, when the input system is calibrating the touch driver. The input system
will then draw a target on the screen for the user to press on.
The driver may use the cDisplayX and cDisplayY to compute a coordinate.
It does not need to remember this computed value internally since it will
be passed back when the input system has collected all of the points and
calls <l TouchPanelSetCalibration.TouchPanelSetCalibration>.
*/
BOOL
TouchDriverCalibrationPointGet(
struct TPDC_CALIBRATION_POINT far *pTCP //@PARM pointer to returned calibration point
)
{
INT32 cDisplayWidth = pTCP -> cDisplayWidth;
INT32 cDisplayHeight = pTCP -> cDisplayHeight;
int CalibrationRadiusX = cDisplayWidth/20;
int CalibrationRadiusY = cDisplayHeight/10;
switch (pTCP -> PointNumber) {
case 0:
pTCP -> CalibrationX = cDisplayWidth/2;
pTCP -> CalibrationY = cDisplayHeight/2;
break;
case 1:
pTCP -> CalibrationX = CalibrationRadiusX*2;
pTCP -> CalibrationY = CalibrationRadiusY*2;
break;
case 2:
pTCP -> CalibrationX = CalibrationRadiusX*2;
pTCP -> CalibrationY = cDisplayHeight - CalibrationRadiusY*2;
break;
case 3:
pTCP -> CalibrationX = cDisplayWidth - CalibrationRadiusX*2;
pTCP -> CalibrationY = cDisplayHeight - CalibrationRadiusY*2;
break;
case 4:
pTCP -> CalibrationX = cDisplayWidth - CalibrationRadiusX*2;
pTCP -> CalibrationY = CalibrationRadiusY*2;
break;
default:
pTCP -> CalibrationX = cDisplayWidth/2;
pTCP -> CalibrationY = cDisplayHeight/2;
SetLastError(ERROR_INVALID_PARAMETER);
return FALSE;
}
return TRUE;
}
// @doc EX_TOUCH_DDSI EXTERNAL DRIVERS DDSI TOUCH_PANEL
//
// @func ULONG | DdsiTouchPanelGetDeviceCaps |
//
// Queries capabilities about the physical touch panel device.
//
// @parm ULONG | iIndex |
//
// Specifies the capability to query. They are one of the following:
//
// @flag TPDC_SAMPLERATE_ID |
// The sample rate.
// @flag TPDC_CALIBRATIONPOINTS_ID |
// The X and Y coordinates used for calibration.
// @flag TPDC_CALIBRATIONDATA_ID |
// The X and Y coordinates used for calibration mapping.
//
// @parm LPVOID | lpOutput |
// Points to the memory location(s) where the queried information
// will be placed. The format of the memory referenced depends on
// the setting of iIndex. If 0, returns the number of words
// required for the output data.
//
// @rdesc
// The return values is set to the amount of information supplied and depends
// on the setting of the iIndex argument.
//
// @comm
// Implemented in the PDD.
//
BOOL
DdsiTouchPanelGetDeviceCaps(
INT iIndex,
LPVOID lpOutput
)
{
struct TPDC_SAMPLE_RATE far *pTSR;
struct TPDC_CALIBRATION_POINT_COUNT far *pTCPC;
if (lpOutput == NULL) {
ERRORMSG(1, (__TEXT("TouchPanelGetDeviceCaps: invalid parameter.\r\n")));
SetLastError(ERROR_INVALID_PARAMETER);
DebugBreak();
return FALSE;
}
switch (iIndex) {
case TPDC_SAMPLE_RATE_ID:
pTSR = (struct TPDC_SAMPLE_RATE far *)lpOutput;
pTSR -> SamplesPerSecondLow = SAMPLES_PER_SECOND_DEFAULT;
pTSR -> SamplesPerSecondHigh = SAMPLES_PER_SECOND_HIGH;
pTSR -> CurrentSampleRateSetting = CurrentSampleRateSetting;
break;
case TPDC_CALIBRATION_POINT_COUNT_ID:
pTCPC = (struct TPDC_CALIBRATION_POINT_COUNT *)lpOutput;
pTCPC -> flags = 0;
pTCPC -> cCalibrationPoints = 5;
break;
case TPDC_CALIBRATION_POINT_ID:
return(TouchDriverCalibrationPointGet((struct TPDC_CALIBRATION_POINT far *)lpOutput));
default:
ERRORMSG(1, (__TEXT("TouchPanelGetDeviceCaps: invalid parameter.\r\n")));
SetLastError(ERROR_INVALID_PARAMETER);
DebugBreak();
return FALSE;
}
return TRUE;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -