📄 grayf.cpp
字号:
/*************************************************************************
This software module was originally developed by
Ming-Chieh Lee (mingcl@microsoft.com), Microsoft Corporation
Wei-ge Chen (wchen@microsoft.com), Microsoft Corporation
Bruce Lin (blin@microsoft.com), Microsoft Corporation
Chuang Gu (chuanggu@microsoft.com), Microsoft Corporation
(date: March, 1996)
in the course of development of the MPEG-4 Video (ISO/IEC 14496-2).
This software module is an implementation of a part of one or more MPEG-4 Video tools
as specified by the MPEG-4 Video.
ISO/IEC gives users of the MPEG-4 Video free license to this software module or modifications
thereof for use in hardware or software products claiming conformance to the MPEG-4 Video.
Those intending to use this software module in hardware or software products are advised that its use may infringe existing patents.
The original developer of this software module and his/her company,
the subsequent editors and their companies,
and ISO/IEC have no liability for use of this software module or modifications thereof in an implementation.
Copyright is not released for non MPEG-4 Video conforming products.
Microsoft retains full right to use the code for his/her own purpose,
assign or donate the code to a third party and to inhibit third parties from using the code for non <MPEG standard> conforming products.
This copyright notice must be included in all copies or derivative works.
Copyright (c) 1996, 1997.
Module Name:
grayf.hpp
Abstract:
Float image class for gray (one-plane) pictures
Revision History:
*************************************************************************/
#include <stdlib.h>
#include <math.h>
#include <stdio.h>
#include <string.h>
#include "typeapi.h"
#ifdef __MFC_
#ifdef _DEBUG
#undef THIS_FILE
static char BASED_CODE THIS_FILE[] = __FILE__;
#endif
#define new DEBUG_NEW
#endif // __MFC_
CFloatImage::~CFloatImage ()
{
delete [] m_ppxlf;
m_ppxlf = NULL;
}
Void CFloatImage::allocate (const CRct& r, PixelF pxlf)
{
m_rc = r;
delete [] m_ppxlf, m_ppxlf = NULL;
// allocate pixels and initialize
if (m_rc.empty ()) return;
m_ppxlf = new PixelF [m_rc.area ()];
PixelF* ppxlf = m_ppxlf;
UInt area = where ().area ();
for (UInt i = 0; i < area; i++)
*ppxlf++ = pxlf;
}
Void CFloatImage::copyConstruct (const CFloatImage& fi, const CRct& rct)
{
CRct r = rct;
if (!r.valid())
r = fi.where ();
if (!fi.valid () || (!fi.m_rc.empty () && fi.m_ppxlf == NULL))
assert (FALSE);
allocate (r, (PixelF) 0);
if (!valid ()) return;
// Copy data
if (r == fi.where ())
memcpy (m_ppxlf, fi.pixels (), m_rc.area () * sizeof (PixelF));
else {
r.clip (fi.where ()); // find the intersection
CoordI x = r.left; // copy pixels
Int cbLine = r.width * sizeof (PixelF);
PixelF* ppxl = (PixelF*) pixels (x, r.top);
const PixelF* ppxlFi = fi.pixels (x, r.top);
Int widthCurr = where ().width;
Int widthFi = fi.where ().width;
for (CoordI y = r.top; y < r.bottom; y++) {
memcpy (ppxl, ppxlFi, cbLine);
ppxl += widthCurr;
ppxlFi += widthFi;
}
}
}
Void CFloatImage::swap (CFloatImage& fi)
{
assert (this && &fi);
CRct rcT = fi.m_rc;
fi.m_rc = m_rc;
m_rc = rcT;
PixelF* ppxlfT = fi.m_ppxlf;
fi.m_ppxlf = m_ppxlf;
m_ppxlf = ppxlfT;
}
CFloatImage::CFloatImage (const CFloatImage& fi, const CRct& r) : m_ppxlf (NULL)
{
copyConstruct (fi, r);
}
CFloatImage::CFloatImage (const CIntImage& ii, const CRct& rct) : m_ppxlf (NULL)
{
CRct r = rct;
if (!r.valid())
r = ii.where ();
if (!ii.valid ())
assert (FALSE);
allocate (r, (PixelF) 0);
if (!valid ()) return;
// Copy data
if (r == ii.where ())
{
Int i;
PixelF *ppxlf = m_ppxlf;
const PixelI *ppxli = ii.pixels();
for(i=m_rc.area();i;i--)
*ppxlf++ = (PixelF)*ppxli++;
}
else {
r.clip (ii.where ()); // find the intersection
CoordI x = r.left; // copy pixels
Int cbLine = r.width;
PixelF* ppxlf = (PixelF*) pixels (x, r.top);
const PixelI* ppxli = ii.pixels (x, r.top);
Int widthCurr = where ().width;
Int widthii = ii.where ().width;
for (CoordI y = r.top; y < r.bottom; y++) {
for(x = 0;x<cbLine;x++)
ppxlf[x]=(PixelF)ppxli[x];
ppxlf += widthCurr;
ppxli += widthii;
}
}
}
CFloatImage::CFloatImage (const CRct& r, PixelF px) : m_ppxlf (NULL)
{
allocate (r, px);
}
CFloatImage::CFloatImage (const CVideoObjectPlane& vop, RGBA comp, const CRct& r) : m_ppxlf (NULL)
{
if (!vop.valid ()) return;
CFloatImage* pfi = new CFloatImage (vop.where ());
PixelF* ppxlf = (PixelF*) pfi -> pixels ();
const CPixel* ppxl = vop.pixels ();
UInt area = pfi -> where ().area ();
for (UInt ip = 0; ip < area; ip++, ppxl++)
*ppxlf++ = (PixelF) ppxl -> pxlU.color [comp];
copyConstruct (*pfi, r);
delete pfi;
}
CFloatImage::CFloatImage (
const Char* pchFileName,
UInt ifr,
const CRct& rct,
UInt nszHeader ) : m_ppxlf (NULL)
{
assert (!rct.empty ());
assert (ifr >= 0);
assert (nszHeader >= 0);
UInt area = rct.area ();
// allocate mem for buffers
U8* pchBuffer = new U8 [area];
U8* pchBuffer0 = pchBuffer;
// read data from a file
FILE* fpSrc = fopen (pchFileName, "rb");
assert (fpSrc != NULL);
fseek (fpSrc, nszHeader + ifr * sizeof (U8) * area, SEEK_SET);
Int size = (Int) fread (pchBuffer, sizeof (U8), area, fpSrc);
assert (size != 0);
fclose (fpSrc);
// assign buffers to a vframe
allocate (rct, .0f);
PixelF* p = (PixelF*) pixels ();
UInt areaThis = where ().area ();
for (UInt ip = 0; ip < areaThis; ip++)
*p++ = (PixelF) *pchBuffer0++;
delete [] pchBuffer;
}
CFloatImage::CFloatImage (const Char* vdlFileName) : m_ppxlf (NULL)// read from a VM file.
{
CVideoObjectPlane vop (vdlFileName);
allocate (vop.where (), 0.0f);
const CPixel* ppxlVop = vop.pixels ();
PixelF* ppxlfRet = (PixelF*) pixels ();
UInt area = where ().area ();
for (UInt ip = 0; ip < area; ip++, ppxlfRet++, ppxlVop++)
*ppxlfRet = (PixelF) ppxlVop -> pxlU.rgb.r;
}
Void CFloatImage::where (const CRct& r)
{
if (!valid ()) return;
if (where () == r) return;
CFloatImage* pfi = new CFloatImage (*this, r);
swap (*pfi);
delete pfi;
}
CRct CFloatImage::boundingBox (const PixelF pxlfOutsideColor) const
{
if (allValue ((PixelF) pxlfOutsideColor))
return CRct ();
CoordI left = where ().right - 1;
CoordI top = where ().bottom - 1;
CoordI right = where ().left;
CoordI bottom = where ().top;
const PixelF* ppxlfThis = pixels ();
for (CoordI y = where ().top; y < where ().bottom; y++) {
for (CoordI x = where ().left; x < where ().right; x++) {
if (*ppxlfThis != (PixelF) pxlfOutsideColor) {
left = min (left, x);
top = min (top, y);
right = max (right, x);
bottom = max (bottom, y);
}
ppxlfThis++;
}
}
right++;
bottom++;
return (CRct (left, top, right, bottom));
}
Double CFloatImage::mean () const
{
if (where ().empty ()) return 0;
Double meanRet = 0;
PixelF* ppxlf = (PixelF*) pixels ();
UInt area = where ().area ();
for (UInt ip = 0; ip < area; ip++)
meanRet += *ppxlf++;
meanRet /= area;
return meanRet;
}
Double CFloatImage::mean (const CFloatImage* pfiMsk) const
{
assert (where () == pfiMsk -> where ()); // no compute if rects are different
if (where ().empty ()) return 0;
Double meanRet = 0;
PixelF* ppxlf = (PixelF*) pixels ();
const PixelF* ppxlfMsk = pfiMsk -> pixels ();
UInt area = where ().area ();
UInt uiNumNonTransp = 0;
for (UInt ip = 0; ip < area; ip++, ppxlf++, ppxlfMsk++) {
if (*ppxlfMsk != transpValueF) {
uiNumNonTransp++;
meanRet += *ppxlf;
}
}
meanRet /= uiNumNonTransp;
return meanRet;
}
Double CFloatImage::sumAbs (const CRct& rct) const
{
CRct rctToDo = (!rct.valid ()) ? where () : rct;
Double dblRet = 0;
if (rctToDo == where ()) {
const PixelF* ppxlf = pixels ();
UInt area = where ().area ();
for (UInt ip = 0; ip < area; ip++, ppxlf++) {
if (*ppxlf > 0)
dblRet += *ppxlf;
else
dblRet -= *ppxlf;
}
}
else {
Int width = where ().width;
const PixelF* ppxlfRow = pixels (rct.left, rct.top);
for (CoordI y = rctToDo.top; y < rctToDo.bottom; y++) {
const PixelF* ppxlf = ppxlfRow;
for (CoordI x = rctToDo.left; x < rctToDo.right; x++, ppxlf++) {
if (*ppxlf > 0)
dblRet += *ppxlf;
else
dblRet -= *ppxlf;
}
ppxlfRow += width;
}
}
return dblRet;
}
Double CFloatImage::sumDeviation (const CFloatImage* pfiMsk) const // sum of first-order deviation
{
Double meanPxl = mean (pfiMsk);
Double devRet = 0;
PixelF* ppxlf = (PixelF*) pixels ();
const PixelF* ppxlfMsk = pfiMsk -> pixels ();
UInt area = where ().area ();
for (UInt ip = 0; ip < area; ip++, ppxlf++, ppxlfMsk++) {
if (*ppxlfMsk != transpValueF) {
Float fDiff = *ppxlf - (Float) meanPxl;
if (fDiff > 0)
devRet += fDiff;
else
devRet -= fDiff;
}
}
return devRet;
}
Double CFloatImage::sumDeviation () const // sum of first-order deviation
{
Double meanPxl = mean ();
Double devRet = 0;
PixelF* ppxlf = (PixelF*) pixels ();
UInt area = where ().area ();
for (UInt ip = 0; ip < area; ip++, ppxlf++) {
Float fDiff = *ppxlf - (Float) meanPxl;
if (fDiff > 0)
devRet += fDiff;
else
devRet -= fDiff;
}
return devRet;
}
Bool CFloatImage::allValue (Float vl, const CRct& rct) const
{
Int ivl = (Int) vl;
Bool bRet = TRUE;
CRct rctToDo = (!rct.valid ()) ? where () : rct;
if (rctToDo == where ()) {
const PixelF* ppxlf = pixels ();
UInt area = where ().area ();
for (UInt ip = 0; ip < area; ip++, ppxlf++) {
Int ipxl = (Int) *ppxlf; //truncation
// if (*ppxlf != vl) {
if (ipxl != ivl) {
bRet = FALSE;
return bRet;
}
}
}
else {
Int width = where ().width;
const PixelF* ppxlf = pixels (rct.left, rct.top);
for (CoordI y = rctToDo.top; y < rctToDo.bottom; y++) {
const PixelF* ppxlfRow = ppxlf;
for (CoordI x = rctToDo.left; x < rctToDo.right; x++, ppxlfRow++) {
Int ipxl = (Int) *ppxlfRow; //truncation
// if (*ppxlfRow != vl) {
if (ipxl != ivl) {
bRet = FALSE;
return bRet;
}
}
ppxlf += width;
}
}
return bRet;
}
Bool CFloatImage::biLevel (const CRct& rct) const
{
Bool bRet = TRUE;
CRct rctToDo = (!rct.valid ()) ? where () : rct;
if (rctToDo == where ()) {
const PixelF* ppxlf = pixels ();
UInt area = where ().area ();
for (UInt ip = 0; ip < area; ip++, ppxlf++) {
Int ipxl = (Int) *ppxlf; //truncation
if (ipxl != opaqueValue && ipxl != transpValue ) {
bRet = FALSE;
return bRet;
}
}
}
else {
Int width = where ().width;
const PixelF* ppxlf = pixels (rct.left, rct.top);
for (CoordI y = rctToDo.top; y < rctToDo.bottom; y++) {
const PixelF* ppxlfRow = ppxlf;
for (CoordI x = rctToDo.left; x < rctToDo.right; x++, ppxlfRow++) {
Int ipxl = (Int) *ppxlfRow; //truncation
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -