ArcMap and BackgroundWorkerThread

I am reading here, I have to stick to STA threads while working inside ArcMap. I used the usual BackgroudnWorker

one and my code was very slow. I am trying to change it so that a worker creates an STA thread internally and runs it for "heavy" stuff.

Now my problem is that after executing the second thread, all my com-objects will be released. I checked if I have some kind of marshal. Calling RelaseComObject or Shutdown, but I don't think it is. Maybe just because the thread that fetched those COM objects is running, the objects are automatically deallocated?

here is my example code:

    private void bckgrndWrkrController_DoWork(object sender, DoWorkEventArgs e)
    {
        BackgroundWorker worker = sender as BackgroundWorker;
        if (worker != null)
        {
            controller.BackgroundWorker = worker;
            Thread thread = new Thread(STAProcessSelection);
            thread.SetApartmentState(ApartmentState.STA);
            thread.Start(e.Argument);
            thread.Join();
            e.Result = processingResult;
            e.Cancel = worker.CancellationPending;
        }
    }

    private void STAProcessSelection(object argument)
    {
        ISelection selection = argument as ISelection;
        if (selection != null)
        {
            processingResult = controller.ProcessSelection(selection);
        }
    }

    private void bckgrndWrkrController_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
    {
        if (e.Error != null)
        {
            MessageBox.Show(e.Error.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
        }
        else if (e.Result is bool)
        {
            // Making sure the thread was not cancelled after we got the result
            processingResult = (bool)e.Result && !worker.CancellationPending;
            if (processingResult)
            {
                // Set the datasource of the grid
                bindingSource.DataSource = controller.List;
            }
        }

        // and inform the command we are done
        OnDoneProcessing(EventArgs.Empty);
    }

      

On line # 22, after calling ProcessSelection, the controller .List [0] contains a valid com object. On line # 11, after the call to thread.Join, the controller.List [0] element already contains a released com object. What am I doing wrong here?

0


a source to share


1 answer


I read that One Thread Apartments (STA) only has one thread allowed inside them (I didn't think it was obvious ...). So even though my main thread was STA and I created another STA tape, they were in different compartments.
When my 2nd thread finished its work and walked away, the code calling COM objects inside that apartment could not execute (there was no thread to call the call. Maybe even no COM objects anymore?)



Anyway, I still don't know how to effectively use the BackgroundWorker inside ArcMAP. But I think this explains why this attempt failed.

0


a source







All Articles