Skip to content

Commit 3af9d40

Browse files
author
rblazek
committed
region check
git-svn-id: http://svn.osgeo.org/qgis/trunk/qgis@5082 c8812cc2-4d05-0410-92ff-de0c093fc19c
1 parent 7354757 commit 3af9d40

File tree

2 files changed

+302
-32
lines changed

2 files changed

+302
-32
lines changed

src/plugins/grass/qgsgrassmodule.cpp

Lines changed: 277 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,7 @@
6969
#include <QPushButton>
7070
#include <QGroupBox>
7171
#include <QFileDialog>
72+
#include <QProcess>
7273

7374
#include "qgis.h"
7475
#include "qgsapplication.h"
@@ -233,10 +234,9 @@ QgsGrassModule::QgsGrassModule ( QgsGrassTools *tools, QgisApp *qgisApp, QgisIfa
233234
mManualTextBrowser->setSource ( manPath );
234235
}
235236

236-
connect ( &mProcess, SIGNAL(readyReadStdout()), this, SLOT(readStdout()));
237-
connect ( &mProcess, SIGNAL(readyReadStderr()), this, SLOT(readStderr()));
238-
connect ( &mProcess, SIGNAL(launchFinished()), this, SLOT(finished()));
239-
connect ( &mProcess, SIGNAL(processExited()), this, SLOT(finished()));
237+
connect ( &mProcess, SIGNAL(readyReadStandardOutput()), this, SLOT(readStdout()));
238+
connect ( &mProcess, SIGNAL(readyReadStandardError()), this, SLOT(readStderr()));
239+
connect ( &mProcess, SIGNAL(finished(int,QProcess::ExitStatus)), this, SLOT(finished(int,QProcess::ExitStatus)));
240240

241241
char *env = "GRASS_MESSAGE_FORMAT=gui";
242242
char *envstr = new char[strlen(env)+1];
@@ -543,6 +543,172 @@ QStringList QgsGrassModuleStandardOptions::ready()
543543
return list;
544544
}
545545

546+
QStringList QgsGrassModuleStandardOptions::checkRegion()
547+
{
548+
#ifdef QGISDEBUG
549+
std::cerr << "QgsGrassModuleStandardOptions::checkRegion()" << std::endl;
550+
#endif
551+
QStringList list;
552+
553+
struct Cell_head currentWindow;
554+
if ( !QgsGrass::region ( QgsGrass::getDefaultGisdbase(),
555+
QgsGrass::getDefaultLocation(),
556+
QgsGrass::getDefaultMapset(), &currentWindow ) )
557+
{
558+
QMessageBox::warning( 0, "Warning", "Cannot get current region" );
559+
return list;
560+
}
561+
562+
for ( int i = 0; i < mItems.size(); i++ )
563+
{
564+
if ( typeid(*(mItems[i])) != typeid (QgsGrassModuleInput) ) {
565+
continue;
566+
}
567+
568+
struct Cell_head window;
569+
570+
QgsGrassModuleInput *item = dynamic_cast<QgsGrassModuleInput *>
571+
(mItems[i]);
572+
573+
int mapType;
574+
switch ( item->type() ) {
575+
case QgsGrassModuleInput::Raster :
576+
mapType = QgsGrass::Raster;
577+
break;
578+
case QgsGrassModuleInput::Vector :
579+
mapType = QgsGrass::Vector;
580+
break;
581+
}
582+
583+
if ( !QgsGrass::mapRegion ( mapType,
584+
QgsGrass::getDefaultGisdbase(),
585+
QgsGrass::getDefaultLocation(), "", item->currentMap(),
586+
&window ) )
587+
{
588+
QMessageBox::warning( 0, "Warning", "Cannot check region "
589+
"of map " + item->currentMap() );
590+
continue;
591+
}
592+
593+
if ( G_window_overlap ( &currentWindow ,
594+
window.north, window.south, window.east, window.west) == 0 )
595+
{
596+
list.append ( item->currentMap() );
597+
}
598+
}
599+
600+
return list;
601+
}
602+
603+
bool QgsGrassModuleStandardOptions::inputRegion ( struct Cell_head *window, bool all )
604+
{
605+
#ifdef QGISDEBUG
606+
std::cerr << "QgsGrassModuleStandardOptions::inputRegion()" << std::endl;
607+
#endif
608+
609+
// Get current resolution
610+
if ( !QgsGrass::region ( QgsGrass::getDefaultGisdbase(),
611+
QgsGrass::getDefaultLocation(),
612+
QgsGrass::getDefaultMapset(), window ) )
613+
{
614+
QMessageBox::warning( 0, "Warning", "Cannot get current region" );
615+
return false;
616+
}
617+
618+
int rasterCount = 0;
619+
int vectorCount = 0;
620+
for ( int i = 0; i < mItems.size(); i++ )
621+
{
622+
if ( typeid(*(mItems[i])) != typeid (QgsGrassModuleInput) ) {
623+
continue;
624+
}
625+
626+
// TODO all flag
627+
628+
struct Cell_head mapWindow;
629+
630+
QgsGrassModuleInput *item = dynamic_cast<QgsGrassModuleInput *>
631+
(mItems[i]);
632+
633+
int mapType;
634+
switch ( item->type() ) {
635+
case QgsGrassModuleInput::Raster :
636+
mapType = QgsGrass::Raster;
637+
break;
638+
case QgsGrassModuleInput::Vector :
639+
mapType = QgsGrass::Vector;
640+
break;
641+
}
642+
643+
if ( !QgsGrass::mapRegion ( mapType,
644+
QgsGrass::getDefaultGisdbase(),
645+
QgsGrass::getDefaultLocation(), "", item->currentMap(),
646+
&mapWindow ) )
647+
{
648+
QMessageBox::warning( 0, "Warning", "Cannot set region "
649+
"of map " + item->currentMap() );
650+
return false;
651+
}
652+
653+
// TODO: best way to set resolution ?
654+
if ( item->type() == QgsGrassModuleInput::Raster
655+
&& rasterCount == 0 )
656+
{
657+
QgsGrass::copyRegionResolution ( &mapWindow, window );
658+
}
659+
if ( rasterCount + vectorCount == 0 )
660+
{
661+
QgsGrass::copyRegionExtent ( &mapWindow, window );
662+
}
663+
else
664+
{
665+
QgsGrass::extendRegion ( &mapWindow, window );
666+
}
667+
668+
if ( item->type() == QgsGrassModuleInput::Raster )
669+
rasterCount++;
670+
else if ( item->type() == QgsGrassModuleInput::Vector )
671+
vectorCount++;
672+
}
673+
674+
G_adjust_Cell_head3 ( window, 0, 0, 0 );
675+
676+
return true;
677+
}
678+
679+
bool QgsGrassModuleStandardOptions::usesRegion ()
680+
{
681+
#ifdef QGISDEBUG
682+
std::cerr << "QgsGrassModuleStandardOptions::usesRegion()" << std::endl;
683+
#endif
684+
685+
for ( int i = 0; i < mItems.size(); i++ )
686+
{
687+
if ( typeid(*(mItems[i])) == typeid (QgsGrassModuleInput) )
688+
{
689+
QgsGrassModuleInput *item =
690+
dynamic_cast<QgsGrassModuleInput *>(mItems[i]);
691+
692+
if ( item->type() == QgsGrassModuleInput::Raster )
693+
return true;
694+
}
695+
696+
if ( typeid(*(mItems[i])) == typeid (QgsGrassModuleOption) )
697+
{
698+
QgsGrassModuleOption *item =
699+
dynamic_cast<QgsGrassModuleOption *> ( mItems[i] );
700+
701+
if ( item->isOutput()
702+
&& item->outputType() == QgsGrassModuleOption::Raster )
703+
{
704+
return true;
705+
}
706+
}
707+
}
708+
709+
return false;
710+
}
711+
546712
QgsGrassModuleStandardOptions::~QgsGrassModuleStandardOptions()
547713
{
548714
}
@@ -703,18 +869,16 @@ void QgsGrassModule::run()
703869
std::cerr << "QgsGrassModule::run()" << std::endl;
704870
#endif
705871

706-
if ( mProcess.isRunning() ) {
872+
if ( mProcess.state() == QProcess::Running ) {
707873
mProcess.kill();
708874
mRunButton->setText( tr("Run") );
709875
} else {
710-
QString command;
876+
//QString command;
877+
QStringList arguments;
711878

712-
if ( mProcess.isRunning() ) {
713-
}
714-
715-
mProcess.clearArguments();
716-
mProcess.addArgument( mXName );
717-
command = mXName;
879+
//mProcess.clearArguments();
880+
//mProcess.addArgument( mXName );
881+
//command = mXName;
718882

719883
// Check if options are ready
720884
QStringList readyErrors = mOptions->ready();
@@ -729,6 +893,55 @@ void QgsGrassModule::run()
729893
return;
730894
}
731895

896+
// Check/set region
897+
struct Cell_head tempWindow;
898+
bool resetRegion = false;
899+
if ( mOptions->requestsRegion() )
900+
{
901+
if ( !mOptions->inputRegion ( &tempWindow, false ) )
902+
{
903+
QMessageBox::warning ( 0, "Warning", "Cannot get input region" );
904+
return;
905+
}
906+
resetRegion = true;
907+
}
908+
else if ( mOptions->usesRegion() )
909+
{
910+
QStringList outsideRegion = mOptions->checkRegion();
911+
if ( outsideRegion.size() > 0 )
912+
{
913+
if ( QgsGrass::versionMajor() >= 6 && QgsGrass::versionMinor() >= 1 )
914+
{
915+
int ret = QMessageBox::question ( 0, "Warning",
916+
"Input " + outsideRegion.join(",")
917+
+ " outside current region!",
918+
"Use input region", "Continue", "Cancel" );
919+
920+
if ( ret == 2 ) return;
921+
if ( ret == 0 ) resetRegion = true;
922+
}
923+
else
924+
{
925+
int ret = QMessageBox::question ( 0, "Warning",
926+
"Input " + outsideRegion.join(",")
927+
+ " outside current region!",
928+
"Continue", "Cancel" );
929+
930+
if ( ret == 1 ) return;
931+
}
932+
933+
if ( resetRegion )
934+
{
935+
if ( !mOptions->inputRegion ( &tempWindow, true ) )
936+
{
937+
QMessageBox::warning ( 0, "Warning",
938+
"Cannot get input region" );
939+
return;
940+
}
941+
}
942+
}
943+
}
944+
732945
// Check if output exists
733946
QStringList outputExists = mOptions->checkOutput();
734947
if ( outputExists.size() > 0 )
@@ -743,8 +956,9 @@ void QgsGrassModule::run()
743956
// r.mapcalc does not use standard parser
744957
if ( typeid(*mOptions) != typeid(QgsGrassMapcalc) )
745958
{
746-
mProcess.addArgument( "--o" );
747-
command.append ( " --o" );
959+
arguments.append ( "--o" );
960+
//mProcess.addArgument( "--o" );
961+
//command.append ( " --o" );
748962
}
749963
}
750964

@@ -760,8 +974,9 @@ void QgsGrassModule::run()
760974

761975
for ( QStringList::Iterator it = list.begin(); it != list.end(); ++it ) {
762976
std::cerr << "option: " << (*it).toLocal8Bit().data() << std::endl;
763-
command.append ( " " + *it );
764-
mProcess.addArgument( *it );
977+
//command.append ( " " + *it );
978+
arguments.append ( *it );
979+
//mProcess.addArgument( *it );
765980
}
766981

767982
/* WARNING - TODO: there was a bug in GRASS 6.0.0 / 6.1.CVS (< 2005-04-29):
@@ -773,28 +988,53 @@ void QgsGrassModule::run()
773988
*/
774989
putenv ( "GISRC_MODE_MEMORY" ); // unset
775990

776-
mProcess.start( );
777-
778-
std::cerr << "command" << command.toLocal8Bit().data() << std::endl;
779991
mOutputTextBrowser->clear();
780992

781-
command.replace ( "&", "&amp;" );
782-
command.replace ( "<", "&lt;" );
783-
command.replace ( ">", "&gt;" );
784-
mOutputTextBrowser->append( "<B>" + command + "</B>" );
993+
QString commandHtml = mXName + " " + arguments.join(" ");
994+
995+
std::cerr << "command: " << commandHtml.toLocal8Bit().data() << std::endl;
996+
commandHtml.replace ( "&", "&amp;" );
997+
commandHtml.replace ( "<", "&lt;" );
998+
commandHtml.replace ( ">", "&gt;" );
999+
mOutputTextBrowser->append( "<B>" + commandHtml + "</B>" );
1000+
1001+
// Warning: it is not useful to write requested region to WIND file and
1002+
// reset then to original beacuse it is reset before
1003+
// the region is read by a module even if waitForStarted() is used
1004+
// -> necessary to pass region as enviroment variable
1005+
// but the feature is available in GRASS 6.1 only since 23.3.2006
1006+
1007+
QStringList env;
1008+
1009+
if ( resetRegion )
1010+
{
1011+
env = QProcess::systemEnvironment();
1012+
QString reg = QgsGrass::regionString( &tempWindow );
1013+
std::cerr << "reg: " << reg.ascii() << std::endl;
1014+
env.append ( "GRASS_REGION=" + reg );
1015+
}
1016+
mProcess.setEnvironment ( env );
1017+
1018+
mProcess.start( mXName, arguments );
1019+
1020+
if ( resetRegion )
1021+
{
1022+
}
1023+
7851024
mTabWidget->setCurrentPage(1);
7861025
mRunButton->setText( tr("Stop") );
7871026
}
7881027
}
7891028

790-
void QgsGrassModule::finished()
1029+
void QgsGrassModule::finished(int exitCode, QProcess::ExitStatus exitStatus )
7911030
{
7921031
#ifdef QGISDEBUG
7931032
std::cerr << "QgsGrassModule::finished()" << std::endl;
7941033
#endif
7951034

796-
if ( mProcess.normalExit() ) {
797-
if ( mProcess.exitStatus () == 0 ) {
1035+
std::cerr << "exitCode = " << exitCode << std::endl;
1036+
if ( exitStatus == QProcess::NormalExit ) {
1037+
if ( exitCode == 0 ) {
7981038
mOutputTextBrowser->append( "<B>Successfully finished</B>" );
7991039
mProgressBar->setProgress ( 100, 100 );
8001040
mSuccess = true;
@@ -815,8 +1055,11 @@ void QgsGrassModule::readStdout()
8151055
#endif
8161056

8171057
QString line;
818-
while ( mProcess.canReadLineStdout() ) {
819-
line = QString::fromLocal8Bit( mProcess.readLineStdout().ascii() );
1058+
mProcess.setReadChannel ( QProcess::StandardOutput );
1059+
while ( mProcess.canReadLine() ) {
1060+
//line = QString::fromLocal8Bit( mProcess.readLineStdout().ascii() );
1061+
QByteArray ba = mProcess.readLine();
1062+
line = QString::fromLocal8Bit( QString(ba).ascii() );
8201063
mOutputTextBrowser->append ( line );
8211064
}
8221065
}
@@ -827,6 +1070,8 @@ void QgsGrassModule::readStderr()
8271070
std::cerr << "QgsGrassModule::readStderr()" << std::endl;
8281071
#endif
8291072

1073+
mProcess.setReadChannel ( QProcess::StandardError );
1074+
8301075
QString line;
8311076
QRegExp rxpercent ( "GRASS_INFO_PERCENT: (\\d+)" );
8321077
QRegExp rxmessage ( "GRASS_INFO_MESSAGE\\(\\d+,\\d+\\): (.*)" );
@@ -835,8 +1080,10 @@ void QgsGrassModule::readStderr()
8351080
QRegExp rxend ( "GRASS_INFO_END\\(\\d+,\\d+\\)" );
8361081

8371082

838-
while ( mProcess.canReadLineStderr() ) {
839-
line = QString::fromLocal8Bit( mProcess.readLineStderr().ascii() );
1083+
while ( mProcess.canReadLine() ) {
1084+
//line = QString::fromLocal8Bit( mProcess.readLineStderr().ascii() );
1085+
QByteArray ba = mProcess.readLine();
1086+
line = QString::fromLocal8Bit( QString(ba).ascii() );
8401087
//std::cerr << "stderr: " << line << std::endl;
8411088

8421089
if ( rxpercent.search ( line ) != -1 ) {

0 commit comments

Comments
 (0)