QGIS API Documentation  2.99.0-Master (37c43df)
qgsrastertransparency.cpp
Go to the documentation of this file.
1 /* **************************************************************************
2  qgsrastertransparency.cpp - description
3  -------------------
4 begin : Mon Nov 30 2007
5 copyright : (C) 2007 by Peter J. Ersts
6 email : [email protected]
7 
8 ****************************************************************************/
9 
10 /* **************************************************************************
11  * *
12  * This program is free software; you can redistribute it and/or modify *
13  * it under the terms of the GNU General Public License as published by *
14  * the Free Software Foundation; either version 2 of the License, or *
15  * (at your option) any later version. *
16  * *
17  ***************************************************************************/
18 
19 #include "qgsrasterinterface.h"
20 #include "qgsrastertransparency.h"
21 #include "qgis.h"
22 #include "qgslogger.h"
23 
24 #include <QDomDocument>
25 #include <QDomElement>
26 
28 {
29 
30 }
31 
35 QList<QgsRasterTransparency::TransparentSingleValuePixel> QgsRasterTransparency::transparentSingleValuePixelList() const
36 {
37  return mTransparentSingleValuePixelList;
38 }
39 
43 QList<QgsRasterTransparency::TransparentThreeValuePixel> QgsRasterTransparency::transparentThreeValuePixelList() const
44 {
45  return mTransparentThreeValuePixelList;
46 }
47 
52 {
53  //clear the existing list
54  mTransparentSingleValuePixelList.clear();
55 
56  //add the initial value
57  TransparentSingleValuePixel myTransparentSingleValuePixel;
58  myTransparentSingleValuePixel.min = theValue;
59  myTransparentSingleValuePixel.max = theValue;
60  myTransparentSingleValuePixel.percentTransparent = 100.0;
61  mTransparentSingleValuePixelList.append( myTransparentSingleValuePixel );
62 }
63 
67 void QgsRasterTransparency::initializeTransparentPixelList( double theRedValue, double theGreenValue, double theBlueValue )
68 {
69  //clearn the existing list
70  mTransparentThreeValuePixelList.clear();
71 
72  //add the initial values
73  TransparentThreeValuePixel myTransparentThreeValuePixel;
74  myTransparentThreeValuePixel.red = theRedValue;
75  myTransparentThreeValuePixel.green = theGreenValue;
76  myTransparentThreeValuePixel.blue = theBlueValue;
77  myTransparentThreeValuePixel.percentTransparent = 100.0;
78  mTransparentThreeValuePixelList.append( myTransparentThreeValuePixel );
79 }
80 
81 
85 void QgsRasterTransparency::setTransparentSingleValuePixelList( const QList<QgsRasterTransparency::TransparentSingleValuePixel>& theNewList )
86 {
87  mTransparentSingleValuePixelList = theNewList;
88 }
89 
93 void QgsRasterTransparency::setTransparentThreeValuePixelList( const QList<QgsRasterTransparency::TransparentThreeValuePixel>& theNewList )
94 {
95  mTransparentThreeValuePixelList = theNewList;
96 }
97 
104 int QgsRasterTransparency::alphaValue( double theValue, int theGlobalTransparency ) const
105 {
106  //if NaN return 0, transparent
107  if ( qIsNaN( theValue ) )
108  {
109  return 0;
110  }
111 
112  //Search through the transparency list looking for a match
113  bool myTransparentPixelFound = false;
114  TransparentSingleValuePixel myTransparentPixel = {0, 0, 100};
115  for ( int myListRunner = 0; myListRunner < mTransparentSingleValuePixelList.count(); myListRunner++ )
116  {
117  myTransparentPixel = mTransparentSingleValuePixelList[myListRunner];
118  if (( theValue >= myTransparentPixel.min && theValue <= myTransparentPixel.max ) ||
119  qgsDoubleNear( theValue, myTransparentPixel.min ) ||
120  qgsDoubleNear( theValue, myTransparentPixel.max ) )
121  {
122  myTransparentPixelFound = true;
123  break;
124  }
125  }
126 
127  //if a match was found use the stored transparency percentage
128  if ( myTransparentPixelFound )
129  {
130  return static_cast< int >( static_cast< float >( theGlobalTransparency ) *( 1.0 - ( myTransparentPixel.percentTransparent / 100.0 ) ) );
131  }
132 
133  return theGlobalTransparency;
134 }
135 
144 int QgsRasterTransparency::alphaValue( double theRedValue, double theGreenValue, double theBlueValue, int theGlobalTransparency ) const
145 {
146  //if NaN return 0, transparent
147  if ( qIsNaN( theRedValue ) || qIsNaN( theGreenValue ) || qIsNaN( theBlueValue ) )
148  {
149  return 0;
150  }
151 
152  //Search through the transparency list looking for a match
153  bool myTransparentPixelFound = false;
154  TransparentThreeValuePixel myTransparentPixel = {0, 0, 0, 100};
155  for ( int myListRunner = 0; myListRunner < mTransparentThreeValuePixelList.count(); myListRunner++ )
156  {
157  myTransparentPixel = mTransparentThreeValuePixelList[myListRunner];
158  if ( qgsDoubleNear( myTransparentPixel.red, theRedValue ) )
159  {
160  if ( qgsDoubleNear( myTransparentPixel.green, theGreenValue ) )
161  {
162  if ( qgsDoubleNear( myTransparentPixel.blue, theBlueValue ) )
163  {
164  myTransparentPixelFound = true;
165  break;
166  }
167  }
168  }
169  }
170 
171  //if a match was found use the stored transparency percentage
172  if ( myTransparentPixelFound )
173  {
174  return static_cast< int >( static_cast< float >( theGlobalTransparency ) *( 1.0 - ( myTransparentPixel.percentTransparent / 100.0 ) ) );
175  }
176 
177  return theGlobalTransparency;
178 }
179 
181 {
182  return mTransparentSingleValuePixelList.isEmpty() && mTransparentThreeValuePixelList.isEmpty();
183 }
184 
185 void QgsRasterTransparency::writeXml( QDomDocument& doc, QDomElement& parentElem ) const
186 {
187  QDomElement rasterTransparencyElem = doc.createElement( QStringLiteral( "rasterTransparency" ) );
188  if ( !mTransparentSingleValuePixelList.isEmpty() )
189  {
190  QDomElement singleValuePixelListElement = doc.createElement( QStringLiteral( "singleValuePixelList" ) );
191  QList<QgsRasterTransparency::TransparentSingleValuePixel>::const_iterator it = mTransparentSingleValuePixelList.constBegin();
192  for ( ; it != mTransparentSingleValuePixelList.constEnd(); ++it )
193  {
194  QDomElement pixelListElement = doc.createElement( QStringLiteral( "pixelListEntry" ) );
195  pixelListElement.setAttribute( QStringLiteral( "min" ), QgsRasterBlock::printValue( it->min ) );
196  pixelListElement.setAttribute( QStringLiteral( "max" ), QgsRasterBlock::printValue( it->max ) );
197  pixelListElement.setAttribute( QStringLiteral( "percentTransparent" ), QString::number( it->percentTransparent ) );
198  singleValuePixelListElement.appendChild( pixelListElement );
199  }
200  rasterTransparencyElem.appendChild( singleValuePixelListElement );
201 
202  }
203  if ( !mTransparentThreeValuePixelList.isEmpty() )
204  {
205  QDomElement threeValuePixelListElement = doc.createElement( QStringLiteral( "threeValuePixelList" ) );
206  QList<QgsRasterTransparency::TransparentThreeValuePixel>::const_iterator it = mTransparentThreeValuePixelList.constBegin();
207  for ( ; it != mTransparentThreeValuePixelList.constEnd(); ++it )
208  {
209  QDomElement pixelListElement = doc.createElement( QStringLiteral( "pixelListEntry" ) );
210  pixelListElement.setAttribute( QStringLiteral( "red" ), QgsRasterBlock::printValue( it->red ) );
211  pixelListElement.setAttribute( QStringLiteral( "green" ), QgsRasterBlock::printValue( it->green ) );
212  pixelListElement.setAttribute( QStringLiteral( "blue" ), QgsRasterBlock::printValue( it->blue ) );
213  pixelListElement.setAttribute( QStringLiteral( "percentTransparent" ), QString::number( it->percentTransparent ) );
214  threeValuePixelListElement.appendChild( pixelListElement );
215  }
216  rasterTransparencyElem.appendChild( threeValuePixelListElement );
217  }
218  parentElem.appendChild( rasterTransparencyElem );
219 }
220 
221 void QgsRasterTransparency::readXml( const QDomElement& elem )
222 {
223  if ( elem.isNull() )
224  {
225  return;
226  }
227 
228  mTransparentSingleValuePixelList.clear();
229  mTransparentThreeValuePixelList.clear();
230  QDomElement currentEntryElem;
231 
232  QDomElement singlePixelListElem = elem.firstChildElement( QStringLiteral( "singleValuePixelList" ) );
233  if ( !singlePixelListElem.isNull() )
234  {
235  QDomNodeList entryList = singlePixelListElem.elementsByTagName( QStringLiteral( "pixelListEntry" ) );
237  for ( int i = 0; i < entryList.size(); ++i )
238  {
239  currentEntryElem = entryList.at( i ).toElement();
240  sp.percentTransparent = currentEntryElem.attribute( QStringLiteral( "percentTransparent" ) ).toDouble();
241  // Backward compoatibility < 1.9 : pixelValue (before ranges)
242  if ( currentEntryElem.hasAttribute( QStringLiteral( "pixelValue" ) ) )
243  {
244  sp.min = sp.max = currentEntryElem.attribute( QStringLiteral( "pixelValue" ) ).toDouble();
245  }
246  else
247  {
248  sp.min = currentEntryElem.attribute( QStringLiteral( "min" ) ).toDouble();
249  sp.max = currentEntryElem.attribute( QStringLiteral( "max" ) ).toDouble();
250  }
251  mTransparentSingleValuePixelList.append( sp );
252  }
253  }
254  QDomElement threeValuePixelListElem = elem.firstChildElement( QStringLiteral( "threeValuePixelList" ) );
255  if ( !threeValuePixelListElem.isNull() )
256  {
257  QDomNodeList entryList = threeValuePixelListElem.elementsByTagName( QStringLiteral( "pixelListEntry" ) );
259  for ( int i = 0; i < entryList.size(); ++i )
260  {
261  currentEntryElem = entryList.at( i ).toElement();
262  tp.red = currentEntryElem.attribute( QStringLiteral( "red" ) ).toDouble();
263  tp.green = currentEntryElem.attribute( QStringLiteral( "green" ) ).toDouble();
264  tp.blue = currentEntryElem.attribute( QStringLiteral( "blue" ) ).toDouble();
265  tp.percentTransparent = currentEntryElem.attribute( QStringLiteral( "percentTransparent" ) ).toDouble();
266  mTransparentThreeValuePixelList.append( tp );
267  }
268  }
269 }
bool isEmpty() const
True if there are no entries in the pixel lists except the nodata value.
static QString printValue(double value)
Print double value with all necessary significant digits.
int alphaValue(double, int theGlobalTransparency=255) const
Returns the transparency value for a single value Pixel.
void setTransparentThreeValuePixelList(const QList< TransparentThreeValuePixel > &theNewList)
Mutator for transparentThreeValuePixelList.
bool qgsDoubleNear(double a, double b, double epsilon=4 *DBL_EPSILON)
Compare two doubles (but allow some difference)
Definition: qgis.h:196
void readXml(const QDomElement &elem)
QList< QgsRasterTransparency::TransparentSingleValuePixel > transparentSingleValuePixelList() const
Accessor for transparentSingleValuePixelList.
void setTransparentSingleValuePixelList(const QList< TransparentSingleValuePixel > &theNewList)
Mutator for transparentSingleValuePixelList.
void writeXml(QDomDocument &doc, QDomElement &parentElem) const
QList< QgsRasterTransparency::TransparentThreeValuePixel > transparentThreeValuePixelList() const
Accessor for transparentThreeValuePixelList.
void initializeTransparentPixelList(double)
Reset to the transparency list to a single value.