Skip to content

Commit 372b731

Browse files
committedSep 1, 2014
Fixed bugs with feature count, maintenance of QgsLegendSymbolItemV2
1 parent f96484f commit 372b731

11 files changed

+125
-87
lines changed
 

‎python/core/qgsmaplayerlegend.sip

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -34,24 +34,26 @@ class QgsLayerTreeModelLegendNode : QObject
3434
};
3535

3636

37+
3738
/**
3839
* Implementation of legend node interface for displaying preview of vector symbols and their labels
3940
* and allowing interaction with the symbol / renderer.
4041
*
4142
* @note added in 2.6
4243
*/
44+
/*
4345
class QgsSymbolV2LegendNode : QgsLayerTreeModelLegendNode
4446
{
4547
%TypeHeaderCode
4648
#include <qgsmaplayerlegend.h>
4749
%End
4850
public:
49-
QgsSymbolV2LegendNode( QgsLayerTreeLayer* nodeLayer, QgsSymbolV2* symbol, const QString& label, int rendererRef = -1 );
51+
QgsSymbolV2LegendNode( QgsLayerTreeLayer* nodeLayer, const QgsLegendSymbolItemV2& item );
5052

5153
virtual Qt::ItemFlags flags() const;
5254
virtual QVariant data( int role ) const;
5355
virtual bool setData( const QVariant& value, int role );
54-
};
56+
};*/
5557

5658

5759
/**

‎src/core/composer/qgscomposerlegenditem.cpp

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,7 @@ void QgsComposerLegendItem::writeXMLChildren( QDomElement& elem, QDomDocument& d
6464
////////////////QgsComposerBaseSymbolItem
6565

6666
QgsComposerBaseSymbolItem::QgsComposerBaseSymbolItem()
67-
: QgsComposerLegendItem( QgsComposerLegendStyle::Symbol )
67+
: QgsComposerLegendItem( QgsComposerLegendStyle::Symbol )
6868
{
6969

7070
}
@@ -162,7 +162,7 @@ QgsComposerSymbolV2Item::QgsComposerSymbolV2Item()
162162
}
163163

164164
QgsComposerSymbolV2Item::QgsComposerSymbolV2Item( const QgsLegendSymbolItemV2& item )
165-
: mItem( item )
165+
: mItem( item )
166166
{
167167
setFlags( Qt::ItemIsEnabled | Qt::ItemIsSelectable );
168168
}
@@ -189,7 +189,7 @@ QVariant QgsComposerSymbolV2Item::data( int role ) const
189189
if ( role == Qt::DecorationRole )
190190
{
191191
if ( mIcon.isNull() )
192-
mIcon = QgsSymbolLayerV2Utils::symbolPreviewIcon( mItem.symbol, QSize( 30, 30 ) );
192+
mIcon = QgsSymbolLayerV2Utils::symbolPreviewIcon( mItem.symbol(), QSize( 30, 30 ) );
193193
return mIcon;
194194
}
195195
else if ( role == Qt::DisplayRole || role == Qt::EditRole )
@@ -202,7 +202,7 @@ QVariant QgsComposerSymbolV2Item::data( int role ) const
202202
// so that single symbol layers are still drawn on single line
203203
if ( parentLayerItem()->rowCount() > 1 || !lbl.isEmpty() )
204204
{
205-
lbl += QString( " [%1]" ).arg( parentVectorLayer()->featureCount( mItem.symbol ) );
205+
lbl += QString( " [%1]" ).arg( parentVectorLayer()->featureCount( mItem.legacyRuleKey() ) );
206206
}
207207
}
208208
return lbl;
@@ -219,14 +219,14 @@ QStandardItem* QgsComposerSymbolV2Item::clone() const
219219
void QgsComposerSymbolV2Item::writeXML( QDomElement& elem, QDomDocument& doc ) const
220220
{
221221
QDomElement vectorClassElem = doc.createElement( "VectorClassificationItemNg" );
222-
if ( mItem.symbol )
222+
if ( mItem.symbol() )
223223
{
224224
QgsSymbolV2Map saveSymbolMap;
225-
saveSymbolMap.insert( "classificationSymbol", mItem.symbol );
225+
saveSymbolMap.insert( "classificationSymbol", mItem.symbol() );
226226
QDomElement symbolsElem = QgsSymbolLayerV2Utils::saveSymbols( saveSymbolMap, "symbols", doc );
227227
vectorClassElem.appendChild( symbolsElem );
228228
}
229-
vectorClassElem.setAttribute( "text", mItem.label );
229+
vectorClassElem.setAttribute( "text", mItem.label() );
230230
vectorClassElem.setAttribute( "userText", userText() );
231231
elem.appendChild( vectorClassElem );
232232
}
@@ -240,7 +240,7 @@ void QgsComposerSymbolV2Item::readXML( const QDomElement& itemElem, bool xServer
240240
return;
241241
}
242242

243-
mItem.label = itemElem.attribute( "text", "" );
243+
mItem.setLabel( itemElem.attribute( "text", "" ) );
244244
setUserText( itemElem.attribute( "userText", "" ) );
245245
QDomElement symbolsElem = itemElem.firstChildElement( "symbols" );
246246
if ( !symbolsElem.isNull() )
@@ -253,10 +253,10 @@ void QgsComposerSymbolV2Item::readXML( const QDomElement& itemElem, bool xServer
253253
QgsSymbolV2* symbolNg = mapIt.value();
254254
if ( symbolNg )
255255
{
256-
delete mItem.symbol;
257-
mItem.symbol = symbolNg;
256+
mItem.setSymbol( symbolNg );
258257
}
259258
}
259+
qDeleteAll( loadSymbolMap );
260260
}
261261
}
262262

@@ -267,7 +267,7 @@ void QgsComposerSymbolV2Item::setSymbolV2( QgsSymbolV2* s )
267267

268268
QSizeF QgsComposerSymbolV2Item::drawSymbol( const QgsLegendSettings& settings, ItemContext* ctx, double itemHeight ) const
269269
{
270-
QgsSymbolV2* s = mItem.symbol;
270+
QgsSymbolV2* s = mItem.symbol();
271271
if ( !s )
272272
{
273273
return QSizeF();
@@ -422,7 +422,7 @@ QString QgsComposerSymbolV2Item::label() const
422422
}
423423
else
424424
{
425-
return mItem.label;
425+
return mItem.label();
426426
}
427427
}
428428
}
@@ -435,8 +435,8 @@ QgsComposerRasterSymbolItem::QgsComposerRasterSymbolItem()
435435
}
436436

437437
QgsComposerRasterSymbolItem::QgsComposerRasterSymbolItem( const QColor& color, const QString& label )
438-
: mColor( color )
439-
, mLabel( label )
438+
: mColor( color )
439+
, mLabel( label )
440440
{
441441
}
442442

@@ -519,7 +519,7 @@ QgsComposerRasterImageItem::QgsComposerRasterImageItem()
519519
}
520520

521521
QgsComposerRasterImageItem::QgsComposerRasterImageItem( const QImage& image )
522-
: mImage( image )
522+
: mImage( image )
523523
{
524524

525525
}

‎src/core/composer/qgscomposerlegenditem.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -156,7 +156,7 @@ class CORE_EXPORT QgsComposerSymbolV2Item : public QgsComposerBaseSymbolItem
156156
@deprecated */
157157
Q_DECL_DEPRECATED void setSymbolV2( QgsSymbolV2* s );
158158
/** @deprecated */
159-
Q_DECL_DEPRECATED QgsSymbolV2* symbolV2() const { return mItem.symbol; }
159+
Q_DECL_DEPRECATED QgsSymbolV2* symbolV2() const { return mItem.symbol(); }
160160

161161
ItemType itemType() const { return SymbologyV2Item; }
162162

@@ -165,7 +165,7 @@ class CORE_EXPORT QgsComposerSymbolV2Item : public QgsComposerBaseSymbolItem
165165
QSizeF drawSymbol( const QgsLegendSettings& settings, ItemContext* ctx, double itemHeight ) const;
166166

167167
//! @note added in 2.6
168-
QString ruleKey() const { return mItem.key; }
168+
QString ruleKey() const { return mItem.ruleKey(); }
169169

170170
//! @note added in 2.6
171171
const QgsLegendSymbolItemV2& itemData() const { return mItem; }

‎src/core/composer/qgslegendmodel.cpp

Lines changed: 4 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -35,8 +35,8 @@
3535
#include <QMessageBox>
3636

3737
QgsLegendModel::QgsLegendModel()
38-
: QStandardItemModel()
39-
, mAutoUpdate( true )
38+
: QStandardItemModel()
39+
, mAutoUpdate( true )
4040
{
4141
setColumnCount( 2 );
4242

@@ -160,7 +160,7 @@ void QgsLegendModel::setLayerSet( const QStringList& layerIds, double scaleDenom
160160
if ( !sItem )
161161
continue;
162162

163-
if ( sItem->itemData().label == rule )
163+
if ( sItem->itemData().label() == rule )
164164
{
165165
QStandardItem* takenSItem = lItem->takeChild( j );
166166
lItem->removeRows( 0, lItem->rowCount() );
@@ -189,13 +189,9 @@ void QgsLegendModel::setLayerSet( const QStringList& layerIds, double scaleDenom
189189
if ( !sItem )
190190
continue;
191191

192-
if ( sItem->itemData().scaleDenomMin > 0 && sItem->itemData().scaleDenomMax > 0 &&
193-
( sItem->itemData().scaleDenomMin > scaleDenominator || sItem->itemData().scaleDenomMax < scaleDenominator ) )
194-
{
192+
if ( !sItem->itemData().isScaleOK( scaleDenominator ) )
195193
lItem->removeRow( j );
196-
}
197194
}
198-
199195
}
200196
}
201197
}

‎src/core/qgsmaplayerlegend.cpp

Lines changed: 10 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -68,23 +68,21 @@ bool QgsLayerTreeModelLegendNode::setData( const QVariant& value, int role )
6868
// -------------------------------------------------------------------------
6969

7070

71-
QgsSymbolV2LegendNode::QgsSymbolV2LegendNode( QgsLayerTreeLayer* nodeLayer, QgsSymbolV2* symbol, const QString& label, const QString& ruleKey )
71+
QgsSymbolV2LegendNode::QgsSymbolV2LegendNode( QgsLayerTreeLayer* nodeLayer, const QgsLegendSymbolItemV2& item )
7272
: QgsLayerTreeModelLegendNode( nodeLayer )
73-
, mSymbol( symbol ? symbol->clone() : 0 )
74-
, mLabel( label )
75-
, mRuleKey( ruleKey )
73+
, mItem( item )
7674
{
77-
if ( nodeLayer->customProperty( "showFeatureCount", 0 ).toBool() && symbol )
75+
mLabel = mItem.label();
76+
if ( nodeLayer->customProperty( "showFeatureCount", 0 ).toBool() && mItem.legacyRuleKey() )
7877
{
7978
QgsVectorLayer* vl = qobject_cast<QgsVectorLayer*>( nodeLayer->layer() );
8079
if ( vl )
81-
mLabel += QString( " [%1]" ).arg( vl->featureCount( symbol ) );
80+
mLabel += QString( " [%1]" ).arg( vl->featureCount( mItem.legacyRuleKey() ) );
8281
}
8382
}
8483

8584
QgsSymbolV2LegendNode::~QgsSymbolV2LegendNode()
8685
{
87-
delete mSymbol;
8886
}
8987

9088
Qt::ItemFlags QgsSymbolV2LegendNode::flags() const
@@ -105,8 +103,8 @@ QVariant QgsSymbolV2LegendNode::data( int role ) const
105103
else if ( role == Qt::DecorationRole )
106104
{
107105
QSize iconSize( 16, 16 ); // TODO: configurable
108-
if ( mIcon.isNull() && mSymbol )
109-
mIcon = QgsSymbolLayerV2Utils::symbolPreviewPixmap( mSymbol, iconSize );
106+
if ( mIcon.isNull() && mItem.symbol() )
107+
mIcon = QgsSymbolLayerV2Utils::symbolPreviewPixmap( mItem.symbol(), iconSize );
110108
return mIcon;
111109
}
112110
else if ( role == Qt::CheckStateRole )
@@ -121,7 +119,7 @@ QVariant QgsSymbolV2LegendNode::data( int role ) const
121119
if ( !vlayer || !vlayer->rendererV2() )
122120
return QVariant();
123121

124-
return vlayer->rendererV2()->legendSymbolItemChecked( mRuleKey ) ? Qt::Checked : Qt::Unchecked;
122+
return vlayer->rendererV2()->legendSymbolItemChecked( mItem.ruleKey() ) ? Qt::Checked : Qt::Unchecked;
125123
}
126124

127125
return QVariant();
@@ -139,7 +137,7 @@ bool QgsSymbolV2LegendNode::setData( const QVariant& value, int role )
139137
if ( !vlayer || !vlayer->rendererV2() )
140138
return false;
141139

142-
vlayer->rendererV2()->checkLegendSymbolItem( mRuleKey, value == Qt::Checked );
140+
vlayer->rendererV2()->checkLegendSymbolItem( mItem.ruleKey(), value == Qt::Checked );
143141

144142
if ( mParent->isVisible() )
145143
vlayer->clearCacheImage();
@@ -192,7 +190,7 @@ QList<QgsLayerTreeModelLegendNode*> QgsDefaultVectorLayerLegend::createLayerTree
192190

193191
foreach ( const QgsLegendSymbolItemV2& i, r->legendSymbolItemsV2() )
194192
{
195-
nodes.append( new QgsSymbolV2LegendNode( nodeLayer, i.symbol, i.label, i.key ) );
193+
nodes.append( new QgsSymbolV2LegendNode( nodeLayer, i ) );
196194
}
197195
return nodes;
198196
}

‎src/core/qgsmaplayerlegend.h

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,7 @@ class CORE_EXPORT QgsLayerTreeModelLegendNode : public QObject
6161
QgsLayerTreeLayer* mParent;
6262
};
6363

64+
#include "qgslegendsymbolitemv2.h"
6465

6566
/**
6667
* Implementation of legend node interface for displaying preview of vector symbols and their labels
@@ -71,18 +72,17 @@ class CORE_EXPORT QgsLayerTreeModelLegendNode : public QObject
7172
class CORE_EXPORT QgsSymbolV2LegendNode : public QgsLayerTreeModelLegendNode
7273
{
7374
public:
74-
QgsSymbolV2LegendNode( QgsLayerTreeLayer* nodeLayer, QgsSymbolV2* symbol, const QString& label, const QString& ruleKey = QString() );
75+
QgsSymbolV2LegendNode( QgsLayerTreeLayer* nodeLayer, const QgsLegendSymbolItemV2& item );
7576
~QgsSymbolV2LegendNode();
7677

7778
virtual Qt::ItemFlags flags() const;
7879
virtual QVariant data( int role ) const;
7980
virtual bool setData( const QVariant& value, int role );
8081

8182
private:
82-
QgsSymbolV2* mSymbol;
83+
QgsLegendSymbolItemV2 mItem;
8384
mutable QIcon mIcon; // cached symbol preview
8485
QString mLabel;
85-
QString mRuleKey;
8686
};
8787

8888

‎src/core/symbology-ng/qgslegendsymbolitemv2.cpp

Lines changed: 41 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -3,45 +3,66 @@
33
#include "qgssymbolv2.h"
44

55
QgsLegendSymbolItemV2::QgsLegendSymbolItemV2()
6-
: symbol( 0 )
7-
, scaleDenomMin( -1 )
8-
, scaleDenomMax( -1 )
6+
: mSymbol( 0 )
7+
, mOriginalSymbolPointer( 0 )
8+
, mScaleMinDenom( -1 )
9+
, mScaleMaxDenom( -1 )
910
{
1011
}
1112

12-
QgsLegendSymbolItemV2::QgsLegendSymbolItemV2( QgsSymbolV2* s, const QString& lbl, const QString& k )
13-
: symbol( s )
14-
, label( lbl )
15-
, key( k )
16-
, scaleDenomMin( -1 )
17-
, scaleDenomMax( -1 )
13+
QgsLegendSymbolItemV2::QgsLegendSymbolItemV2( QgsSymbolV2* symbol, const QString& label, const QString& ruleKey, int scaleMinDenom, int scaleMaxDenom )
14+
: mSymbol( symbol ? symbol->clone() : 0 )
15+
, mLabel( label )
16+
, mKey( ruleKey )
17+
, mOriginalSymbolPointer( symbol )
18+
, mScaleMinDenom( scaleMinDenom )
19+
, mScaleMaxDenom( scaleMaxDenom )
1820
{
1921
}
2022

2123
QgsLegendSymbolItemV2::QgsLegendSymbolItemV2( const QgsLegendSymbolItemV2& other )
22-
: symbol( 0 )
23-
, scaleDenomMin( -1 )
24-
, scaleDenomMax( -1 )
24+
: mSymbol( 0 )
25+
, mOriginalSymbolPointer( 0 )
2526
{
2627
*this = other;
2728
}
2829

2930
QgsLegendSymbolItemV2::~QgsLegendSymbolItemV2()
3031
{
31-
delete symbol;
32+
delete mSymbol;
3233
}
3334

34-
QgsLegendSymbolItemV2& QgsLegendSymbolItemV2::operator=( const QgsLegendSymbolItemV2& other )
35+
QgsLegendSymbolItemV2& QgsLegendSymbolItemV2::operator=( const QgsLegendSymbolItemV2 & other )
3536
{
3637
if ( this == &other )
3738
return *this;
3839

39-
delete symbol;
40-
symbol = other.symbol ? other.symbol->clone() : 0;
41-
label = other.label;
42-
key = other.key;
43-
scaleDenomMin = other.scaleDenomMin;
44-
scaleDenomMax = other.scaleDenomMax;
40+
setSymbol( other.mSymbol ? other.mSymbol->clone() : 0 );
41+
mLabel = other.mLabel;
42+
mKey = other.mKey;
43+
mOriginalSymbolPointer = other.mOriginalSymbolPointer;
44+
mScaleMinDenom = other.mScaleMinDenom;
45+
mScaleMaxDenom = other.mScaleMaxDenom;
4546

4647
return *this;
4748
}
49+
50+
bool QgsLegendSymbolItemV2::isScaleOK( double scale ) const
51+
{
52+
if ( scale <= 0 )
53+
return true;
54+
if ( mScaleMinDenom <= 0 && mScaleMaxDenom <= 0 )
55+
return true;
56+
if ( mScaleMinDenom > 0 && mScaleMinDenom > scale )
57+
return false;
58+
if ( mScaleMaxDenom > 0 && mScaleMaxDenom < scale )
59+
return false;
60+
return true;
61+
}
62+
63+
void QgsLegendSymbolItemV2::setSymbol( QgsSymbolV2* s )
64+
{
65+
delete mSymbol;
66+
mSymbol = s ? s->clone() : 0;
67+
mOriginalSymbolPointer = s;
68+
}

‎src/core/symbology-ng/qgslegendsymbolitemv2.h

Lines changed: 43 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -5,24 +5,51 @@
55

66
class QgsSymbolV2;
77

8+
/**
9+
* The class stores information about one class/rule of a vector layer renderer in a unified way
10+
* that can be used by legend model for rendering of legend.
11+
*
12+
* @note added in 2.6
13+
*/
814
class CORE_EXPORT QgsLegendSymbolItemV2
915
{
10-
public:
11-
QgsLegendSymbolItemV2();
12-
//! construct item, takes ownership of symbol
13-
QgsLegendSymbolItemV2( QgsSymbolV2* s, const QString& lbl, const QString& k );
14-
~QgsLegendSymbolItemV2();
15-
QgsLegendSymbolItemV2( const QgsLegendSymbolItemV2& other );
16-
QgsLegendSymbolItemV2& operator=( const QgsLegendSymbolItemV2& other );
17-
18-
QgsSymbolV2* symbol; //!< owned by the struct
19-
QString label;
20-
QString key; //!< identifier of the symbol item (within renderer)
21-
22-
// additional data that may be used for filtering
23-
24-
int scaleDenomMin;
25-
int scaleDenomMax;
16+
public:
17+
QgsLegendSymbolItemV2();
18+
//! construct item, does not take ownership of symbol (makes internal clone)
19+
QgsLegendSymbolItemV2( QgsSymbolV2* symbol, const QString& label, const QString& ruleKey, int scaleMinDenom = -1, int scaleMaxDenom = -1 );
20+
~QgsLegendSymbolItemV2();
21+
QgsLegendSymbolItemV2( const QgsLegendSymbolItemV2& other );
22+
QgsLegendSymbolItemV2& operator=( const QgsLegendSymbolItemV2& other );
23+
24+
QgsSymbolV2* symbol() const { return mSymbol; }
25+
QString label() const { return mLabel; }
26+
QString ruleKey() const { return mKey; }
27+
28+
//! used for older code that identifies legend entries from symbol pointer within renderer
29+
QgsSymbolV2* legacyRuleKey() const { return mOriginalSymbolPointer; }
30+
31+
bool isScaleOK( double scale ) const;
32+
int scaleMinDenom() const { return mScaleMinDenom; }
33+
int scaleMaxDenom() const { return mScaleMaxDenom; }
34+
35+
//! takes ownership of symbol
36+
void setSymbol( QgsSymbolV2* s );
37+
void setLabel( const QString& label ) { mLabel = label; }
38+
39+
private:
40+
//! symbol. owned by the struct. can be null.
41+
QgsSymbolV2* mSymbol;
42+
//! label of the item (may be empty or non-unique)
43+
QString mLabel;
44+
//! unique identifier of the symbol item (within renderer)
45+
QString mKey;
46+
47+
QgsSymbolV2* mOriginalSymbolPointer;
48+
49+
// additional data that may be used for filtering
50+
51+
int mScaleMinDenom;
52+
int mScaleMaxDenom;
2653
};
2754

2855

‎src/core/symbology-ng/qgsrendererv2.cpp

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -539,11 +539,7 @@ QgsLegendSymbolListV2 QgsFeatureRendererV2::legendSymbolItemsV2() const
539539
int i = 0;
540540
for ( QgsLegendSymbolList::const_iterator it = lst.begin(); it != lst.end(); ++it, ++i )
541541
{
542-
QgsLegendSymbolItemV2 item;
543-
item.symbol = it->second ? it->second->clone() : 0;
544-
item.label = it->first;
545-
item.key = QString::number( i );
546-
lst2 << item;
542+
lst2 << QgsLegendSymbolItemV2( it->second, it->first, QString::number( i ) );
547543
}
548544
return lst2;
549545
}

‎src/core/symbology-ng/qgsrulebasedrendererv2.cpp

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -216,9 +216,7 @@ QgsLegendSymbolListV2 QgsRuleBasedRendererV2::Rule::legendSymbolItemsV2() const
216216
QgsLegendSymbolListV2 lst;
217217
if ( mSymbol )
218218
{
219-
lst << QgsLegendSymbolItemV2( mSymbol->clone(), mLabel, mRuleKey );
220-
lst.last().scaleDenomMin = mScaleMinDenom;
221-
lst.last().scaleDenomMax = mScaleMaxDenom;
219+
lst << QgsLegendSymbolItemV2( mSymbol, mLabel, mRuleKey, mScaleMinDenom, mScaleMaxDenom );
222220
}
223221

224222
for ( RuleList::const_iterator it = mChildren.constBegin(); it != mChildren.constEnd(); ++it )

‎src/core/symbology-ng/qgssinglesymbolrendererv2.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -370,6 +370,6 @@ QgsLegendSymbolList QgsSingleSymbolRendererV2::legendSymbolItems( double scaleDe
370370
QgsLegendSymbolListV2 QgsSingleSymbolRendererV2::legendSymbolItemsV2() const
371371
{
372372
QgsLegendSymbolListV2 lst;
373-
lst << QgsLegendSymbolItemV2( mSymbol.data() ? mSymbol->clone() : 0, QString(), 0 );
373+
lst << QgsLegendSymbolItemV2( mSymbol.data(), QString(), 0 );
374374
return lst;
375375
}

0 commit comments

Comments
 (0)
Please sign in to comment.