<commit_before>// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <iostream>

#include "base/at_exit.h"
#include "base/basictypes.h"
#include "base/command_line.h"
#include "base/event_recorder.h"
#include "base/file_path.h"
#include "base/file_util.h"
#include "base/icu_util.h"
#include "base/memory_debug.h"
#include "base/message_loop.h"
#include "base/path_service.h"
#include "base/process_util.h"
#include "base/rand_util.h"
#include "base/stats_table.h"
#include "base/string_util.h"
#include "base/sys_info.h"
#include "base/trace_event.h"
#include "net/base/cookie_monster.h"
#include "net/base/net_module.h"
#include "net/http/http_cache.h"
#include "net/base/ssl_test_util.h"
#include "net/url_request/url_request_context.h"
#include "webkit/api/public/WebKit.h"
#include "webkit/glue/webkit_glue.h"
#include "webkit/glue/window_open_disposition.h"
#include "webkit/extensions/v8/gc_extension.h"
#include "webkit/extensions/v8/playback_extension.h"
#include "webkit/extensions/v8/profiler_extension.h"
#include "webkit/tools/test_shell/simple_resource_loader_bridge.h"
#include "webkit/tools/test_shell/test_shell.h"
#include "webkit/tools/test_shell/test_shell_platform_delegate.h"
#include "webkit/tools/test_shell/test_shell_request_context.h"
#include "webkit/tools/test_shell/test_shell_switches.h"
#include "webkit/tools/test_shell/test_shell_webkit_init.h"

using namespace std;

static const size_t kPathBufSize = 2048;

namespace {

// StatsTable initialization parameters.
static const char* kStatsFilePrefix = "testshell_";
static int kStatsFileThreads = 20;
static int kStatsFileCounters = 200;

}  // namespace

int main(int argc, char* argv[]) {
  base::EnableTerminationOnHeapCorruption();

  // Some tests may use base::Singleton<>, thus we need to instanciate
  // the AtExitManager or else we will leak objects.
  base::AtExitManager at_exit_manager;

  TestShellPlatformDelegate::PreflightArgs(&argc, &argv);
  CommandLine::Init(argc, argv);
  const CommandLine& parsed_command_line = *CommandLine::ForCurrentProcess();

  TestShellPlatformDelegate platform(parsed_command_line);

  if (parsed_command_line.HasSwitch(test_shell::kStartupDialog))
    TestShell::ShowStartupDebuggingDialog();

  if (parsed_command_line.HasSwitch(test_shell::kCheckLayoutTestSystemDeps)) {
    exit(platform.CheckLayoutTestSystemDependencies() ? 0 : 1);
  }

  // Allocate a message loop for this thread.  Although it is not used
  // directly, its constructor sets up some necessary state.
  MessageLoopForUI main_message_loop;

  bool suppress_error_dialogs = (
       base::SysInfo::HasEnvVar(L"CHROME_HEADLESS") ||
       parsed_command_line.HasSwitch(test_shell::kNoErrorDialogs) ||
       parsed_command_line.HasSwitch(test_shell::kLayoutTests));
  bool layout_test_mode =
      parsed_command_line.HasSwitch(test_shell::kLayoutTests);

  bool enable_gp_fault_error_box = false;
  enable_gp_fault_error_box =
      parsed_command_line.HasSwitch(test_shell::kGPFaultErrorBox);
  TestShell::InitLogging(suppress_error_dialogs,
                         layout_test_mode,
                         enable_gp_fault_error_box);

  // Initialize WebKit for this scope.
  TestShellWebKitInit test_shell_webkit_init(layout_test_mode);

  // Suppress abort message in v8 library in debugging mode (but not
  // actually under a debugger).  V8 calls abort() when it hits
  // assertion errors.
  if (suppress_error_dialogs) {
    platform.SuppressErrorReporting();
  }

  if (parsed_command_line.HasSwitch(test_shell::kEnableTracing))
    base::TraceLog::StartTracing();

  net::HttpCache::Mode cache_mode = net::HttpCache::NORMAL;

  // This is a special mode where JS helps the browser implement
  // playback/record mode.  Generally, in this mode, some functions
  // of client-side randomness are removed.  For example, in
  // this mode Math.random() and Date.getTime() may not return
  // values which vary.
  bool playback_mode =
    parsed_command_line.HasSwitch(test_shell::kPlaybackMode);
  bool record_mode =
    parsed_command_line.HasSwitch(test_shell::kRecordMode);

  if (playback_mode)
    cache_mode = net::HttpCache::PLAYBACK;
  else if (record_mode)
    cache_mode = net::HttpCache::RECORD;

  if (layout_test_mode ||
      parsed_command_line.HasSwitch(test_shell::kEnableFileCookies))
    net::CookieMonster::EnableFileScheme();

  FilePath cache_path = FilePath::FromWStringHack(
      parsed_command_line.GetSwitchValue(test_shell::kCacheDir));
  // If the cache_path is empty and it's layout_test_mode, leave it empty
  // so we use an in-memory cache. This makes running multiple test_shells
  // in parallel less flaky.
  if (cache_path.empty() && !layout_test_mode) {
    PathService::Get(base::DIR_EXE, &cache_path);
    cache_path = cache_path.AppendASCII("cache");
  }

  // Initializing with a default context, which means no on-disk cookie DB,
  // and no support for directory listings.
  SimpleResourceLoaderBridge::Init(
      new TestShellRequestContext(cache_path.ToWStringHack(),
                                  cache_mode, layout_test_mode));

  // Load ICU data tables
  icu_util::Initialize();

  // Config the network module so it has access to a limited set of resources.
  net::NetModule::SetResourceProvider(TestShell::NetResourceProvider);

  // On Linux, load the test root certificate.
  net::TestServerLauncher ssl_util;
  ssl_util.LoadTestRootCert();

  platform.InitializeGUI();

  TestShell::InitializeTestShell(layout_test_mode);

  if (parsed_command_line.HasSwitch(test_shell::kAllowScriptsToCloseWindows))
    TestShell::SetAllowScriptsToCloseWindows();

  // Disable user themes for layout tests so pixel tests are consistent.
  if (layout_test_mode) {
    platform.SelectUnifiedTheme();
  }

  if (parsed_command_line.HasSwitch(test_shell::kTestShellTimeOut)) {
    const std::wstring timeout_str = parsed_command_line.GetSwitchValue(
        test_shell::kTestShellTimeOut);
    int timeout_ms =
        static_cast<int>(StringToInt64(WideToUTF16Hack(timeout_str.c_str())));
    if (timeout_ms > 0)
      TestShell::SetFileTestTimeout(timeout_ms);
  }

  // Treat the first loose value as the initial URL to open.
  FilePath uri;

  // Default to a homepage if we're interactive.
  if (!layout_test_mode) {
    PathService::Get(base::DIR_SOURCE_ROOT, &uri);
    uri = uri.AppendASCII("webkit");
    uri = uri.AppendASCII("data");
    uri = uri.AppendASCII("test_shell");
    uri = uri.AppendASCII("index.html");
  }

  std::vector<std::wstring> loose_values = parsed_command_line.GetLooseValues();
  if (loose_values.size() > 0)
    uri = FilePath::FromWStringHack(loose_values[0]);

  std::wstring js_flags =
    parsed_command_line.GetSwitchValue(test_shell::kJavaScriptFlags);
  // Test shell always exposes the GC.
  js_flags += L" --expose-gc";
  webkit_glue::SetJavaScriptFlags(js_flags);
  // Expose GCController to JavaScript.
  WebKit::registerExtension(extensions_v8::GCExtension::Get());

  if (parsed_command_line.HasSwitch(test_shell::kProfiler)) {
    WebKit::registerExtension(extensions_v8::ProfilerExtension::Get());
  }

  // Load and initialize the stats table.  Attempt to construct a somewhat
  // unique name to isolate separate instances from each other.
  StatsTable *table = new StatsTable(
      // truncate the random # to 32 bits for the benefit of Mac OS X, to
      // avoid tripping over its maximum shared memory segment name length
      kStatsFilePrefix + Uint64ToString(base::RandUint64() & 0xFFFFFFFFL),
      kStatsFileThreads,
      kStatsFileCounters);
  StatsTable::set_current(table);

  TestShell* shell;
  if (TestShell::CreateNewWindow(uri.ToWStringHack(), &shell)) {
    if (record_mode || playback_mode) {
      platform.SetWindowPositionForRecording(shell);
      WebKit::registerExtension(extensions_v8::PlaybackExtension::Get());
    }

    shell->Show(shell->webView(), NEW_WINDOW);

    if (parsed_command_line.HasSwitch(test_shell::kDumpStatsTable))
      shell->DumpStatsTableOnExit();

    bool no_events = parsed_command_line.HasSwitch(test_shell::kNoEvents);
    if ((record_mode || playback_mode) && !no_events) {
      FilePath script_path = cache_path;
      // Create the cache directory in case it doesn't exist.
      file_util::CreateDirectory(cache_path);
      script_path = script_path.AppendASCII("script.log");
      if (record_mode)
        base::EventRecorder::current()->StartRecording(script_path);
      if (playback_mode)
        base::EventRecorder::current()->StartPlayback(script_path);
    }

    if (parsed_command_line.HasSwitch(test_shell::kDebugMemoryInUse)) {
      base::MemoryDebug::SetMemoryInUseEnabled(true);
      // Dump all in use memory at startup
      base::MemoryDebug::DumpAllMemoryInUse();
    }

    if (false) {
      // TODO(scherkus): check for any DLL dependencies.
      webkit_glue::SetMediaPlayerAvailable(true);
    }

    // See if we need to run the tests.
    if (layout_test_mode) {
      // Set up for the kind of test requested.
      TestShell::TestParams params;
      if (parsed_command_line.HasSwitch(test_shell::kDumpPixels)) {
        // The pixel test flag also gives the image file name to use.
        params.dump_pixels = true;
        params.pixel_file_name = parsed_command_line.GetSwitchValue(
            test_shell::kDumpPixels);
        if (params.pixel_file_name.size() == 0) {
          fprintf(stderr, "No file specified for pixel tests");
          exit(1);
        }
      }
      if (parsed_command_line.HasSwitch(test_shell::kNoTree)) {
          params.dump_tree = false;
      }

      if (uri.empty()) {
        // Watch stdin for URLs.
        char filenameBuffer[kPathBufSize];
        while (fgets(filenameBuffer, sizeof(filenameBuffer), stdin)) {
          // When running layout tests we pass new line separated
          // tests to TestShell. Each line is a space separated list
          // of filename, timeout and expected pixel hash. The timeout
          // and the pixel hash are optional.
          char* newLine = strchr(filenameBuffer, '\n');
          if (newLine)
            *newLine = '\0';
          if (!*filenameBuffer)
            continue;

          params.test_url = strtok(filenameBuffer, " ");

          int old_timeout_ms = TestShell::GetLayoutTestTimeout();

          char* timeout = strtok(NULL, " ");
          if (timeout) {
            TestShell::SetFileTestTimeout(atoi(timeout));
            char* pixel_hash = strtok(NULL, " ");
            if (pixel_hash)
              params.pixel_hash = pixel_hash;
          }

          if (!TestShell::RunFileTest(params))
            break;

          TestShell::SetFileTestTimeout(old_timeout_ms);
        }
      } else {
        // TODO(ojan): Provide a way for run-singly tests to pass
        // in a hash and then set params.pixel_hash here.
        params.test_url = WideToUTF8(uri.ToWStringHack()).c_str();
        TestShell::RunFileTest(params);
      }

      shell->CallJSGC();
      shell->CallJSGC();
      if (shell) {
        // When we finish the last test, cleanup the LayoutTestController.
        // It may have references to not-yet-cleaned up windows.  By
        // cleaning up here we help purify reports.
        shell->ResetTestController();
        delete shell;
      }
    } else {
      MessageLoop::current()->Run();
    }

    // Flush any remaining messages.  This ensures that any accumulated
    // Task objects get destroyed before we exit, which avoids noise in
    // purify leak-test results.
    MessageLoop::current()->RunAllPending();

    if (record_mode)
      base::EventRecorder::current()->StopRecording();
    if (playback_mode)
      base::EventRecorder::current()->StopPlayback();
  }

  TestShell::ShutdownTestShell();
  TestShell::CleanupLogging();

  // Tear down shared StatsTable; prevents unit_tests from leaking it.
  StatsTable::set_current(NULL);
  delete table;

  return 0;
}
<commit_msg>test_shell: flush message loop before destroying the shell.<commit_after>// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <iostream>

#include "base/at_exit.h"
#include "base/basictypes.h"
#include "base/command_line.h"
#include "base/event_recorder.h"
#include "base/file_path.h"
#include "base/file_util.h"
#include "base/icu_util.h"
#include "base/memory_debug.h"
#include "base/message_loop.h"
#include "base/path_service.h"
#include "base/process_util.h"
#include "base/rand_util.h"
#include "base/stats_table.h"
#include "base/string_util.h"
#include "base/sys_info.h"
#include "base/trace_event.h"
#include "net/base/cookie_monster.h"
#include "net/base/net_module.h"
#include "net/http/http_cache.h"
#include "net/base/ssl_test_util.h"
#include "net/url_request/url_request_context.h"
#include "webkit/api/public/WebKit.h"
#include "webkit/glue/webkit_glue.h"
#include "webkit/glue/window_open_disposition.h"
#include "webkit/extensions/v8/gc_extension.h"
#include "webkit/extensions/v8/playback_extension.h"
#include "webkit/extensions/v8/profiler_extension.h"
#include "webkit/tools/test_shell/simple_resource_loader_bridge.h"
#include "webkit/tools/test_shell/test_shell.h"
#include "webkit/tools/test_shell/test_shell_platform_delegate.h"
#include "webkit/tools/test_shell/test_shell_request_context.h"
#include "webkit/tools/test_shell/test_shell_switches.h"
#include "webkit/tools/test_shell/test_shell_webkit_init.h"

using namespace std;

static const size_t kPathBufSize = 2048;

namespace {

// StatsTable initialization parameters.
static const char* kStatsFilePrefix = "testshell_";
static int kStatsFileThreads = 20;
static int kStatsFileCounters = 200;

}  // namespace

int main(int argc, char* argv[]) {
  base::EnableTerminationOnHeapCorruption();

  // Some tests may use base::Singleton<>, thus we need to instanciate
  // the AtExitManager or else we will leak objects.
  base::AtExitManager at_exit_manager;

  TestShellPlatformDelegate::PreflightArgs(&argc, &argv);
  CommandLine::Init(argc, argv);
  const CommandLine& parsed_command_line = *CommandLine::ForCurrentProcess();

  TestShellPlatformDelegate platform(parsed_command_line);

  if (parsed_command_line.HasSwitch(test_shell::kStartupDialog))
    TestShell::ShowStartupDebuggingDialog();

  if (parsed_command_line.HasSwitch(test_shell::kCheckLayoutTestSystemDeps)) {
    exit(platform.CheckLayoutTestSystemDependencies() ? 0 : 1);
  }

  // Allocate a message loop for this thread.  Although it is not used
  // directly, its constructor sets up some necessary state.
  MessageLoopForUI main_message_loop;

  bool suppress_error_dialogs = (
       base::SysInfo::HasEnvVar(L"CHROME_HEADLESS") ||
       parsed_command_line.HasSwitch(test_shell::kNoErrorDialogs) ||
       parsed_command_line.HasSwitch(test_shell::kLayoutTests));
  bool layout_test_mode =
      parsed_command_line.HasSwitch(test_shell::kLayoutTests);

  bool enable_gp_fault_error_box = false;
  enable_gp_fault_error_box =
      parsed_command_line.HasSwitch(test_shell::kGPFaultErrorBox);
  TestShell::InitLogging(suppress_error_dialogs,
                         layout_test_mode,
                         enable_gp_fault_error_box);

  // Initialize WebKit for this scope.
  TestShellWebKitInit test_shell_webkit_init(layout_test_mode);

  // Suppress abort message in v8 library in debugging mode (but not
  // actually under a debugger).  V8 calls abort() when it hits
  // assertion errors.
  if (suppress_error_dialogs) {
    platform.SuppressErrorReporting();
  }

  if (parsed_command_line.HasSwitch(test_shell::kEnableTracing))
    base::TraceLog::StartTracing();

  net::HttpCache::Mode cache_mode = net::HttpCache::NORMAL;

  // This is a special mode where JS helps the browser implement
  // playback/record mode.  Generally, in this mode, some functions
  // of client-side randomness are removed.  For example, in
  // this mode Math.random() and Date.getTime() may not return
  // values which vary.
  bool playback_mode =
    parsed_command_line.HasSwitch(test_shell::kPlaybackMode);
  bool record_mode =
    parsed_command_line.HasSwitch(test_shell::kRecordMode);

  if (playback_mode)
    cache_mode = net::HttpCache::PLAYBACK;
  else if (record_mode)
    cache_mode = net::HttpCache::RECORD;

  if (layout_test_mode ||
      parsed_command_line.HasSwitch(test_shell::kEnableFileCookies))
    net::CookieMonster::EnableFileScheme();

  FilePath cache_path = FilePath::FromWStringHack(
      parsed_command_line.GetSwitchValue(test_shell::kCacheDir));
  // If the cache_path is empty and it's layout_test_mode, leave it empty
  // so we use an in-memory cache. This makes running multiple test_shells
  // in parallel less flaky.
  if (cache_path.empty() && !layout_test_mode) {
    PathService::Get(base::DIR_EXE, &cache_path);
    cache_path = cache_path.AppendASCII("cache");
  }

  // Initializing with a default context, which means no on-disk cookie DB,
  // and no support for directory listings.
  SimpleResourceLoaderBridge::Init(
      new TestShellRequestContext(cache_path.ToWStringHack(),
                                  cache_mode, layout_test_mode));

  // Load ICU data tables
  icu_util::Initialize();

  // Config the network module so it has access to a limited set of resources.
  net::NetModule::SetResourceProvider(TestShell::NetResourceProvider);

  // On Linux, load the test root certificate.
  net::TestServerLauncher ssl_util;
  ssl_util.LoadTestRootCert();

  platform.InitializeGUI();

  TestShell::InitializeTestShell(layout_test_mode);

  if (parsed_command_line.HasSwitch(test_shell::kAllowScriptsToCloseWindows))
    TestShell::SetAllowScriptsToCloseWindows();

  // Disable user themes for layout tests so pixel tests are consistent.
  if (layout_test_mode) {
    platform.SelectUnifiedTheme();
  }

  if (parsed_command_line.HasSwitch(test_shell::kTestShellTimeOut)) {
    const std::wstring timeout_str = parsed_command_line.GetSwitchValue(
        test_shell::kTestShellTimeOut);
    int timeout_ms =
        static_cast<int>(StringToInt64(WideToUTF16Hack(timeout_str.c_str())));
    if (timeout_ms > 0)
      TestShell::SetFileTestTimeout(timeout_ms);
  }

  // Treat the first loose value as the initial URL to open.
  FilePath uri;

  // Default to a homepage if we're interactive.
  if (!layout_test_mode) {
    PathService::Get(base::DIR_SOURCE_ROOT, &uri);
    uri = uri.AppendASCII("webkit");
    uri = uri.AppendASCII("data");
    uri = uri.AppendASCII("test_shell");
    uri = uri.AppendASCII("index.html");
  }

  std::vector<std::wstring> loose_values = parsed_command_line.GetLooseValues();
  if (loose_values.size() > 0)
    uri = FilePath::FromWStringHack(loose_values[0]);

  std::wstring js_flags =
    parsed_command_line.GetSwitchValue(test_shell::kJavaScriptFlags);
  // Test shell always exposes the GC.
  js_flags += L" --expose-gc";
  webkit_glue::SetJavaScriptFlags(js_flags);
  // Expose GCController to JavaScript.
  WebKit::registerExtension(extensions_v8::GCExtension::Get());

  if (parsed_command_line.HasSwitch(test_shell::kProfiler)) {
    WebKit::registerExtension(extensions_v8::ProfilerExtension::Get());
  }

  // Load and initialize the stats table.  Attempt to construct a somewhat
  // unique name to isolate separate instances from each other.
  StatsTable *table = new StatsTable(
      // truncate the random # to 32 bits for the benefit of Mac OS X, to
      // avoid tripping over its maximum shared memory segment name length
      kStatsFilePrefix + Uint64ToString(base::RandUint64() & 0xFFFFFFFFL),
      kStatsFileThreads,
      kStatsFileCounters);
  StatsTable::set_current(table);

  TestShell* shell;
  if (TestShell::CreateNewWindow(uri.ToWStringHack(), &shell)) {
    if (record_mode || playback_mode) {
      platform.SetWindowPositionForRecording(shell);
      WebKit::registerExtension(extensions_v8::PlaybackExtension::Get());
    }

    shell->Show(shell->webView(), NEW_WINDOW);

    if (parsed_command_line.HasSwitch(test_shell::kDumpStatsTable))
      shell->DumpStatsTableOnExit();

    bool no_events = parsed_command_line.HasSwitch(test_shell::kNoEvents);
    if ((record_mode || playback_mode) && !no_events) {
      FilePath script_path = cache_path;
      // Create the cache directory in case it doesn't exist.
      file_util::CreateDirectory(cache_path);
      script_path = script_path.AppendASCII("script.log");
      if (record_mode)
        base::EventRecorder::current()->StartRecording(script_path);
      if (playback_mode)
        base::EventRecorder::current()->StartPlayback(script_path);
    }

    if (parsed_command_line.HasSwitch(test_shell::kDebugMemoryInUse)) {
      base::MemoryDebug::SetMemoryInUseEnabled(true);
      // Dump all in use memory at startup
      base::MemoryDebug::DumpAllMemoryInUse();
    }

    if (false) {
      // TODO(scherkus): check for any DLL dependencies.
      webkit_glue::SetMediaPlayerAvailable(true);
    }

    // See if we need to run the tests.
    if (layout_test_mode) {
      // Set up for the kind of test requested.
      TestShell::TestParams params;
      if (parsed_command_line.HasSwitch(test_shell::kDumpPixels)) {
        // The pixel test flag also gives the image file name to use.
        params.dump_pixels = true;
        params.pixel_file_name = parsed_command_line.GetSwitchValue(
            test_shell::kDumpPixels);
        if (params.pixel_file_name.size() == 0) {
          fprintf(stderr, "No file specified for pixel tests");
          exit(1);
        }
      }
      if (parsed_command_line.HasSwitch(test_shell::kNoTree)) {
          params.dump_tree = false;
      }

      if (uri.empty()) {
        // Watch stdin for URLs.
        char filenameBuffer[kPathBufSize];
        while (fgets(filenameBuffer, sizeof(filenameBuffer), stdin)) {
          // When running layout tests we pass new line separated
          // tests to TestShell. Each line is a space separated list
          // of filename, timeout and expected pixel hash. The timeout
          // and the pixel hash are optional.
          char* newLine = strchr(filenameBuffer, '\n');
          if (newLine)
            *newLine = '\0';
          if (!*filenameBuffer)
            continue;

          params.test_url = strtok(filenameBuffer, " ");

          int old_timeout_ms = TestShell::GetLayoutTestTimeout();

          char* timeout = strtok(NULL, " ");
          if (timeout) {
            TestShell::SetFileTestTimeout(atoi(timeout));
            char* pixel_hash = strtok(NULL, " ");
            if (pixel_hash)
              params.pixel_hash = pixel_hash;
          }

          if (!TestShell::RunFileTest(params))
            break;

          TestShell::SetFileTestTimeout(old_timeout_ms);
        }
      } else {
        // TODO(ojan): Provide a way for run-singly tests to pass
        // in a hash and then set params.pixel_hash here.
        params.test_url = WideToUTF8(uri.ToWStringHack()).c_str();
        TestShell::RunFileTest(params);
      }

      shell->CallJSGC();
      shell->CallJSGC();

      // When we finish the last test, cleanup the LayoutTestController.
      // It may have references to not-yet-cleaned up windows.  By
      // cleaning up here we help purify reports.
      shell->ResetTestController();

      // Flush any remaining messages before we kill ourselves.
      // http://code.google.com/p/chromium/issues/detail?id=9500
      MessageLoop::current()->RunAllPending();

      delete shell;
    } else {
      MessageLoop::current()->Run();
    }

    // Flush any remaining messages.  This ensures that any accumulated
    // Task objects get destroyed before we exit, which avoids noise in
    // purify leak-test results.
    MessageLoop::current()->RunAllPending();

    if (record_mode)
      base::EventRecorder::current()->StopRecording();
    if (playback_mode)
      base::EventRecorder::current()->StopPlayback();
  }

  TestShell::ShutdownTestShell();
  TestShell::CleanupLogging();

  // Tear down shared StatsTable; prevents unit_tests from leaking it.
  StatsTable::set_current(NULL);
  delete table;

  return 0;
}
<|endoftext|>


<commit_before>/*=========================================================================
 *
 *  Copyright Insight Software Consortium
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *         http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 *=========================================================================*/
#ifndef __itkImageToVectorImageFilter_hxx
#define __itkImageToVectorImageFilter_hxx

#include "itkImageToVectorImageFilter.h"
#include "itkImageRegionConstIteratorWithIndex.h"
#include "itkImageRegionIterator.h"

namespace itk
{
//----------------------------------------------------------------------------
template< class TInputImage >
ImageToVectorImageFilter< TInputImage >
::ImageToVectorImageFilter()
{
  // At least 1 inputs is necessary for a vector image.
  this->SetNumberOfRequiredInputs(1);
}

//----------------------------------------------------------------------------
template< class TInputImage >
void
ImageToVectorImageFilter< TInputImage >
::GenerateOutputInformation(void)
{
  // Override the method in itkImageSource, so we can set the vector length of
  // the output itk::VectorImage

  this->Superclass::GenerateOutputInformation();

  OutputImageType *output = this->GetOutput();
  output->SetVectorLength( this->GetNumberOfInputs() );
}

//----------------------------------------------------------------------------
template< class TInputImage >
void
ImageToVectorImageFilter< TInputImage >
::BeforeThreadedGenerateData()
{
  // Check to verify all inputs are specified and have the same metadata,
  // spacing etc...
  const unsigned int numberOfInputs = this->GetNumberOfInputs();
  RegionType         region;

  for ( unsigned int i = 0; i < numberOfInputs; i++ )
    {
    InputImageType *input = this->Superclass::GetInput(i);
    if ( !input )
      {
      itkExceptionMacro(<< "Input " << i << " not set!");
      }
    if ( i == 0 )
      {
      region = input->GetLargestPossibleRegion();
      }
    else if ( input->GetLargestPossibleRegion() != region )
      {
      itkExceptionMacro(<< "All Inputs must have the same dimensions.");
      }
    }
}

//----------------------------------------------------------------------------
template< class TInputImage >
void
ImageToVectorImageFilter< TInputImage >
::ThreadedGenerateData(const RegionType & outputRegionForThread,
                       ThreadIdType)
{
  typename OutputImageType::Pointer outputImage =
    static_cast< OutputImageType * >( this->ProcessObject::GetOutput(0) );

  ImageRegionIterator< OutputImageType > oit(outputImage, outputRegionForThread);
  oit.GoToBegin();

  typedef ImageRegionConstIterator< InputImageType > InputIteratorType;
  std::vector< InputIteratorType * > inputItContainer;

  for ( unsigned int i = 0; i < this->GetNumberOfInputs(); i++ )
    {
    typename InputImageType::Pointer inputImagePointer =
      static_cast< InputImageType * >( this->ProcessObject::GetInput(i) );

    InputIteratorType *iit = new InputIteratorType(
      inputImagePointer, outputRegionForThread);
    iit->GoToBegin();
    inputItContainer.push_back(iit);
    }

  typename OutputImageType::PixelType pix( this->GetNumberOfInputs() );
  while ( !oit.IsAtEnd() )
    {
    for ( unsigned int i = 0; i < this->GetNumberOfInputs(); i++ )
      {
      pix[i] = inputItContainer[i]->Get();
      ++( *inputItContainer[i] );
      }
    oit.Set(pix);
    ++oit;
    }

  for ( unsigned int i = 0; i < this->GetNumberOfInputs(); i++ )
    {
    delete inputItContainer[i];
    }
}
} // end namespace itk

#endif
<commit_msg>BUG: ConstPointer assigned to non-const raw pointer<commit_after>/*=========================================================================
 *
 *  Copyright Insight Software Consortium
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *         http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 *=========================================================================*/
#ifndef __itkImageToVectorImageFilter_hxx
#define __itkImageToVectorImageFilter_hxx

#include "itkImageToVectorImageFilter.h"
#include "itkImageRegionConstIteratorWithIndex.h"
#include "itkImageRegionIterator.h"

namespace itk
{
//----------------------------------------------------------------------------
template< class TInputImage >
ImageToVectorImageFilter< TInputImage >
::ImageToVectorImageFilter()
{
  // At least 1 inputs is necessary for a vector image.
  this->SetNumberOfRequiredInputs(1);
}

//----------------------------------------------------------------------------
template< class TInputImage >
void
ImageToVectorImageFilter< TInputImage >
::GenerateOutputInformation(void)
{
  // Override the method in itkImageSource, so we can set the vector length of
  // the output itk::VectorImage

  this->Superclass::GenerateOutputInformation();

  OutputImageType *output = this->GetOutput();
  output->SetVectorLength( this->GetNumberOfInputs() );
}

//----------------------------------------------------------------------------
template< class TInputImage >
void
ImageToVectorImageFilter< TInputImage >
::BeforeThreadedGenerateData()
{
  // Check to verify all inputs are specified and have the same metadata,
  // spacing etc...
  const unsigned int numberOfInputs = this->GetNumberOfInputs();
  RegionType         region;

  for ( unsigned int i = 0; i < numberOfInputs; i++ )
    {
    const InputImageType * input = this->Superclass::GetInput(i);
    if ( !input )
      {
      itkExceptionMacro(<< "Input " << i << " not set!");
      }
    if ( i == 0 )
      {
      region = input->GetLargestPossibleRegion();
      }
    else if ( input->GetLargestPossibleRegion() != region )
      {
      itkExceptionMacro(<< "All Inputs must have the same dimensions.");
      }
    }
}

//----------------------------------------------------------------------------
template< class TInputImage >
void
ImageToVectorImageFilter< TInputImage >
::ThreadedGenerateData(const RegionType & outputRegionForThread,
                       ThreadIdType)
{
  typename OutputImageType::Pointer outputImage =
    static_cast< OutputImageType * >( this->ProcessObject::GetOutput(0) );

  ImageRegionIterator< OutputImageType > oit(outputImage, outputRegionForThread);
  oit.GoToBegin();

  typedef ImageRegionConstIterator< InputImageType > InputIteratorType;
  std::vector< InputIteratorType * > inputItContainer;

  for ( unsigned int i = 0; i < this->GetNumberOfInputs(); i++ )
    {
    typename InputImageType::Pointer inputImagePointer =
      static_cast< InputImageType * >( this->ProcessObject::GetInput(i) );

    InputIteratorType *iit = new InputIteratorType(
      inputImagePointer, outputRegionForThread);
    iit->GoToBegin();
    inputItContainer.push_back(iit);
    }

  typename OutputImageType::PixelType pix( this->GetNumberOfInputs() );
  while ( !oit.IsAtEnd() )
    {
    for ( unsigned int i = 0; i < this->GetNumberOfInputs(); i++ )
      {
      pix[i] = inputItContainer[i]->Get();
      ++( *inputItContainer[i] );
      }
    oit.Set(pix);
    ++oit;
    }

  for ( unsigned int i = 0; i < this->GetNumberOfInputs(); i++ )
    {
    delete inputItContainer[i];
    }
}
} // end namespace itk

#endif
<|endoftext|>


<commit_before>/* -*- mode: c++; c-basic-offset:4 -*-
    dialogs/selftestdialog.cpp

    This file is part of Kleopatra, the KDE keymanager
    Copyright (c) 2008 Klarälvdalens Datakonsult AB

    Kleopatra is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation; either version 2 of the License, or
    (at your option) any later version.

    Kleopatra is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program; if not, write to the Free Software
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA

    In addition, as a special exception, the copyright holders give
    permission to link the code of this program with any edition of
    the Qt library by Trolltech AS, Norway (or with modified versions
    of Qt that use the same license as Qt), and distribute linked
    combinations including the two.  You must obey the GNU General
    Public License in all respects for all of the code used other than
    Qt.  If you modify this file, you may extend this exception to
    your version of the file, but you are not obligated to do so.  If
    you do not wish to do so, delete this exception statement from
    your version.
*/

#include <config-kleopatra.h>

#include "selftestdialog.h"

#include "ui_selftestdialog.h"

#include <selftest/selftest.h>

#include <QAbstractTableModel>

#include <boost/shared_ptr.hpp>

#include <cassert>
#include <vector>

using namespace Kleo;
using namespace Kleo::Dialogs;
using namespace boost;

namespace {

    class Model : public QAbstractTableModel {
        Q_OBJECT
    public:
        explicit Model( QObject * parent=0 )
            : QAbstractTableModel( parent ),
              m_tests()
        {

        }

        enum Column {
            TestName,
            TestResult,

            NumColumns
        };

        const shared_ptr<SelfTest> & fromModelIndex( const QModelIndex & idx ) const {
            const unsigned int row = idx.row();
            if ( row < m_tests.size() )
                return m_tests[row];
            static const shared_ptr<SelfTest> null;
            return null;
        }

        /* reimp */ int rowCount( const QModelIndex & idx ) const { return idx.isValid() ? 0 : m_tests.size() ; }
        /* reimp */ int columnCount( const QModelIndex & ) const { return NumColumns; }

        /* reimp */ QVariant data( const QModelIndex & idx, int role ) const {
            const unsigned int row = idx.row();
            if ( idx.isValid() && row < m_tests.size() )
                switch ( role ) {
                case Qt::DisplayRole:
                case Qt::ToolTipRole:
                    switch ( idx.column() ) {
                    case TestName:
                        return m_tests[row]->name();
                    case TestResult:
                        if ( m_tests[row]->passed() )
                            return i18n("Passed");
                        else
                            if ( role == Qt::ToolTipRole )
                                return m_tests[row]->longError();
                            else
                                return m_tests[row]->shortError();
                    }
                    break;
                case Qt::BackgroundRole:
                    return QColor( m_tests[row]->passed() ? Qt::green : Qt::red );
                }
            return QVariant();
        }

        /* reimp */ QVariant headerData( int section, Qt::Orientation o, int role ) const {
            if ( o == Qt::Horizontal &&
                 section >= 0 && section < NumColumns &&
                 role == Qt::DisplayRole )
                switch ( section ) {
                case TestName:   return i18n("Test Name");
                case TestResult: return i18n("Result");
                }
            return QVariant();
        }

        void clear() {
            if ( m_tests.empty() )
                return;
            beginRemoveRows( QModelIndex(), 0, m_tests.size() - 1 );
            m_tests.clear();
            endRemoveRows();
        }

        void append( const std::vector< shared_ptr<SelfTest> > & tests ) {
            if ( tests.empty() )
                return;
            beginInsertRows( QModelIndex(), m_tests.size(), m_tests.size() + tests.size() );
            m_tests.insert( m_tests.end(), tests.begin(), tests.end() );
            endInsertRows();
        }

        void reloadData() {
            if ( !m_tests.empty() )
                emit dataChanged( index( 0, 0 ), index( m_tests.size() - 1, NumColumns - 1 ) );
        }

        const shared_ptr<SelfTest> & at( unsigned int idx ) const {
            return m_tests.at( idx );
        }

    private:
        std::vector< shared_ptr<SelfTest> > m_tests;
    };

}

class SelfTestDialog::Private {
    friend class ::Kleo::Dialogs::SelfTestDialog;
    SelfTestDialog * const q;
public:
    explicit Private( SelfTestDialog * qq )
        : q( qq ),
          ui( q )
    {
        ui.resultsTV->setModel( &model );

        connect( ui.resultsTV->selectionModel(), SIGNAL(selectionChanged(QItemSelection,QItemSelection)),
                 q, SLOT(slotSelectionChanged()) );
    }

private:
    void slotSelectionChanged() {
        const int row = selectedRowIndex();
        if ( row < 0 ) {
            ui.proposedCorrectiveActionLB->setText( i18n("(select test first)" ) );
            ui.proposedCorrectiveActionGB->setEnabled( false );
        } else {
            ui.proposedCorrectiveActionGB->setEnabled( true );
            ui.proposedCorrectiveActionLB->setText( model.at(row)->proposedFix() );
            ui.doItPB->setEnabled( !model.at(row)->passed() && model.at(row)->canFixAutomatically() );
        }
    }
    void slotDoItClicked() {
        if ( const shared_ptr<SelfTest> st = model.fromModelIndex( selectedRow() ) )
            if ( st->fix() )
                model.reloadData();
    }

private:
    QModelIndex selectedRow() const {
        const QItemSelectionModel * const ism = ui.resultsTV->selectionModel();
        if ( !ism )
            return QModelIndex();
        const QModelIndexList mil = ism->selectedRows();
        return mil.empty() ? QModelIndex() : mil.front() ;
    }
    int selectedRowIndex() const {
        return selectedRow().row();
    }

private:
    Model model;

    struct UI : public Ui_SelfTestDialog {

        QPushButton * rerunPB;

        explicit UI( SelfTestDialog * qq )
            : Ui_SelfTestDialog(),
              rerunPB( new QPushButton( i18n("Rerun Tests") ) )
        {
            setupUi( qq );

            buttonBox->addButton( rerunPB, QDialogButtonBox::ActionRole );
            buttonBox->button( QDialogButtonBox::Ok )->setText( i18n("Continue") );

            connect( rerunPB, SIGNAL(clicked()),
                     qq, SIGNAL(updateRequested()) );
        }
    } ui;
};

SelfTestDialog::SelfTestDialog( QWidget * p, Qt::WindowFlags f )
    : QDialog( p, f ), d( new Private( this ) )
{

}

SelfTestDialog::SelfTestDialog( const std::vector< shared_ptr<SelfTest> > & tests, QWidget * p, Qt::WindowFlags f )
    : QDialog( p, f ), d( new Private( this ) )
{
    addSelfTests( tests );
}

SelfTestDialog::~SelfTestDialog() {}

void SelfTestDialog::clear() {
    d->model.clear();
}

void SelfTestDialog::addSelfTest( const shared_ptr<SelfTest> & test ) {
    d->model.append( std::vector< shared_ptr<SelfTest> >( 1, test ) );
}

void SelfTestDialog::addSelfTests( const std::vector< shared_ptr<SelfTest> > & tests ) {
    d->model.append( tests );
}

void SelfTestDialog::setRunAtStartUp( bool on ) {
    d->ui.runAtStartUpCB->setChecked( on );
}

bool SelfTestDialog::runAtStartUp() const {
    return d->ui.runAtStartUpCB->isChecked();
}

void SelfTestDialog::setAutomaticMode( bool automatic ) {
    d->ui.buttonBox->button( QDialogButtonBox::Ok     )->setVisible(  automatic );
    d->ui.buttonBox->button( QDialogButtonBox::Cancel )->setVisible(  automatic );
    d->ui.buttonBox->button( QDialogButtonBox::Close  )->setVisible( !automatic );
}

#include "selftestdialog.moc"
#include "moc_selftestdialog.cpp"
<commit_msg>Choose a default<commit_after>/* -*- mode: c++; c-basic-offset:4 -*-
    dialogs/selftestdialog.cpp

    This file is part of Kleopatra, the KDE keymanager
    Copyright (c) 2008 Klarälvdalens Datakonsult AB

    Kleopatra is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation; either version 2 of the License, or
    (at your option) any later version.

    Kleopatra is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program; if not, write to the Free Software
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA

    In addition, as a special exception, the copyright holders give
    permission to link the code of this program with any edition of
    the Qt library by Trolltech AS, Norway (or with modified versions
    of Qt that use the same license as Qt), and distribute linked
    combinations including the two.  You must obey the GNU General
    Public License in all respects for all of the code used other than
    Qt.  If you modify this file, you may extend this exception to
    your version of the file, but you are not obligated to do so.  If
    you do not wish to do so, delete this exception statement from
    your version.
*/

#include <config-kleopatra.h>

#include "selftestdialog.h"

#include "ui_selftestdialog.h"

#include <selftest/selftest.h>

#include <QAbstractTableModel>

#include <boost/shared_ptr.hpp>

#include <cassert>
#include <vector>

using namespace Kleo;
using namespace Kleo::Dialogs;
using namespace boost;

namespace {

    class Model : public QAbstractTableModel {
        Q_OBJECT
    public:
        explicit Model( QObject * parent=0 )
            : QAbstractTableModel( parent ),
              m_tests()
        {

        }

        enum Column {
            TestName,
            TestResult,

            NumColumns
        };

        const shared_ptr<SelfTest> & fromModelIndex( const QModelIndex & idx ) const {
            const unsigned int row = idx.row();
            if ( row < m_tests.size() )
                return m_tests[row];
            static const shared_ptr<SelfTest> null;
            return null;
        }

        /* reimp */ int rowCount( const QModelIndex & idx ) const { return idx.isValid() ? 0 : m_tests.size() ; }
        /* reimp */ int columnCount( const QModelIndex & ) const { return NumColumns; }

        /* reimp */ QVariant data( const QModelIndex & idx, int role ) const {
            const unsigned int row = idx.row();
            if ( idx.isValid() && row < m_tests.size() )
                switch ( role ) {
                case Qt::DisplayRole:
                case Qt::ToolTipRole:
                    switch ( idx.column() ) {
                    case TestName:
                        return m_tests[row]->name();
                    case TestResult:
                        if ( m_tests[row]->passed() )
                            return i18n("Passed");
                        else
                            if ( role == Qt::ToolTipRole )
                                return m_tests[row]->longError();
                            else
                                return m_tests[row]->shortError();
                    }
                    break;
                case Qt::BackgroundRole:
                    return QColor( m_tests[row]->passed() ? Qt::green : Qt::red );
                }
            return QVariant();
        }

        /* reimp */ QVariant headerData( int section, Qt::Orientation o, int role ) const {
            if ( o == Qt::Horizontal &&
                 section >= 0 && section < NumColumns &&
                 role == Qt::DisplayRole )
                switch ( section ) {
                case TestName:   return i18n("Test Name");
                case TestResult: return i18n("Result");
                }
            return QVariant();
        }

        void clear() {
            if ( m_tests.empty() )
                return;
            beginRemoveRows( QModelIndex(), 0, m_tests.size() - 1 );
            m_tests.clear();
            endRemoveRows();
        }

        void append( const std::vector< shared_ptr<SelfTest> > & tests ) {
            if ( tests.empty() )
                return;
            beginInsertRows( QModelIndex(), m_tests.size(), m_tests.size() + tests.size() );
            m_tests.insert( m_tests.end(), tests.begin(), tests.end() );
            endInsertRows();
        }

        void reloadData() {
            if ( !m_tests.empty() )
                emit dataChanged( index( 0, 0 ), index( m_tests.size() - 1, NumColumns - 1 ) );
        }

        const shared_ptr<SelfTest> & at( unsigned int idx ) const {
            return m_tests.at( idx );
        }

    private:
        std::vector< shared_ptr<SelfTest> > m_tests;
    };

}

class SelfTestDialog::Private {
    friend class ::Kleo::Dialogs::SelfTestDialog;
    SelfTestDialog * const q;
public:
    explicit Private( SelfTestDialog * qq )
        : q( qq ),
          ui( q )
    {
        ui.resultsTV->setModel( &model );

        connect( ui.resultsTV->selectionModel(), SIGNAL(selectionChanged(QItemSelection,QItemSelection)),
                 q, SLOT(slotSelectionChanged()) );
    }

private:
    void slotSelectionChanged() {
        const int row = selectedRowIndex();
        if ( row < 0 ) {
            ui.proposedCorrectiveActionLB->setText( i18n("(select test first)" ) );
            ui.proposedCorrectiveActionGB->setEnabled( false );
        } else {
            ui.proposedCorrectiveActionGB->setEnabled( true );
            ui.proposedCorrectiveActionLB->setText( model.at(row)->proposedFix() );
            ui.doItPB->setEnabled( !model.at(row)->passed() && model.at(row)->canFixAutomatically() );
        }
    }
    void slotDoItClicked() {
        if ( const shared_ptr<SelfTest> st = model.fromModelIndex( selectedRow() ) )
            if ( st->fix() )
                model.reloadData();
    }

private:
    QModelIndex selectedRow() const {
        const QItemSelectionModel * const ism = ui.resultsTV->selectionModel();
        if ( !ism )
            return QModelIndex();
        const QModelIndexList mil = ism->selectedRows();
        return mil.empty() ? QModelIndex() : mil.front() ;
    }
    int selectedRowIndex() const {
        return selectedRow().row();
    }

private:
    Model model;

    struct UI : public Ui_SelfTestDialog {

        QPushButton * rerunPB;

        explicit UI( SelfTestDialog * qq )
            : Ui_SelfTestDialog(),
              rerunPB( new QPushButton( i18n("Rerun Tests") ) )
        {
            setupUi( qq );

            buttonBox->addButton( rerunPB, QDialogButtonBox::ActionRole );
            buttonBox->button( QDialogButtonBox::Ok )->setText( i18n("Continue") );

            connect( rerunPB, SIGNAL(clicked()),
                     qq, SIGNAL(updateRequested()) );
        }
    } ui;
};

SelfTestDialog::SelfTestDialog( QWidget * p, Qt::WindowFlags f )
    : QDialog( p, f ), d( new Private( this ) )
{
    setAutomaticMode( false );
}

SelfTestDialog::SelfTestDialog( const std::vector< shared_ptr<SelfTest> > & tests, QWidget * p, Qt::WindowFlags f )
    : QDialog( p, f ), d( new Private( this ) )
{
    addSelfTests( tests );
    setAutomaticMode( false );
}

SelfTestDialog::~SelfTestDialog() {}

void SelfTestDialog::clear() {
    d->model.clear();
}

void SelfTestDialog::addSelfTest( const shared_ptr<SelfTest> & test ) {
    d->model.append( std::vector< shared_ptr<SelfTest> >( 1, test ) );
}

void SelfTestDialog::addSelfTests( const std::vector< shared_ptr<SelfTest> > & tests ) {
    d->model.append( tests );
}

void SelfTestDialog::setRunAtStartUp( bool on ) {
    d->ui.runAtStartUpCB->setChecked( on );
}

bool SelfTestDialog::runAtStartUp() const {
    return d->ui.runAtStartUpCB->isChecked();
}

void SelfTestDialog::setAutomaticMode( bool automatic ) {
    d->ui.buttonBox->button( QDialogButtonBox::Ok     )->setVisible(  automatic );
    d->ui.buttonBox->button( QDialogButtonBox::Cancel )->setVisible(  automatic );
    d->ui.buttonBox->button( QDialogButtonBox::Close  )->setVisible( !automatic );
}

#include "selftestdialog.moc"
#include "moc_selftestdialog.cpp"
<|endoftext|>


<commit_before>// Sh: A GPU metaprogramming language.
//
// Copyright 2003-2005 Serious Hack Inc.
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must
// not claim that you wrote the original software. If you use this
// software in a product, an acknowledgment in the product documentation
// would be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must
// not be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//////////////////////////////////////////////////////////////////////////////
#ifndef SHTABLE_HPP
#define SHTABLE_HPP

#include "ShBaseTexture.hpp"

namespace SH {

struct
ShTableTraits : public ShTextureTraits {
  ShTableTraits()
    : ShTextureTraits(1, SH_FILTER_NONE, SH_WRAP_CLAMP_TO_EDGE)
  {
  }
};

template<typename T> class ShTableRect;

template<typename T>
class ShTable1D
  : public ShBaseTexture1D<T> {
public:
  ShTable1D()
    : ShBaseTexture1D<T>(ShTableTraits())
  {}
  ShTable1D(int width)
    : ShBaseTexture1D<T>(width, ShTableTraits())
  {}
	typedef ShTableRect<T> rectangular_type;
	typedef ShBaseTexture1D<T> base_type;
  typedef T return_type;
};

template<typename T>
class ShTable2D
  : public ShBaseTexture2D<T> {
public:
  ShTable2D()
    : ShBaseTexture2D<T>(ShTableTraits())
  {}
  ShTable2D(int width, int height)
    : ShBaseTexture2D<T>(width, height, ShTableTraits())
  {}
	typedef ShTableRect<T> rectangular_type;
	typedef ShBaseTexture2D<T> base_type;
  typedef T return_type;
};

template<typename T>
class ShTableRect
  : public ShBaseTextureRect<T> {
public:
  ShTableRect()
    : ShBaseTextureRect<T>(ShTableTraits())
  {}
  ShTableRect(int width, int height)
    : ShBaseTextureRect<T>(width, height, ShTableTraits())
  {}
	typedef ShTableRect<T> rectangular_type;
	typedef ShBaseTextureRect<T> base_type;
  typedef T return_type;
};

template<typename T>
class ShTable3D
  : public ShBaseTexture3D<T> {
public:
  ShTable3D()
    : ShBaseTexture3D<T>(ShTableTraits())
  {}
  ShTable3D(int width, int height, int depth)
    : ShBaseTexture3D<T>(width, height, depth, ShTableTraits())
  {}
	typedef ShTableRect<T> rectangular_type;
	typedef ShBaseTexture3D<T> base_type;
  typedef T return_type;
};

template<typename T>
class ShTableCube
  : public ShBaseTextureCube<T> {
public:
  ShTableCube()
    : ShBaseTextureCube<T>(ShTableTraits())
  {}
  ShTableCube(int width, int height)
    : ShBaseTextureCube<T>(width, height, ShTableTraits())
  {}
	typedef ShTableRect<T> rectangular_type;
	typedef ShBaseTextureCube<T> base_type;
  typedef T return_type;
};

}

#endif
<commit_msg>Fix indentation<commit_after>// Sh: A GPU metaprogramming language.
//
// Copyright 2003-2005 Serious Hack Inc.
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must
// not claim that you wrote the original software. If you use this
// software in a product, an acknowledgment in the product documentation
// would be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must
// not be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//////////////////////////////////////////////////////////////////////////////
#ifndef SHTABLE_HPP
#define SHTABLE_HPP

#include "ShBaseTexture.hpp"

namespace SH {

struct
ShTableTraits : public ShTextureTraits {
  ShTableTraits()
    : ShTextureTraits(1, SH_FILTER_NONE, SH_WRAP_CLAMP_TO_EDGE)
  {
  }
};

template<typename T> class ShTableRect;

template<typename T>
class ShTable1D
  : public ShBaseTexture1D<T> {
public:
  ShTable1D()
    : ShBaseTexture1D<T>(ShTableTraits())
  {}
  ShTable1D(int width)
    : ShBaseTexture1D<T>(width, ShTableTraits())
  {}
  typedef ShTableRect<T> rectangular_type;
  typedef ShBaseTexture1D<T> base_type;
  typedef T return_type;
};

template<typename T>
class ShTable2D
  : public ShBaseTexture2D<T> {
public:
  ShTable2D()
    : ShBaseTexture2D<T>(ShTableTraits())
  {}
  ShTable2D(int width, int height)
    : ShBaseTexture2D<T>(width, height, ShTableTraits())
  {}
  typedef ShTableRect<T> rectangular_type;
  typedef ShBaseTexture2D<T> base_type;
  typedef T return_type;
};

template<typename T>
class ShTableRect
  : public ShBaseTextureRect<T> {
public:
  ShTableRect()
    : ShBaseTextureRect<T>(ShTableTraits())
  {}
  ShTableRect(int width, int height)
    : ShBaseTextureRect<T>(width, height, ShTableTraits())
  {}
  typedef ShTableRect<T> rectangular_type;
  typedef ShBaseTextureRect<T> base_type;
  typedef T return_type;
};

template<typename T>
class ShTable3D
  : public ShBaseTexture3D<T> {
public:
  ShTable3D()
    : ShBaseTexture3D<T>(ShTableTraits())
  {}
  ShTable3D(int width, int height, int depth)
    : ShBaseTexture3D<T>(width, height, depth, ShTableTraits())
  {}
  typedef ShTableRect<T> rectangular_type;
  typedef ShBaseTexture3D<T> base_type;
  typedef T return_type;
};

template<typename T>
class ShTableCube
  : public ShBaseTextureCube<T> {
public:
  ShTableCube()
    : ShBaseTextureCube<T>(ShTableTraits())
  {}
  ShTableCube(int width, int height)
    : ShBaseTextureCube<T>(width, height, ShTableTraits())
  {}
  typedef ShTableRect<T> rectangular_type;
  typedef ShBaseTextureCube<T> base_type;
  typedef T return_type;
};

}

#endif
<|endoftext|>


<commit_before>/*============================================================================

The Medical Imaging Interaction Toolkit (MITK)

Copyright (c) German Cancer Research Center (DKFZ)
All rights reserved.

Use of this source code is governed by a 3-clause BSD license that can be
found in the LICENSE file.

============================================================================*/

// Blueberry
#include <berryISelectionService.h>
#include <berryIWorkbenchWindow.h>
#include "mitkScaleLegendAnnotation.h"
#include "mitkLayoutAnnotationRenderer.h"
#include "mitkManualPlacementAnnotationRenderer.h"
#include "mitkTextAnnotation2D.h"

#include "QmitkPAUSViewerView.h"

const std::string QmitkPAUSViewerView::VIEW_ID = "org.mitk.views.photoacoustics.pausviewer";

QmitkPAUSViewerView::QmitkPAUSViewerView() : m_PADataStorage(mitk::StandaloneDataStorage::New()), m_USDataStorage(mitk::StandaloneDataStorage::New()), m_UltrasoundReference(nullptr)
{
}

QmitkPAUSViewerView::~QmitkPAUSViewerView()
{
  if(m_UltrasoundReference != nullptr)
    *m_UltrasoundReference = nullptr;
}

void QmitkPAUSViewerView::InitWindows()
{
  AddOverlays();
}

void QmitkPAUSViewerView::SetFocus()
{
}

void QmitkPAUSViewerView::OnSelectionChanged(berry::IWorkbenchPart::Pointer /*source*/,
  const QList<mitk::DataNode::Pointer>& /*nodes*/)
{
}

void QmitkPAUSViewerView::CreateQtPartControl(QWidget *parent)
{
  m_Controls = new Ui::QmitkPAUSViewerViewControls;
  m_Controls->setupUi(parent);

  m_Controls->m_PARenderWindow->GetRenderer()->SetDataStorage(m_PADataStorage);
  m_Controls->m_USRenderWindow->GetRenderer()->SetDataStorage(m_USDataStorage);
}

void QmitkPAUSViewerView::SetPADataStorage(mitk::StandaloneDataStorage::Pointer paStore)
{
  if (m_Controls == nullptr)
    return;

  m_PADataStorage = paStore;
  m_Controls->m_PARenderWindow->GetRenderer()->SetDataStorage(m_PADataStorage);
  m_Controls->m_PALevelWindow->SetDataStorage(m_PADataStorage);
}

void QmitkPAUSViewerView::SetUSDataStorage(mitk::StandaloneDataStorage::Pointer usStore)
{
  if (m_Controls == nullptr)
    return;

  m_USDataStorage = usStore;
  m_Controls->m_USRenderWindow->GetRenderer()->SetDataStorage(m_USDataStorage);
  m_Controls->m_USLevelWindow->SetDataStorage(m_USDataStorage);
}

vtkRenderWindow* QmitkPAUSViewerView::GetPARenderWindow()
{
  if (m_Controls == nullptr)
    return nullptr;

  return m_Controls->m_PARenderWindow->GetRenderWindow();
}

vtkRenderWindow* QmitkPAUSViewerView::GetUSRenderWindow()
{
  if (m_Controls == nullptr)
    return nullptr;

  return m_Controls->m_USRenderWindow->GetRenderWindow();
}

void QmitkPAUSViewerView::AddOverlays()
{
  //if (m_PARenderer == nullptr || /*m_PAOverlayController == nullptr||*/ m_USRenderer == nullptr /*|| m_USOverlayController == nullptr*/)
  //{
    m_PARenderer = mitk::BaseRenderer::GetInstance(GetPARenderWindow());
    m_USRenderer = mitk::BaseRenderer::GetInstance(GetUSRenderWindow());
  //}
    MITK_INFO << "1111111111111111111111";
  mitk::ScaleLegendAnnotation::Pointer scaleAnnotation = mitk::ScaleLegendAnnotation::New();
  //scaleAnnotation->SetLeftAxisVisibility(true);
  //scaleAnnotation->SetRightAxisVisibility(false);
  //scaleAnnotation->SetRightAxisVisibility(false);
  //scaleAnnotation->SetTopAxisVisibility(false);
  //scaleAnnotation->SetCornerOffsetFactor(0);
  MITK_INFO << "1111111111111111111111";

  // Add Overlays
  //![TextAnnotation2D]
  // Create a textAnnotation2D
  mitk::TextAnnotation2D::Pointer textAnnotation = mitk::TextAnnotation2D::New();

  textAnnotation->SetText("Test!"); // set UTF-8 encoded text to render
  textAnnotation->SetFontSize(40);
  textAnnotation->SetColor(1, 0, 0); // Set text color to red
  textAnnotation->SetOpacity(0.5);
  MITK_INFO << "1111111111111111111111";

  // The position of the Annotation can be set to a fixed coordinate on the display.
  mitk::Point2D pos;
  pos[0] = 10;
  pos[1] = 20;
  textAnnotation->SetPosition2D(pos);
  MITK_INFO << "1111111111111111111111";

  std::string rendererID = m_PARenderer->GetName();

  // The LayoutAnnotationRenderer can place the TextAnnotation2D at some defined corner positions
  mitk::LayoutAnnotationRenderer::AddAnnotation(
    textAnnotation, rendererID, mitk::LayoutAnnotationRenderer::TopLeft, 5, 5, 1);
  mitk::LayoutAnnotationRenderer::AddAnnotation(
    textAnnotation, m_PARenderer.GetPointer(), mitk::LayoutAnnotationRenderer::TopLeft, 5, 5, 1);
  mitk::ManualPlacementAnnotationRenderer::AddAnnotation(
    textAnnotation, m_PARenderer.GetPointer());
  MITK_INFO << "1111111111111111111111";

  mitk::LayoutAnnotationRenderer::AddAnnotation(scaleAnnotation.GetPointer(), m_PARenderer->GetName(), mitk::LayoutAnnotationRenderer::TopLeft, 5, 5, 1);
  mitk::LayoutAnnotationRenderer::AddAnnotation(scaleAnnotation.GetPointer(), m_USRenderer, mitk::LayoutAnnotationRenderer::TopLeft, 5, 5, 1);
  MITK_INFO << "1111111111111111111111";

}

void QmitkPAUSViewerView::RemoveOverlays()
{
 // m_PAOverlayManager->RemoveAllOverlays();
}

void QmitkPAUSViewerView::SetUltrasoundReference(QmitkPAUSViewerView** ultrasoundReference)
{
  m_UltrasoundReference = ultrasoundReference;
}
<commit_msg>Fix method names<commit_after>/*============================================================================

The Medical Imaging Interaction Toolkit (MITK)

Copyright (c) German Cancer Research Center (DKFZ)
All rights reserved.

Use of this source code is governed by a 3-clause BSD license that can be
found in the LICENSE file.

============================================================================*/

// Blueberry
#include <berryISelectionService.h>
#include <berryIWorkbenchWindow.h>
#include "mitkScaleLegendAnnotation.h"
#include "mitkLayoutAnnotationRenderer.h"
#include "mitkManualPlacementAnnotationRenderer.h"
#include "mitkTextAnnotation2D.h"

#include "QmitkPAUSViewerView.h"

const std::string QmitkPAUSViewerView::VIEW_ID = "org.mitk.views.photoacoustics.pausviewer";

QmitkPAUSViewerView::QmitkPAUSViewerView() : m_PADataStorage(mitk::StandaloneDataStorage::New()), m_USDataStorage(mitk::StandaloneDataStorage::New()), m_UltrasoundReference(nullptr)
{
}

QmitkPAUSViewerView::~QmitkPAUSViewerView()
{
  if(m_UltrasoundReference != nullptr)
    *m_UltrasoundReference = nullptr;
}

void QmitkPAUSViewerView::InitWindows()
{
  AddOverlays();
}

void QmitkPAUSViewerView::SetFocus()
{
}

void QmitkPAUSViewerView::OnSelectionChanged(berry::IWorkbenchPart::Pointer /*source*/,
  const QList<mitk::DataNode::Pointer>& /*nodes*/)
{
}

void QmitkPAUSViewerView::CreateQtPartControl(QWidget *parent)
{
  m_Controls = new Ui::QmitkPAUSViewerViewControls;
  m_Controls->setupUi(parent);

  m_Controls->m_PARenderWindow->GetRenderer()->SetDataStorage(m_PADataStorage);
  m_Controls->m_USRenderWindow->GetRenderer()->SetDataStorage(m_USDataStorage);
}

void QmitkPAUSViewerView::SetPADataStorage(mitk::StandaloneDataStorage::Pointer paStore)
{
  if (m_Controls == nullptr)
    return;

  m_PADataStorage = paStore;
  m_Controls->m_PARenderWindow->GetRenderer()->SetDataStorage(m_PADataStorage);
  m_Controls->m_PALevelWindow->SetDataStorage(m_PADataStorage);
}

void QmitkPAUSViewerView::SetUSDataStorage(mitk::StandaloneDataStorage::Pointer usStore)
{
  if (m_Controls == nullptr)
    return;

  m_USDataStorage = usStore;
  m_Controls->m_USRenderWindow->GetRenderer()->SetDataStorage(m_USDataStorage);
  m_Controls->m_USLevelWindow->SetDataStorage(m_USDataStorage);
}

vtkRenderWindow* QmitkPAUSViewerView::GetPARenderWindow()
{
  if (m_Controls == nullptr)
    return nullptr;

  return m_Controls->m_PARenderWindow->renderWindow();
}

vtkRenderWindow* QmitkPAUSViewerView::GetUSRenderWindow()
{
  if (m_Controls == nullptr)
    return nullptr;

  return m_Controls->m_USRenderWindow->renderWindow();
}

void QmitkPAUSViewerView::AddOverlays()
{
  //if (m_PARenderer == nullptr || /*m_PAOverlayController == nullptr||*/ m_USRenderer == nullptr /*|| m_USOverlayController == nullptr*/)
  //{
    m_PARenderer = mitk::BaseRenderer::GetInstance(GetPARenderWindow());
    m_USRenderer = mitk::BaseRenderer::GetInstance(GetUSRenderWindow());
  //}
    MITK_INFO << "1111111111111111111111";
  mitk::ScaleLegendAnnotation::Pointer scaleAnnotation = mitk::ScaleLegendAnnotation::New();
  //scaleAnnotation->SetLeftAxisVisibility(true);
  //scaleAnnotation->SetRightAxisVisibility(false);
  //scaleAnnotation->SetRightAxisVisibility(false);
  //scaleAnnotation->SetTopAxisVisibility(false);
  //scaleAnnotation->SetCornerOffsetFactor(0);
  MITK_INFO << "1111111111111111111111";

  // Add Overlays
  //![TextAnnotation2D]
  // Create a textAnnotation2D
  mitk::TextAnnotation2D::Pointer textAnnotation = mitk::TextAnnotation2D::New();

  textAnnotation->SetText("Test!"); // set UTF-8 encoded text to render
  textAnnotation->SetFontSize(40);
  textAnnotation->SetColor(1, 0, 0); // Set text color to red
  textAnnotation->SetOpacity(0.5);
  MITK_INFO << "1111111111111111111111";

  // The position of the Annotation can be set to a fixed coordinate on the display.
  mitk::Point2D pos;
  pos[0] = 10;
  pos[1] = 20;
  textAnnotation->SetPosition2D(pos);
  MITK_INFO << "1111111111111111111111";

  std::string rendererID = m_PARenderer->GetName();

  // The LayoutAnnotationRenderer can place the TextAnnotation2D at some defined corner positions
  mitk::LayoutAnnotationRenderer::AddAnnotation(
    textAnnotation, rendererID, mitk::LayoutAnnotationRenderer::TopLeft, 5, 5, 1);
  mitk::LayoutAnnotationRenderer::AddAnnotation(
    textAnnotation, m_PARenderer.GetPointer(), mitk::LayoutAnnotationRenderer::TopLeft, 5, 5, 1);
  mitk::ManualPlacementAnnotationRenderer::AddAnnotation(
    textAnnotation, m_PARenderer.GetPointer());
  MITK_INFO << "1111111111111111111111";

  mitk::LayoutAnnotationRenderer::AddAnnotation(scaleAnnotation.GetPointer(), m_PARenderer->GetName(), mitk::LayoutAnnotationRenderer::TopLeft, 5, 5, 1);
  mitk::LayoutAnnotationRenderer::AddAnnotation(scaleAnnotation.GetPointer(), m_USRenderer, mitk::LayoutAnnotationRenderer::TopLeft, 5, 5, 1);
  MITK_INFO << "1111111111111111111111";

}

void QmitkPAUSViewerView::RemoveOverlays()
{
 // m_PAOverlayManager->RemoveAllOverlays();
}

void QmitkPAUSViewerView::SetUltrasoundReference(QmitkPAUSViewerView** ultrasoundReference)
{
  m_UltrasoundReference = ultrasoundReference;
}
<|endoftext|>


<commit_before>/*
    Copyright 2015 KU Leuven, Dept. Electrical Engineering, ESAT/PSI, Leuven, Belgium

    Written by Daan Christiaens, 26/09/15.

    This file is part of MRtrix.

    MRtrix is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    MRtrix is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with MRtrix.  If not, see <http://www.gnu.org/licenses/>.

*/

#include "command.h"
#include "file/ofstream.h"
#include "dwi/tractography/file.h"
#include "dwi/tractography/properties.h"

using namespace MR;
using namespace App;
using namespace MR::DWI::Tractography;

void usage ()
{
  AUTHOR = "Daan Christiaens (daan.christiaens@gmail.com), "
           "J-Donald Tournier (jdtournier@gmail.com), "
           "Philip Broser (philip.broser@me.com).";

  DESCRIPTION
  + "Convert between different track file formats."

  + "The program currently supports MRtrix .tck files, "
    "VTK polydata files, and ascii text files.";

  ARGUMENTS
  + Argument ("input", "the input track file.").type_file_in ()
  + Argument ("output", "the output track file.").type_file_out ();

  OPTIONS
  + Option ("scanner2voxel",
      "if specified, the properties of this image will be used to convert "
      "track point positions from real (scanner) coordinates into voxel coordinates.")
    + Argument ("reference").type_image_in ()

  + Option ("scanner2image",
      "if specified, the properties of this image will be used to convert "
      "track point positions from real (scanner) coordinates into image coordinates (in mm).")
  +    Argument ("reference").type_image_in ();

}

class VTKWriter
{
public:
    VTKWriter(const std::string& file) : VTKout (file) {
        // create and write header of VTK output file:
        VTKout <<
          "# vtk DataFile Version 1.0\n"
          "Data values for Tracks\n"
          "ASCII\n"
          "DATASET POLYDATA\n"
          "POINTS ";
        // keep track of offset to write proper value later:
        offset_num_points = VTKout.tellp();
        VTKout << "XXXXXXXXXX float\n";
    }

    template <class ValueType>
    bool operator() (const Streamline<ValueType>& tck) {
        // write out points, and build index of tracks:
        size_t start_index = current_index;
        current_index += tck.size();
        track_list.push_back (std::pair<size_t,size_t> (start_index, current_index));

        for (auto pos : tck) {
          VTKout << pos[0] << " " << pos[1] << " " << pos[2] << "\n";
        }
        return true;
    }

    ~VTKWriter() {
        // write out list of tracks:
        VTKout << "LINES " << track_list.size() << " " << track_list.size() + current_index << "\n";
        for (const auto track : track_list) {
          VTKout << track.second - track.first << " " << track.first;
          for (size_t i = track.first + 1; i < track.second; ++i)
            VTKout << " " << i;
          VTKout << "\n";
        };

        // write back total number of points:
        VTKout.seekp (offset_num_points);
        std::string num_points (str (current_index));
        num_points.resize (10, ' ');
        VTKout.write (num_points.c_str(), 10);

        VTKout.close();
    }

private:
    File::OFStream VTKout;
    size_t offset_num_points;
    std::vector<std::pair<size_t,size_t>> track_list;
    size_t current_index = 0;

};

void run ()
{
    Properties properties;
    Reader read (argument[0], properties);

    VTKWriter write (argument[1]);

    // Tranform matrix
    transform_type T;
    T.setIdentity();
    size_t nopts = 0;
    auto opt = get_options("scanner2voxel");
    if (opt.size()) {
        auto header = Header::open(opt[0][0]);
        T = Transform(header).scanner2voxel;
        nopts++;
    }
    opt = get_options("scanner2image");
    if (opt.size()) {
        auto header = Header::open(opt[0][0]);
        T = Transform(header).scanner2image;
        nopts++;
    }
    if (nopts > 1) {
        throw Exception("Transform options are mutually exclusive.");
    }

    Streamline<float> tck;
    while (read(tck))
    {
        for (auto& pos : tck) {
            Eigen::Vector3 x {pos[0], pos[1], pos[2]};
            auto y = T * x;
            pos = {y[0], y[1], y[2]};
        }
        write(tck);
    }

}

<commit_msg>small change to avoid narrowing conversion compiler warning<commit_after>/*
    Copyright 2015 KU Leuven, Dept. Electrical Engineering, ESAT/PSI, Leuven, Belgium

    Written by Daan Christiaens, 26/09/15.

    This file is part of MRtrix.

    MRtrix is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    MRtrix is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with MRtrix.  If not, see <http://www.gnu.org/licenses/>.

*/

#include "command.h"
#include "file/ofstream.h"
#include "dwi/tractography/file.h"
#include "dwi/tractography/properties.h"

using namespace MR;
using namespace App;
using namespace MR::DWI::Tractography;

void usage ()
{
  AUTHOR = "Daan Christiaens (daan.christiaens@gmail.com), "
           "J-Donald Tournier (jdtournier@gmail.com), "
           "Philip Broser (philip.broser@me.com).";

  DESCRIPTION
  + "Convert between different track file formats."

  + "The program currently supports MRtrix .tck files, "
    "VTK polydata files, and ascii text files.";

  ARGUMENTS
  + Argument ("input", "the input track file.").type_file_in ()
  + Argument ("output", "the output track file.").type_file_out ();

  OPTIONS
  + Option ("scanner2voxel",
      "if specified, the properties of this image will be used to convert "
      "track point positions from real (scanner) coordinates into voxel coordinates.")
    + Argument ("reference").type_image_in ()

  + Option ("scanner2image",
      "if specified, the properties of this image will be used to convert "
      "track point positions from real (scanner) coordinates into image coordinates (in mm).")
  +    Argument ("reference").type_image_in ();

}

class VTKWriter
{
public:
    VTKWriter(const std::string& file) : VTKout (file) {
        // create and write header of VTK output file:
        VTKout <<
          "# vtk DataFile Version 1.0\n"
          "Data values for Tracks\n"
          "ASCII\n"
          "DATASET POLYDATA\n"
          "POINTS ";
        // keep track of offset to write proper value later:
        offset_num_points = VTKout.tellp();
        VTKout << "XXXXXXXXXX float\n";
    }

    template <class ValueType>
    bool operator() (const Streamline<ValueType>& tck) {
        // write out points, and build index of tracks:
        size_t start_index = current_index;
        current_index += tck.size();
        track_list.push_back (std::pair<size_t,size_t> (start_index, current_index));

        for (auto pos : tck) {
          VTKout << pos[0] << " " << pos[1] << " " << pos[2] << "\n";
        }
        return true;
    }

    ~VTKWriter() {
        // write out list of tracks:
        VTKout << "LINES " << track_list.size() << " " << track_list.size() + current_index << "\n";
        for (const auto track : track_list) {
          VTKout << track.second - track.first << " " << track.first;
          for (size_t i = track.first + 1; i < track.second; ++i)
            VTKout << " " << i;
          VTKout << "\n";
        };

        // write back total number of points:
        VTKout.seekp (offset_num_points);
        std::string num_points (str (current_index));
        num_points.resize (10, ' ');
        VTKout.write (num_points.c_str(), 10);

        VTKout.close();
    }

private:
    File::OFStream VTKout;
    size_t offset_num_points;
    std::vector<std::pair<size_t,size_t>> track_list;
    size_t current_index = 0;

};

void run ()
{
    Properties properties;
    Reader read (argument[0], properties);

    VTKWriter write (argument[1]);

    // Tranform matrix
    transform_type T;
    T.setIdentity();
    size_t nopts = 0;
    auto opt = get_options("scanner2voxel");
    if (opt.size()) {
        auto header = Header::open(opt[0][0]);
        T = Transform(header).scanner2voxel;
        nopts++;
    }
    opt = get_options("scanner2image");
    if (opt.size()) {
        auto header = Header::open(opt[0][0]);
        T = Transform(header).scanner2image;
        nopts++;
    }
    if (nopts > 1) {
        throw Exception("Transform options are mutually exclusive.");
    }

    Streamline<float> tck;
    while (read(tck))
    {
        for (auto& pos : tck) {
            Eigen::Vector3 x {pos[0], pos[1], pos[2]};
            auto y = T * x;
            pos = y.cast<float>();
        }
        write(tck);
    }

}

<|endoftext|>


<commit_before>#include <QtGui>
#include <QtOpenGL>

#include <math.h>

#include "glwidget.h"

#ifndef GL_MULTISAMPLE
#define GL_MULTISAMPLE  0x809D
#endif

GLWidget::GLWidget(QWidget *parent)
    : QGLWidget(QGLFormat(QGL::SampleBuffers), parent)
{
    xRot = 0;
    yRot = 0;
    zRot = 0;
}

void GLWidget::initializeGL()
{
    qglClearColor(Qt::black);

    glEnable(GL_DEPTH_TEST);
    glEnable(GL_CULL_FACE);
    glShadeModel(GL_SMOOTH);
    glEnable(GL_LIGHTING);
    glEnable(GL_LIGHT0);
    glEnable(GL_MULTISAMPLE);
    static GLfloat lightPosition[4] = { 0.5, 5.0, 7.0, 1.0 };
    glLightfv(GL_LIGHT0, GL_POSITION, lightPosition);
}

void GLWidget::paintGL()
{
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    glLoadIdentity();
    glTranslatef(0.0, 0.0, -10.0);
    glRotatef(xRot / 16.0, 1.0, 0.0, 0.0);
    glRotatef(yRot / 16.0, 0.0, 1.0, 0.0);
    glRotatef(zRot / 16.0, 0.0, 0.0, 1.0);
}

void GLWidget::resizeGL(int width, int height)
{
    int side = qMin(width, height);
    glViewport((width - side) / 2, (height - side) / 2, side, side);

    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
#ifdef QT_OPENGL_ES_1
    glOrthof(-0.5, +0.5, -0.5, +0.5, 4.0, 15.0);
#else
    glOrtho(-0.5, +0.5, -0.5, +0.5, 4.0, 15.0);
#endif
    glMatrixMode(GL_MODELVIEW);
}

/**
 * Listen for the escape key for quick exiting.
 */
void GLWidget::keyPressEvent(QKeyEvent *e)
{
    if (e->key() == Qt::Key_Escape)
        close();
    else
        QWidget::keyPressEvent(e);
}

void GLWidget::mousePressEvent(QMouseEvent *event)
{
    lastPos = event->pos();
}

void GLWidget::mouseMoveEvent(QMouseEvent *event)
{
    int dx = event->x() - lastPos.x();
    int dy = event->y() - lastPos.y();

    if (event->buttons() & Qt::LeftButton) {
        setXRotation(xRot + 8 * dy);
        setYRotation(yRot + 8 * dx);
    } else if (event->buttons() & Qt::RightButton) {
        setXRotation(xRot + 8 * dy);
        setZRotation(zRot + 8 * dx);
    }
    lastPos = event->pos();
}

static void qNormalizeAngle(int &angle)
{
    while (angle < 0)
        angle += 360 * 16;
    while (angle > 360 * 16)
        angle -= 360 * 16;
}

void GLWidget::setXRotation(int angle)
{
    qNormalizeAngle(angle);
    if (angle != xRot) {
        xRot = angle;
        emit xRotationChanged(angle);
        updateGL();
    }
}

void GLWidget::setYRotation(int angle)
{
    qNormalizeAngle(angle);
    if (angle != yRot) {
        yRot = angle;
        emit yRotationChanged(angle);
        updateGL();
    }
}

void GLWidget::setZRotation(int angle)
{
    qNormalizeAngle(angle);
    if (angle != zRot) {
        zRot = angle;
        emit zRotationChanged(angle);
        updateGL();
    }
}

<commit_msg>Added comment for mouseMoveEvent<commit_after>#include <QtGui>
#include <QtOpenGL>

#include <math.h>

#include "glwidget.h"

#ifndef GL_MULTISAMPLE
#define GL_MULTISAMPLE  0x809D
#endif

GLWidget::GLWidget(QWidget *parent)
    : QGLWidget(QGLFormat(QGL::SampleBuffers), parent)
{
    xRot = 0;
    yRot = 0;
    zRot = 0;
}

void GLWidget::initializeGL()
{
    qglClearColor(Qt::black);

    glEnable(GL_DEPTH_TEST);
    glEnable(GL_CULL_FACE);
    glShadeModel(GL_SMOOTH);
    glEnable(GL_LIGHTING);
    glEnable(GL_LIGHT0);
    glEnable(GL_MULTISAMPLE);
    static GLfloat lightPosition[4] = { 0.5, 5.0, 7.0, 1.0 };
    glLightfv(GL_LIGHT0, GL_POSITION, lightPosition);
}

void GLWidget::paintGL()
{
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    glLoadIdentity();
    glTranslatef(0.0, 0.0, -10.0);
    glRotatef(xRot / 16.0, 1.0, 0.0, 0.0);
    glRotatef(yRot / 16.0, 0.0, 1.0, 0.0);
    glRotatef(zRot / 16.0, 0.0, 0.0, 1.0);
}

void GLWidget::resizeGL(int width, int height)
{
    int side = qMin(width, height);
    glViewport((width - side) / 2, (height - side) / 2, side, side);

    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
#ifdef QT_OPENGL_ES_1
    glOrthof(-0.5, +0.5, -0.5, +0.5, 4.0, 15.0);
#else
    glOrtho(-0.5, +0.5, -0.5, +0.5, 4.0, 15.0);
#endif
    glMatrixMode(GL_MODELVIEW);
}

/**
 * Listen for the escape key for quick exiting.
 */
void GLWidget::keyPressEvent(QKeyEvent *e)
{
    if (e->key() == Qt::Key_Escape)
        close();
    else
        QWidget::keyPressEvent(e);
}

void GLWidget::mousePressEvent(QMouseEvent *event)
{
    lastPos = event->pos();
}

/**
 * Interpret the mouse event to rotate the camera around the scene.
 */
void GLWidget::mouseMoveEvent(QMouseEvent *event)
{
    int dx = event->x() - lastPos.x();
    int dy = event->y() - lastPos.y();

    if (event->buttons() & Qt::LeftButton) {
        setXRotation(xRot + 8 * dy);
        setYRotation(yRot + 8 * dx);
    } else if (event->buttons() & Qt::RightButton) {
        setXRotation(xRot + 8 * dy);
        setZRotation(zRot + 8 * dx);
    }
    lastPos = event->pos();
}

static void qNormalizeAngle(int &angle)
{
    while (angle < 0)
        angle += 360 * 16;
    while (angle > 360 * 16)
        angle -= 360 * 16;
}

void GLWidget::setXRotation(int angle)
{
    qNormalizeAngle(angle);
    if (angle != xRot) {
        xRot = angle;
        emit xRotationChanged(angle);
        updateGL();
    }
}

void GLWidget::setYRotation(int angle)
{
    qNormalizeAngle(angle);
    if (angle != yRot) {
        yRot = angle;
        emit yRotationChanged(angle);
        updateGL();
    }
}

void GLWidget::setZRotation(int angle)
{
    qNormalizeAngle(angle);
    if (angle != zRot) {
        zRot = angle;
        emit zRotationChanged(angle);
        updateGL();
    }
}

<|endoftext|>