private void setdf() throws Exception {

        float per = 1;
        // direction factor, where the components are 1/length
        double[] directionFactor = calculateDirectionFactor(xRes, yRes);

        dir = new int[nCols][nRows];
        apool = new int[nCols][nRows];

        /*
         * Initialise internal pointers, if the point is an invalid value then set the dir value to
         * -1 else to 0
         */
        pm.message(msg.message("pitfiller.initpointers"));
        for( int r = firstRow; r < lastRow; r++ ) {
            if (pm.isCanceled()) {
                return;
            }
            for( int c = firstCol; c < lastCol; c++ ) {
                if (r == firstRow || r == lastRow - 1 || c == firstCol || c == lastCol - 1
                        || isNovalue(pitIter.getSampleDouble(c, r, 0))) {
                    dir[c][r] = -1;
                } else {
                    dir[c][r] = 0;
                }
            }
        }

        pm.message(msg.message("pitfiller.setpos"));

        /* Set positive slope directions - store unresolved on stack */
        currentPitsCount = 0;
        for( int r = (firstRow + 1); r < (lastRow - 1); r++ ) {
            if (pm.isCanceled()) {
                return;
            }
            for( int c = (firstCol + 1); c < (lastCol - 1); c++ ) {
                double pitValue = pitIter.getSampleDouble(c, r, 0);
                if (!isNovalue(pitValue)) {
                    // set the value in the dir matrix (D8 matrix)
                    setDirection(pitValue, r, c, dir, directionFactor);
                }
                /*
                 * Put unresolved pixels (which have, in the dir matrix, 0 as value) on stack
                 * addstack method increased nis by one unit
                 */
                if (dir[c][r] == 0) {
                    addPitToStack(r, c);
                }
            }
        }

        /* routine to drain flats to neighbors */
        int stillPitsCount = resolveFlats(currentPitsCount);
        if (stillPitsCount == -1) {
            return;
        }

        // for( int i = 0; i < currentPitRows.length; i++ ) {
        // int r = currentPitRows[i];
        // int c = currentPitCols[i];
        // System.out.println("row/cols = " + r + "/" + c);
        // }

        int n = currentPitsCount;
        pm.message(msg.message("pitfiller.numpit") + n);
        int np1 = n;
        int nt = (int) (np1 * 1 - per / 100);

        /* initialize apool to zero */
        // for( int i = firstRow; i < lastRow; i++ ) {
        // if (pm.isCanceled()) {
        // return;
        // }
        // for( int j = firstCol; j < lastCol; j++ ) {
        // apool[j][i] = 0;
        // }
        // }

        pm.message(msg.message("pitfiller.main"));
        pm.message(msg.message("pitfiller.perc"));
        pm.message("0%");
        /* store unresolved stack location in apool for easy deletion */
        while( currentPitsCount > 0 ) {
            if (pm.isCanceled()) {
                return;
            }
            // set the index to the lowest point in the map, during the
            // iteration, which filled the elevation map, the lowest point will
            // changed
            int r = currentPitRows[stillPitsCount];
            int c = currentPitCols[stillPitsCount];
            pooln = 1;
            nf = 0;/* reset flag to that new min elev is found */
            // calculate recursively the pool
            int npool = pool(r, c, 0);

            /*
             * Find the pour point of the pool: the lowest point on the edge of the pool
             */
            for( int ip = 1; ip <= npool; ip++ ) {
                if (pm.isCanceled()) {
                    return;
                }
                r = ipool[ip];
                c = jpool[ip];
                for( int k = 1; k <= 8; k++ ) {
                    int jn = c + DIR_WITHFLOW_EXITING_INVERTED[k][0];
                    int in = r + DIR_WITHFLOW_EXITING_INVERTED[k][1];
                    // if the point isn't in this pool but on the edge then
                    // check the minimun elevation edge
                    if (apool[jn][in] != pooln) {
                        et = max2(pitIter.getSampleDouble(c, r, 0), pitIter.getSampleDouble(jn, in, 0));
                        if (nf == 0) {
                            emin = et;
                            nf = 1;
                        } else {
                            if (emin > et) {
                                emin = et;
                            }
                        }
                    }
                }
            }

            /* Fill the pool */
            for( int k = 1; k <= npool; k++ ) {
                if (pm.isCanceled()) {
                    return;
                }
                r = ipool[k];
                c = jpool[k];
                if (pitIter.getSampleDouble(c, r, 0) <= emin) {
                    if (dir[c][r] > 0) { /* Can be in pool, but not flat */
                        dir[c][r] = 0;
                        addPitToStack(r, c);
                    }

                    for( int ip = 1; ip <= 8; ip++ ) {
                        int jn = c + DIR_WITHFLOW_EXITING_INVERTED[ip][0];
                        int in = r + DIR_WITHFLOW_EXITING_INVERTED[ip][1];
                        if ((pitIter.getSampleDouble(jn, in, 0) > pitIter.getSampleDouble(c, r, 0)) && (dir[jn][in] > 0)) {
                            /*
                             * Only zero direction of neighbors that are higher - because lower or
                             * equal may be a pour point in a pit that must not be disrupted
                             */
                            dir[jn][in] = 0;
                            addPitToStack(in, jn);
                        }
                    }
                    pitIter.setSample(c, r, 0, emin);
                }
                apool[c][r] = 0;
            }

            /* reset unresolved stack */
            int ni = 0;
            for( int ip = 1; ip <= currentPitsCount; ip++ ) {
                if (pm.isCanceled()) {
                    return;
                }
                setDirection(pitIter.getSampleDouble(currentPitCols[ip], currentPitRows[ip], 0), currentPitRows[ip],
                        currentPitCols[ip], dir, directionFactor);

                if (dir[currentPitCols[ip]][currentPitRows[ip]] == 0) {
                    ni++;
                    currentPitRows[ni] = currentPitRows[ip];
                    currentPitCols[ni] = currentPitCols[ip];
                }
            }

            n = currentPitsCount;

            stillPitsCount = resolveFlats(ni);
            if (stillPitsCount == -1) {
                return;
            }
            // System.out.println(nis);
            if (currentPitsCount < nt) {
                if (per % 10 == 0)
                    pm.message((int) per + "%");
                per = per + 1;
                nt = (int) (np1 * (1 - per / 100));
            }
        }
        pm.message("OmsPitfiller finished...");
    }
private void setdf ( ) throws Exception { float per = 1 ; double [ ] directionFactor = calculateDirectionFactor ( xRes , yRes ) ; dir = new int [ nCols ] [ nRows ] ; apool = new int [ nCols ] [ nRows ] ; pm . message ( msg . message ( "pitfiller.initpointers" ) ) ; for ( int r = firstRow ; r < lastRow ; r ++ ) { if ( pm . isCanceled ( ) ) { return ; } for ( int c = firstCol ; c < lastCol ; c ++ ) { if ( r == firstRow || r == lastRow - 1 || c == firstCol || c == lastCol - 1 || isNovalue ( pitIter . getSampleDouble ( c , r , 0 ) ) ) { dir [ c ] [ r ] = - 1 ; } else { dir [ c ] [ r ] = 0 ; } } } pm . message ( msg . message ( "pitfiller.setpos" ) ) ; currentPitsCount = 0 ; for ( int r = ( firstRow + 1 ) ; r < ( lastRow - 1 ) ; r ++ ) { if ( pm . isCanceled ( ) ) { return ; } for ( int c = ( firstCol + 1 ) ; c < ( lastCol - 1 ) ; c ++ ) { double pitValue = pitIter . getSampleDouble ( c , r , 0 ) ; if ( ! isNovalue ( pitValue ) ) { setDirection ( pitValue , r , c , dir , directionFactor ) ; } if ( dir [ c ] [ r ] == 0 ) { addPitToStack ( r , c ) ; } } } int stillPitsCount = resolveFlats ( currentPitsCount ) ; if ( stillPitsCount == - 1 ) { return ; } int n = currentPitsCount ; pm . message ( msg . message ( "pitfiller.numpit" ) + n ) ; int np1 = n ; int nt = ( int ) ( np1 * 1 - per / 100 ) ; pm . message ( msg . message ( "pitfiller.main" ) ) ; pm . message ( msg . message ( "pitfiller.perc" ) ) ; pm . message ( "0%" ) ; while ( currentPitsCount > 0 ) { if ( pm . isCanceled ( ) ) { return ; } int r = currentPitRows [ stillPitsCount ] ; int c = currentPitCols [ stillPitsCount ] ; pooln = 1 ; nf = 0 ; int npool = pool ( r , c , 0 ) ; for ( int ip = 1 ; ip <= npool ; ip ++ ) { if ( pm . isCanceled ( ) ) { return ; } r = ipool [ ip ] ; c = jpool [ ip ] ; for ( int k = 1 ; k <= 8 ; k ++ ) { int jn = c + DIR_WITHFLOW_EXITING_INVERTED [ k ] [ 0 ] ; int in = r + DIR_WITHFLOW_EXITING_INVERTED [ k ] [ 1 ] ; if ( apool [ jn ] [ in ] != pooln ) { et = max2 ( pitIter . getSampleDouble ( c , r , 0 ) , pitIter . getSampleDouble ( jn , in , 0 ) ) ; if ( nf == 0 ) { emin = et ; nf = 1 ; } else { if ( emin > et ) { emin = et ; } } } } } for ( int k = 1 ; k <= npool ; k ++ ) { if ( pm . isCanceled ( ) ) { return ; } r = ipool [ k ] ; c = jpool [ k ] ; if ( pitIter . getSampleDouble ( c , r , 0 ) <= emin ) { if ( dir [ c ] [ r ] > 0 ) { dir [ c ] [ r ] = 0 ; addPitToStack ( r , c ) ; } for ( int ip = 1 ; ip <= 8 ; ip ++ ) { int jn = c + DIR_WITHFLOW_EXITING_INVERTED [ ip ] [ 0 ] ; int in = r + DIR_WITHFLOW_EXITING_INVERTED [ ip ] [ 1 ] ; if ( ( pitIter . getSampleDouble ( jn , in , 0 ) > pitIter . getSampleDouble ( c , r , 0 ) ) && ( dir [ jn ] [ in ] > 0 ) ) { dir [ jn ] [ in ] = 0 ; addPitToStack ( in , jn ) ; } } pitIter . setSample ( c , r , 0 , emin ) ; } apool [ c ] [ r ] = 0 ; } int ni = 0 ; for ( int ip = 1 ; ip <= currentPitsCount ; ip ++ ) { if ( pm . isCanceled ( ) ) { return ; } setDirection ( pitIter . getSampleDouble ( currentPitCols [ ip ] , currentPitRows [ ip ] , 0 ) , currentPitRows [ ip ] , currentPitCols [ ip ] , dir , directionFactor ) ; if ( dir [ currentPitCols [ ip ] ] [ currentPitRows [ ip ] ] == 0 ) { ni ++ ; currentPitRows [ ni ] = currentPitRows [ ip ] ; currentPitCols [ ni ] = currentPitCols [ ip ] ; } } n = currentPitsCount ; stillPitsCount = resolveFlats ( ni ) ; if ( stillPitsCount == - 1 ) { return ; } if ( currentPitsCount < nt ) { if ( per % 10 == 0 ) pm . message ( ( int ) per + "%" ) ; per = per + 1 ; nt = ( int ) ( np1 * ( 1 - per / 100 ) ) ; } } pm . message ( "OmsPitfiller finished..." ) ; }
Initialise the dir matrix and then call the set method to obtain a D8 matrix
<p>
It's possible summarise the logical pitfiller stream like:
<ol>
<li>Initialise DIR to 0 (no flood) if the elevation value is valid and isn't apixel on the
edge</li>
<li>If the pixel have as DIR[j][i] a valid value then check if the adjacent pixels are valid
values:
<dl>
<dt>Yes, there are only valid value
<dd>then set the DIR value to the drainage direction (if slope is greater than 0) or to 0 if
there aren't.
<dt>No, there are an invalid value
<dd>set DIR to -1 (impossible value)
</dl>
</li>
<li>If DIR=0 then keep in temporary vector the index of this pixel.</li>
<li>Call <b>vdn</b> method, which assign the drainage value if the slope is greater or equal
to 0. Notice that neighbour pixel are valid pixel if DIR=0. And then calculate the minimum
elevation point (where there are a pool)</li>
<li>Start a conditioning cycle (while there are a cell which have as a drainage direction 0
(is a pool);<ol type=a>
<li>Find if there are a pool and check the pixels which belong to</li>
<li>Check the lowest point of the edge</li>
<li>Set the pixels pool elevation to the lowest point of the edge</li>
<li>Call <b>vdn</b> to recalculate unresolved pixels
<li>-
<li>return to the begin</li>
</ol>
</li> </ol>

@throws Exception