<commit_before>// Base header file.  Must be first.
#include <Include/PlatformDefinitions.hpp>

#if defined(XALAN_OLD_STREAM_HEADERS)
#include <fstream.h>
#include <iostream.h>
#else
#include <fstream>
#include <iostream>
#endif

#include <util/PlatformUtils.hpp>

#include <PlatformSupport/DOMStringHelper.hpp>
#include <PlatformSupport/XalanOutputStreamPrintWriter.hpp>
#include <PlatformSupport/XalanStdOutputStream.hpp>

#include <DOMSupport/DOMSupportDefault.hpp>

#include <XPath/XObjectFactoryDefault.hpp>
#include <XPath/XPathFactoryDefault.hpp>
#include <XPath/XPathProcessorImpl.hpp>

#include <XalanSourceTree/XalanSourceTreeDOMSupport.hpp>
#include <XalanSourceTree/XalanSourceTreeParserLiaison.hpp>

#include <XSLT/XSLTEngineImpl.hpp>
#include <XSLT/XSLTInit.hpp>
#include <XSLT/XSLTInputSource.hpp>
#include <XSLT/XSLTResultTarget.hpp>
#include <XSLT/StylesheetConstructionContextDefault.hpp>
#include <XSLT/StylesheetExecutionContextDefault.hpp>
#include <XSLT/TraceListenerDefault.hpp>
#include <XSLT/XSLTProcessorEnvSupportDefault.hpp>

int
main(
			int				argc,
			const char*		argv[])
{
#if !defined(XALAN_NO_NAMESPACES)
	using std::auto_ptr;
	using std::cerr;
	using std::endl;
#endif

	// TraceListener flags...
	bool traceTemplates = false;
	bool traceTemplateChildren = false;
	bool traceGenerationEvent = false;
	bool traceSelectionEvent = false;

	if (argc < 2 || argc > 5)
	{
		cerr << "Usage: TraceListen [+ 1 or more of following] -TT -TG -TS -TTC" << endl;
		return -1;
	}

	// Set the TraceListener flags...
	for (int i = 1;	i < argc;	i ++)
	{
		if(!stricmp("-TT", argv[i]))
		{
			traceTemplates = true;
		}
		else if(!stricmp("-TG", argv[i]))
		{
			traceGenerationEvent = true;
		}
		else if(!stricmp("-TS", argv[i]))
		{
			traceSelectionEvent = true;
		}
		else if(!stricmp("-TTC", argv[i]))
		{
			traceTemplateChildren = true;
		}
		else
		{
  			cerr << "Usage: TraceListen [+ 1 or more of following] -TT -TG -TS -TTC" << endl;
	  		return -1;
		}
	}

	try
	{
		// Call the static initializers...
		XMLPlatformUtils::Initialize();

		{
			// Initialize the Xalan XSLT subsystem...
			XSLTInit						theInit;

			// Create some support objects that are necessary for running the processor...
			XalanSourceTreeDOMSupport		theDOMSupport;
			XalanSourceTreeParserLiaison	theParserLiaison(theDOMSupport);

			// Hook the two together...
			theDOMSupport.setParserLiaison(&theParserLiaison);

			// Create some more support objects.
			XSLTProcessorEnvSupportDefault	theXSLTProcessorEnvSupport;
			XObjectFactoryDefault			theXObjectFactory;
			XPathFactoryDefault				theXPathFactory;

			// Create a processor...
			XSLTEngineImpl	theProcessor(
						theParserLiaison,
						theXSLTProcessorEnvSupport,
						theDOMSupport,
						theXObjectFactory,
						theXPathFactory);

			// Connect the processor to the support object...
			theXSLTProcessorEnvSupport.setProcessor(&theProcessor);

			// Create a stylesheet construction context, and a stylesheet
			// execution context...
			StylesheetConstructionContextDefault	theConstructionContext(
							theProcessor,
							theXSLTProcessorEnvSupport,
							theXPathFactory);

			StylesheetExecutionContextDefault		theExecutionContext(
							theProcessor,
							theXSLTProcessorEnvSupport,
							theDOMSupport,
							theXObjectFactory);

			// Our input files...The assumption is that the executable will be run
			// from same directory as the input files.
			const XalanDOMString		theXMLFileName("birds.xml");
			const XalanDOMString		theXSLFileName("birds.xsl");

			// Our input sources...
			XSLTInputSource		theInputSource(c_wstr(theXMLFileName));
			XSLTInputSource		theStylesheetSource(c_wstr(theXSLFileName));

			// Our output target...
			const XalanDOMString	theOutputFile("birds.out");
			XSLTResultTarget		theResultTarget(theOutputFile);

			// Set up a diagnostic writer to be used by the TraceListener...
			XalanStdOutputStream			theStdErr(cerr);
			XalanOutputStreamPrintWriter	diagnosticsWriter(theStdErr);

			// Set up the TraceListener...
			TraceListenerDefault		theTraceListener(
					diagnosticsWriter,
					traceTemplates,
					traceTemplateChildren,
					traceGenerationEvent,
					traceSelectionEvent);

			// Add the TraceListener to the XSLT processor...
			theProcessor.setTraceSelects(traceSelectionEvent);
			theProcessor.addTraceListener(&theTraceListener);

			// Perform the transformation...
			theProcessor.process(
							theInputSource,
							theStylesheetSource,
							theResultTarget,
							theConstructionContext,
							theExecutionContext);

		}

		// Call the static terminator for Xerces...
		XMLPlatformUtils::Terminate();
	}
	catch(...)
	{
		cerr << "Exception caught!  Exiting..." << endl;
	}

	return 0;
}
<commit_msg>Removed extraneous using directive.<commit_after>// Base header file.  Must be first.
#include <Include/PlatformDefinitions.hpp>

#if defined(XALAN_OLD_STREAM_HEADERS)
#include <fstream.h>
#include <iostream.h>
#else
#include <fstream>
#include <iostream>
#endif

#include <util/PlatformUtils.hpp>

#include <PlatformSupport/DOMStringHelper.hpp>
#include <PlatformSupport/XalanOutputStreamPrintWriter.hpp>
#include <PlatformSupport/XalanStdOutputStream.hpp>

#include <DOMSupport/DOMSupportDefault.hpp>

#include <XPath/XObjectFactoryDefault.hpp>
#include <XPath/XPathFactoryDefault.hpp>
#include <XPath/XPathProcessorImpl.hpp>

#include <XalanSourceTree/XalanSourceTreeDOMSupport.hpp>
#include <XalanSourceTree/XalanSourceTreeParserLiaison.hpp>

#include <XSLT/XSLTEngineImpl.hpp>
#include <XSLT/XSLTInit.hpp>
#include <XSLT/XSLTInputSource.hpp>
#include <XSLT/XSLTResultTarget.hpp>
#include <XSLT/StylesheetConstructionContextDefault.hpp>
#include <XSLT/StylesheetExecutionContextDefault.hpp>
#include <XSLT/TraceListenerDefault.hpp>
#include <XSLT/XSLTProcessorEnvSupportDefault.hpp>

int
main(
			int				argc,
			const char*		argv[])
{
#if !defined(XALAN_NO_NAMESPACES)
	using std::cerr;
	using std::endl;
#endif

	// TraceListener flags...
	bool traceTemplates = false;
	bool traceTemplateChildren = false;
	bool traceGenerationEvent = false;
	bool traceSelectionEvent = false;

	if (argc < 2 || argc > 5)
	{
		cerr << "Usage: TraceListen [+ 1 or more of following] -TT -TG -TS -TTC" << endl;
		return -1;
	}

	// Set the TraceListener flags...
	for (int i = 1;	i < argc;	i ++)
	{
		if(!stricmp("-TT", argv[i]))
		{
			traceTemplates = true;
		}
		else if(!stricmp("-TG", argv[i]))
		{
			traceGenerationEvent = true;
		}
		else if(!stricmp("-TS", argv[i]))
		{
			traceSelectionEvent = true;
		}
		else if(!stricmp("-TTC", argv[i]))
		{
			traceTemplateChildren = true;
		}
		else
		{
  			cerr << "Usage: TraceListen [+ 1 or more of following] -TT -TG -TS -TTC" << endl;
	  		return -1;
		}
	}

	try
	{
		// Call the static initializers...
		XMLPlatformUtils::Initialize();

		{
			// Initialize the Xalan XSLT subsystem...
			XSLTInit						theInit;

			// Create some support objects that are necessary for running the processor...
			XalanSourceTreeDOMSupport		theDOMSupport;
			XalanSourceTreeParserLiaison	theParserLiaison(theDOMSupport);

			// Hook the two together...
			theDOMSupport.setParserLiaison(&theParserLiaison);

			// Create some more support objects.
			XSLTProcessorEnvSupportDefault	theXSLTProcessorEnvSupport;
			XObjectFactoryDefault			theXObjectFactory;
			XPathFactoryDefault				theXPathFactory;

			// Create a processor...
			XSLTEngineImpl	theProcessor(
						theParserLiaison,
						theXSLTProcessorEnvSupport,
						theDOMSupport,
						theXObjectFactory,
						theXPathFactory);

			// Connect the processor to the support object...
			theXSLTProcessorEnvSupport.setProcessor(&theProcessor);

			// Create a stylesheet construction context, and a stylesheet
			// execution context...
			StylesheetConstructionContextDefault	theConstructionContext(
							theProcessor,
							theXSLTProcessorEnvSupport,
							theXPathFactory);

			StylesheetExecutionContextDefault		theExecutionContext(
							theProcessor,
							theXSLTProcessorEnvSupport,
							theDOMSupport,
							theXObjectFactory);

			// Our input files...The assumption is that the executable will be run
			// from same directory as the input files.
			const XalanDOMString		theXMLFileName("birds.xml");
			const XalanDOMString		theXSLFileName("birds.xsl");

			// Our input sources...
			XSLTInputSource		theInputSource(c_wstr(theXMLFileName));
			XSLTInputSource		theStylesheetSource(c_wstr(theXSLFileName));

			// Our output target...
			const XalanDOMString	theOutputFile("birds.out");
			XSLTResultTarget		theResultTarget(theOutputFile);

			// Set up a diagnostic writer to be used by the TraceListener...
			XalanStdOutputStream			theStdErr(cerr);
			XalanOutputStreamPrintWriter	diagnosticsWriter(theStdErr);

			// Set up the TraceListener...
			TraceListenerDefault		theTraceListener(
					diagnosticsWriter,
					traceTemplates,
					traceTemplateChildren,
					traceGenerationEvent,
					traceSelectionEvent);

			// Add the TraceListener to the XSLT processor...
			theProcessor.setTraceSelects(traceSelectionEvent);
			theProcessor.addTraceListener(&theTraceListener);

			// Perform the transformation...
			theProcessor.process(
							theInputSource,
							theStylesheetSource,
							theResultTarget,
							theConstructionContext,
							theExecutionContext);

		}

		// Call the static terminator for Xerces...
		XMLPlatformUtils::Terminate();
	}
	catch(...)
	{
		cerr << "Exception caught!  Exiting..." << endl;
	}

	return 0;
}
<|endoftext|>


<commit_before>/**
 * @file platform.cpp
 * @brief Purpose: Contains the methods for Platform class.
 *
 * MIT License
 * Copyright (c) 2017 MindScape
 *
 * https://github.com/TecProg2017-2/mindscape/blob/master/LICENSE.md
 */

#include "../include/platform.hpp"
#include "../engine/include/game.hpp"

using namespace mindscape;

/**
 * @brief Platform class constructor
 *
 * Initializes everything need for the platform.
 *
 * @param name The object's name.
 * @param position Pair of integers representing the x and y position.
 * @param priority Priority in object's rendering.
 *
 * @return void
 */
Platform::Platform(
		std::string name,
		std::pair<int, int> position,
		int priority)
		: engine::GameObject(name, position, priority,
							 {{engine::KeyboardEvent::LEFT,  "MOVE_LEFT"},
							  {engine::KeyboardEvent::RIGHT, "MOVE_RIGHT"}}
) {};

/**
 * @brief Event processor method
 *
 * Process Game Events received.
 *
 * @param game_event The game event to be received.
 *
 * @return void
 */
void Platform::on_event(GameEvent game_event) {

	platform_movement(game_event);

	/*
	 * First Level Limiter.
     * All limiter are in pixels.
	 */
	first_level_clown(game_event);

	/*
	 * Second Level Limiter
	 * All limiters are in pixels
	 */
	second_level_boss(game_event);
}

/**
 * @brief Movements platform.
 *
 * Movements platform based on the girl's movement
 *
 * @param game_event The game event to be received.
 *
 * @return void.
 */
void Platform::platform_movement(GameEvent game_event){
	std::string event_name = game_event.game_event_name; /**< string. Name of the game_event */
	const int movement_platform = 10; /**< int. Movement of the platform (value in pixels) */

	if (event_name == "MOVE_LEFT" && !engine::GameObject::on_limit_of_level) {
		/* set the right position of the platform based in the game_event */

		set_position_x(get_position_x() + movement_platform);
	}
	else if (event_name == "MOVE_RIGHT" && !engine::GameObject::on_limit_of_level) {
		/* set the left position of the platform based in the game_event */

		set_position_x(get_position_x() - movement_platform);
	}
	else {
		/* Do nothing */
	}
}

/**
 * @brief Level limiter.
 *
 * This method limits the level in right and left position in pixels.
 *
 * @param game_event The game event to be received.
 *
 * @return void.
 */
void Platform::first_level_clown(GameEvent game_event){
	if (name == "clown_tree") {
		const int first_level_inicial_limiter = -1300; /**< Int. Left limit in pixel of the girl can walk */
		const int first_level_final_limiter = 13350; /**< Int. Right limit in pixel of the girl can walk */

		if (get_position_x() > first_level_final_limiter) {
			/* Sets the limit of the map in axis x and don't let the girl pass this limit */

			engine::GameObject::on_limit_of_level = true;

			set_position_x(first_level_final_limiter);
		}
		else if (get_position_x() < first_level_inicial_limiter) {
			/* Sets the limit of the map in axis x and don't let the girl pass this limit */

			engine::GameObject::on_limit_of_level = true;

			set_position_x(first_level_inicial_limiter);
		}
		else {
			/* The girl is in between the limits */

			engine::GameObject::on_limit_of_level = false;
		}
	}
	else {
		/* Do nothing */
	}
}

/**
 * @brief Level limiter.
 *
 * This method limits the level in right and left position in pixels.
 *
 * @param game_event The game event to be received.
 *
 * @return void.
 */
void Platform::second_level_boss(GameEvent game_event){
	if (name == "limiter") {
		const int second_level_inicial_limiter = 0; /**< Int. Left limit in pixel of the girl can walk */
		const int second_level_final_limiter = 3000; /**< Int. Right limit in pixel of the girl can walk */

		if (get_position_x() > second_level_final_limiter) {
			/* Sets the limit of the map in axis x and don't let the girl pass this limit */

			engine::GameObject::on_limit_of_level = true;

			set_position_x(second_level_final_limiter);
		}
		else if (get_position_x() < second_level_inicial_limiter) {
			/* Sets the limit of the map in axis x and don't let the girl pass this limit */

			engine::GameObject::on_limit_of_level = true;

			set_position_x(second_level_inicial_limiter);
		}
		else {
			/* The girl is in between the limits */

			engine::GameObject::on_limit_of_level = false;
		}
	}
	else {
		/* Do nothing */
	}
}
<commit_msg>[ASSERT] Applies technique in platform.cpp<commit_after>/**
 * @file platform.cpp
 * @brief Purpose: Contains the methods for Platform class.
 *
 * MIT License
 * Copyright (c) 2017 MindScape
 *
 * https://github.com/TecProg2017-2/mindscape/blob/master/LICENSE.md
 */

#include "../include/platform.hpp"
#include "../engine/include/game.hpp"
#include <assert.h>
using namespace mindscape;

/**
 * @brief Platform class constructor
 *
 * Initializes everything need for the platform.
 *
 * @param name The object's name.
 * @param position Pair of integers representing the x and y position.
 * @param priority Priority in object's rendering.
 *
 * @return void
 */
Platform::Platform(
		std::string name,
		std::pair<int, int> position,
		int priority)
		: engine::GameObject(name, position, priority,
							 {{engine::KeyboardEvent::LEFT,  "MOVE_LEFT"},
							  {engine::KeyboardEvent::RIGHT, "MOVE_RIGHT"}}
) {};

/**
 * @brief Event processor method
 *
 * Process Game Events received.
 *
 * @param game_event The game event to be received.
 *
 * @return void
 */
void Platform::on_event(GameEvent game_event) {
	platform_movement(game_event);

	/*
	 * First Level Limiter.
     * All limiter are in pixels.
	 */
	first_level_clown(game_event);

	/*
	 * Second Level Limiter
	 * All limiters are in pixels
	 */
	second_level_boss(game_event);
}

/**
 * @brief Movements platform.
 *
 * Movements platform based on the girl's movement
 *
 * @param game_event The game event to be received.
 *
 * @return void.
 */
void Platform::platform_movement(GameEvent game_event){
	assert(!game_event.game_event_name.empty());

	std::string event_name = game_event.game_event_name; /**< string. Name of the game_event */
	const int movement_platform = 10; /**< int. Movement of the platform (value in pixels) */

	if (event_name == "MOVE_LEFT" && !engine::GameObject::on_limit_of_level) {
		/* set the right position of the platform based in the game_event */

		set_position_x(get_position_x() + movement_platform);
	}
	else if (event_name == "MOVE_RIGHT" && !engine::GameObject::on_limit_of_level) {
		/* set the left position of the platform based in the game_event */

		set_position_x(get_position_x() - movement_platform);
	}
	else {
		/* Do nothing */
	}
}

/**
 * @brief Level limiter.
 *
 * This method limits the level in right and left position in pixels.
 *
 * @param game_event The game event to be received.
 *
 * @return void.
 */
void Platform::first_level_clown(GameEvent game_event){
	if (name == "clown_tree") {
		const int first_level_inicial_limiter = -1300; /**< Int. Left limit in pixel of the girl can walk */
		const int first_level_final_limiter = 13350; /**< Int. Right limit in pixel of the girl can walk */

		if (get_position_x() > first_level_final_limiter) {
			/* Sets the limit of the map in axis x and don't let the girl pass this limit */

			engine::GameObject::on_limit_of_level = true;

			set_position_x(first_level_final_limiter);
		}
		else if (get_position_x() < first_level_inicial_limiter) {
			/* Sets the limit of the map in axis x and don't let the girl pass this limit */

			engine::GameObject::on_limit_of_level = true;

			set_position_x(first_level_inicial_limiter);
		}
		else {
			/* The girl is in between the limits */

			engine::GameObject::on_limit_of_level = false;
		}
	}
	else {
		/* Do nothing */
	}
}

/**
 * @brief Level limiter.
 *
 * This method limits the level in right and left position in pixels.
 *
 * @param game_event The game event to be received.
 *
 * @return void.
 */
void Platform::second_level_boss(GameEvent game_event){
	if (name == "limiter") {
		const int second_level_inicial_limiter = 0; /**< Int. Left limit in pixel of the girl can walk */
		const int second_level_final_limiter = 3000; /**< Int. Right limit in pixel of the girl can walk */

		if (get_position_x() > second_level_final_limiter) {
			/* Sets the limit of the map in axis x and don't let the girl pass this limit */

			engine::GameObject::on_limit_of_level = true;

			set_position_x(second_level_final_limiter);
		}
		else if (get_position_x() < second_level_inicial_limiter) {
			/* Sets the limit of the map in axis x and don't let the girl pass this limit */

			engine::GameObject::on_limit_of_level = true;

			set_position_x(second_level_inicial_limiter);
		}
		else {
			/* The girl is in between the limits */

			engine::GameObject::on_limit_of_level = false;
		}
	}
	else {
		/* Do nothing */
	}
}
<|endoftext|>


<commit_before>#include "mainwindow.h"

#include <QActionGroup>
#include <QFileDialog>
#include <QKeyEvent>
#include <QString>
#include "ui_mainwindow.h"
#include "screenwidget.h"
#include "emuthread.h"
#include "gameboy/core.h"
#include "gameboy/keyboard.h"

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow),
    videoScalingGroup(new QActionGroup(this)) {
    ui->setupUi(this);

    videoScalingGroup->addAction(ui->action1x);
    videoScalingGroup->addAction(ui->action2x);
    videoScalingGroup->addAction(ui->action4x);
    videoScalingGroup->addAction(ui->action6x);

    gameboyCore = new gameboy::Core;

    keyboard = gameboyCore->getKeyboard();

    screenWidget = new ScreenWidget(this);
    screenWidget->setFramebuffer(gameboyCore->getFramebuffer());
    setCentralWidget(screenWidget);

    setScaling(4);

    emuThread = new EmuThread(gameboyCore, screenWidget);
    screenWidget->doneCurrent();
    screenWidget->context()->moveToThread(emuThread);
}

MainWindow::~MainWindow() {
    pauseEmulation();
    delete emuThread;
    delete gameboyCore;

    delete ui;
}

void MainWindow::continueEmulation() {
    if (!emuThread->isRunning()) {
        emuThread->stopped = false;
        emuThread->start();
    }
}

void MainWindow::pauseEmulation() {
    if (emuThread->isRunning()) {
        emuThread->stopped = true;
        emuThread->wait();
    }
}

void MainWindow::loadROM() {
    QString fileName = QFileDialog::getOpenFileName(this, "Open ROM", "", "Gameboy ROMs (*.gb)");
    if (!fileName.isNull()) {
        pauseEmulation();

        gameboyCore->reset();
        gameboyCore->loadROM(fileName.toStdString());
        continueEmulation();
    }
}

void MainWindow::setScaling(int scaling) {
    screenWidget->resize(160*scaling, 144*scaling);
    resize(160*scaling, 144*scaling + ui->menubar->height());
}

void MainWindow::scale1x() {
    setScaling(1);
}

void MainWindow::scale2x() {
    setScaling(2);
}

void MainWindow::scale4x() {
    setScaling(4);
}

void MainWindow::scale6x() {
    setScaling(6);
}

void MainWindow::keyPressEvent(QKeyEvent *event) {
    switch (event->key()) {
    case Qt::Key_Up:
        keyboard->up = true;
    break;
    case Qt::Key_Down:
        keyboard->down = true;
    break;
    case Qt::Key_Left:
        keyboard->left = true;
    break;
    case Qt::Key_Right:
        keyboard->right = true;
    break;
    case Qt::Key_C:
        keyboard->select = true;
    break;
    case Qt::Key_V:
        keyboard->start = true;
    break;
    case Qt::Key_F:
        keyboard->a = true;
    break;
    case Qt::Key_D:
        keyboard->b = true;
    break;
    default: //To make the compiler STFU
    break;
   }
}

void MainWindow::keyReleaseEvent(QKeyEvent *event) {
    switch (event->key()) {
        case Qt::Key_Up:
            keyboard->up = false;
        break;
        case Qt::Key_Down:
            keyboard->down = false;
        break;
        case Qt::Key_Left:
            keyboard->left = false;
        break;
        case Qt::Key_Right:
            keyboard->right = false;
        break;
        case Qt::Key_C:
            keyboard->select = false;
        break;
        case Qt::Key_V:
            keyboard->start = false;
        break;
        case Qt::Key_F:
            keyboard->a = false;
        break;
        case Qt::Key_D:
            keyboard->b = false;
        break;
        default: //To make the compiler STFU
        break;
    }
}

<commit_msg>Command line argument parsing<commit_after>#include "mainwindow.h"

#include <QActionGroup>
#include <QFileDialog>
#include <QKeyEvent>
#include <QString>
#include <QStringList>
#include "ui_mainwindow.h"
#include "screenwidget.h"
#include "emuthread.h"
#include "gameboy/core.h"
#include "gameboy/keyboard.h"

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow),
    videoScalingGroup(new QActionGroup(this)) {
    ui->setupUi(this);

    videoScalingGroup->addAction(ui->action1x);
    videoScalingGroup->addAction(ui->action2x);
    videoScalingGroup->addAction(ui->action4x);
    videoScalingGroup->addAction(ui->action6x);

    gameboyCore = new gameboy::Core;

    keyboard = gameboyCore->getKeyboard();

    screenWidget = new ScreenWidget(this);
    screenWidget->setFramebuffer(gameboyCore->getFramebuffer());
    setCentralWidget(screenWidget);

    setScaling(4);

    emuThread = new EmuThread(gameboyCore, screenWidget);
    screenWidget->doneCurrent();
    screenWidget->context()->moveToThread(emuThread);

    QStringList args = QCoreApplication::arguments();
    if (args.size() > 1) {
        gameboyCore->loadROM(args.at(1).toStdString());
        continueEmulation();
    }
}

MainWindow::~MainWindow() {
    pauseEmulation();
    delete emuThread;
    delete gameboyCore;

    delete ui;
}

void MainWindow::continueEmulation() {
    if (!emuThread->isRunning()) {
        emuThread->stopped = false;
        emuThread->start();
    }
}

void MainWindow::pauseEmulation() {
    if (emuThread->isRunning()) {
        emuThread->stopped = true;
        emuThread->wait();
    }
}

void MainWindow::loadROM() {
    QString fileName = QFileDialog::getOpenFileName(this, "Open ROM", "", "Gameboy ROMs (*.gb)");
    if (!fileName.isNull()) {
        pauseEmulation();

        gameboyCore->reset();
        gameboyCore->loadROM(fileName.toStdString());
        continueEmulation();
    }
}

void MainWindow::setScaling(int scaling) {
    screenWidget->resize(160*scaling, 144*scaling);
    resize(160*scaling, 144*scaling + ui->menubar->height());
}

void MainWindow::scale1x() {
    setScaling(1);
}

void MainWindow::scale2x() {
    setScaling(2);
}

void MainWindow::scale4x() {
    setScaling(4);
}

void MainWindow::scale6x() {
    setScaling(6);
}

void MainWindow::keyPressEvent(QKeyEvent *event) {
    switch (event->key()) {
    case Qt::Key_Up:
        keyboard->up = true;
    break;
    case Qt::Key_Down:
        keyboard->down = true;
    break;
    case Qt::Key_Left:
        keyboard->left = true;
    break;
    case Qt::Key_Right:
        keyboard->right = true;
    break;
    case Qt::Key_C:
        keyboard->select = true;
    break;
    case Qt::Key_V:
        keyboard->start = true;
    break;
    case Qt::Key_F:
        keyboard->a = true;
    break;
    case Qt::Key_D:
        keyboard->b = true;
    break;
    default: //To make the compiler STFU
    break;
   }
}

void MainWindow::keyReleaseEvent(QKeyEvent *event) {
    switch (event->key()) {
        case Qt::Key_Up:
            keyboard->up = false;
        break;
        case Qt::Key_Down:
            keyboard->down = false;
        break;
        case Qt::Key_Left:
            keyboard->left = false;
        break;
        case Qt::Key_Right:
            keyboard->right = false;
        break;
        case Qt::Key_C:
            keyboard->select = false;
        break;
        case Qt::Key_V:
            keyboard->start = false;
        break;
        case Qt::Key_F:
            keyboard->a = false;
        break;
        case Qt::Key_D:
            keyboard->b = false;
        break;
        default: //To make the compiler STFU
        break;
    }
}

<|endoftext|>


<commit_before>#include "NFComm/NFPluginModule/NFPlatform.h"

#if NF_PLATFORM == NF_PLATFORM_WIN
#endif

#pragma comment( lib, "Dbghelp.lib" )

#ifdef NF_DEBUG_MODE

#if NF_PLATFORM == NF_PLATFORM_WIN

#ifdef NF_DYNAMIC_PLUGIN
#pragma comment( lib, "NFCore_d.lib" )
#pragma comment( lib, "Theron_d.lib" )

#else
#pragma comment( lib, "NFCore_d.lib" )
#pragma comment( lib, "Theron_d.lib" )
#endif

//#pragma comment( lib, "Theron_d.lib" )
#pragma comment( lib, "libglog_static_d.lib" )
#elif NF_PLATFORM == NF_PLATFORM_LINUX || NF_PLATFORM == NF_PLATFORM_ANDROID
#pragma comment( lib, "NFCore_d.a" )
#pragma comment( lib, "libglog_d.a" )
#pragma comment( lib, "libtherond.a")
#elif NF_PLATFORM == NF_PLATFORM_APPLE || NF_PLATFORM == NF_PLATFORM_APPLE_IOS
#endif

#else

#if NF_PLATFORM == NF_PLATFORM_WIN
#ifdef NF_DYNAMIC_PLUGIN
#pragma comment( lib, "NFCore.lib" )
#pragma comment( lib, "Theron.lib" )
#else
#pragma comment( lib, "NFCorec.lib" )
#pragma comment( lib, "Theron.lib" )
#endif

//#pragma comment( lib, "Theron.lib" )
#pragma comment( lib, "libglog_static.lib" )
#elif NF_PLATFORM == NF_PLATFORM_LINUX || NF_PLATFORM == NF_PLATFORM_ANDROID
#pragma comment( lib, "NFCore.a" )
#pragma comment( lib, "libglog.a" )
#pragma comment( lib, "libtherond.a")
#elif NF_PLATFORM == NF_PLATFORM_APPLE || NF_PLATFORM == NF_PLATFORM_APPLE_IOS
#endif

#endif
<commit_msg>remove glog lib linking<commit_after>#include "NFComm/NFPluginModule/NFPlatform.h"

#if NF_PLATFORM == NF_PLATFORM_WIN
#endif

#pragma comment( lib, "Dbghelp.lib" )

#ifdef NF_DEBUG_MODE

#if NF_PLATFORM == NF_PLATFORM_WIN

#ifdef NF_DYNAMIC_PLUGIN
#pragma comment( lib, "NFCore_d.lib" )
#pragma comment( lib, "Theron_d.lib" )

#else
#pragma comment( lib, "NFCore_d.lib" )
#pragma comment( lib, "Theron_d.lib" )
#endif

//#pragma comment( lib, "Theron_d.lib" )
#elif NF_PLATFORM == NF_PLATFORM_LINUX || NF_PLATFORM == NF_PLATFORM_ANDROID
#pragma comment( lib, "NFCore_d.a" )
#pragma comment( lib, "libtherond.a")
#elif NF_PLATFORM == NF_PLATFORM_APPLE || NF_PLATFORM == NF_PLATFORM_APPLE_IOS
#endif

#else

#if NF_PLATFORM == NF_PLATFORM_WIN
#ifdef NF_DYNAMIC_PLUGIN
#pragma comment( lib, "NFCore.lib" )
#pragma comment( lib, "Theron.lib" )
#else
#pragma comment( lib, "NFCorec.lib" )
#pragma comment( lib, "Theron.lib" )
#endif

//#pragma comment( lib, "Theron.lib" )
#elif NF_PLATFORM == NF_PLATFORM_LINUX || NF_PLATFORM == NF_PLATFORM_ANDROID
#pragma comment( lib, "NFCore.a" )
#pragma comment( lib, "libtherond.a")
#elif NF_PLATFORM == NF_PLATFORM_APPLE || NF_PLATFORM == NF_PLATFORM_APPLE_IOS
#endif

#endif
<|endoftext|>


<commit_before>#pragma once
#include "includes.hpp"

#define TAGLIB_STATIC
#include <taglib/fileref.h>
#include <taglib/tag.h>
#include <taglib/tpropertymap.h>

class playlist : public Component, public FileDragAndDropTarget {
    struct playlistModel : public ListBoxModel {
		StringArray entries;
        int getNumRows() override {
            return entries.size();
        }

        void paintListBoxItem(int rowNumber, Graphics& g,
							  int width, int height, bool rowIsSelected) override {
            if (rowIsSelected)
                g.fillAll(Colours::lightblue);

            g.setColour(Colours::black);
            g.setFont(height * 0.7f);
			g.drawText(entries[rowNumber], 5, 0, width, height, Justification::centredLeft, true);
        }
    };

    ListBox box;
    playlistModel model;
    JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(playlist);

public:
    playlist() : box("playlist-box", nullptr) {
		setName("playlist");
		box.setModel(&model);
		box.setMultipleSelectionEnabled(true);
		addAndMakeVisible(box);
	}

    void resized() override {
		box.setBounds(getLocalBounds().reduced(0));
	}

	bool isInterestedInFileDrag(const StringArray& /*files*/) override {
		return true;
	}

	void fileDragEnter(const StringArray& /*files*/, int /*x*/, int /*y*/) override {
		repaint();
	}

	void fileDragMove (const StringArray& /*files*/, int /*x*/, int /*y*/) override {}

	void fileDragExit (const StringArray& /*files*/) override {
		repaint();
	}

	void filesDropped (const StringArray& files, int /*x*/, int /*y*/) override {
		for (auto &f : files) {
			//TagLib::FileRef file(f.toRawUTF8());
			//f = (file.tag()->album() + L" | " + file.tag()->artist() + L" | " + file.tag()->title()).toCString();
		}
		model.entries.addArray(files);
		box.updateContent();
		repaint();
	}

	base::string getSelectedRowString() {
		return model.entries[box.getSelectedRow()].toStdString();
	}
};
<commit_msg>+ encoding<commit_after>#pragma once
#include "includes.hpp"

#define TAGLIB_STATIC
#include <taglib/fileref.h>
#include <taglib/tag.h>
#include <taglib/tpropertymap.h>

class playlist : public Component, public FileDragAndDropTarget {
    struct playlistModel : public ListBoxModel {
		StringArray entries;
        int getNumRows() override {
            return entries.size();
        }

        void paintListBoxItem(int rowNumber, Graphics& g,
							  int width, int height, bool rowIsSelected) override {
            if (rowIsSelected)
                g.fillAll(Colours::lightblue);

            g.setColour(Colours::black);
            g.setFont(height * 0.7f);
			g.drawText(entries[rowNumber], 5, 0, width, height, Justification::centredLeft, true);
        }
    };

    ListBox box;
    playlistModel model;
    JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(playlist);

	// TODO: system codecs?
	bool isFileSupported(const String &fname) {
		return fname.endsWith(".mp3")
			|| fname.endsWith(".wav")
			|| fname.endsWith(".wma")
			|| fname.endsWith(".flac")
			|| fname.endsWith(".ogg")
			|| fname.endsWith(".ape");
	}

public:
    playlist() : box("playlist-box", nullptr) {
		setName("playlist");
		box.setModel(&model);
		box.setMultipleSelectionEnabled(true);
		addAndMakeVisible(box);
	}

    void resized() override {
		box.setBounds(getLocalBounds().reduced(0));
	}

	bool isInterestedInFileDrag(const StringArray& /*files*/) override {
		return true;
	}

	void fileDragEnter(const StringArray& /*files*/, int /*x*/, int /*y*/) override {
		repaint();
	}

	void fileDragMove (const StringArray& /*files*/, int /*x*/, int /*y*/) override {}

	void fileDragExit (const StringArray& /*files*/) override {
		repaint();
	}

	void filesDropped (const StringArray& files, int /*x*/, int /*y*/) override {
		for (auto &f : files) {
			if (isFileSupported(f)) {
				//TagLib::FileRef file(f.toRawUTF8());
				//f = (file.tag()->album() + L" | " + file.tag()->artist() + L" | " + file.tag()->title()).toCString();
			}
		}
		model.entries.addArray(files);
		box.updateContent();
		repaint();
	}

	base::string getSelectedRowString() {
		return model.entries[box.getSelectedRow()].toStdString();
	}
};
<|endoftext|>


<commit_before>#include "util/assert.h"
#ifdef DEBUG
#include <stdio.h>

void  __AssertFail(const char* file, unsigned line)
#ifndef _MSC_VER
  throw (__Assert)
#endif
{
  static bool yes_all = false;
  if (yes_all)
    return;

  const char* msg =
"\n\
**************************************\n\
Assertion failure:\n\
\tfile %s line %d\n\
Continue (y/a/n) ?\n";
  fprintf(stderr, msg, file, line);

  for (;;) {
    switch (getchar()) {
      case 'a': yes_all = true;
      case 'y': return;
      case EOF:
      case 'n': throw __Assert(file, line);
    }
  }
}

#endif //defined(DEBUG)
<commit_msg>don't need this anymore<commit_after><|endoftext|>


<commit_before>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: cuisrchdlg.cxx,v $
 *
 *  $Revision: 1.9 $
 *
 *  last change: $Author: kz $ $Date: 2007-05-10 14:36:33 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License version 2.1, as published by the Free Software Foundation.
 *
 *    This library 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
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/

// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_svx.hxx"

#ifdef SVX_DLLIMPLEMENTATION
#undef SVX_DLLIMPLEMENTATION
#endif

// include ---------------------------------------------------------------

#ifndef _SV_WRKWIN_HXX
#include <vcl/wrkwin.hxx>
#endif
#ifndef _SV_MOREBTN_HXX //autogen wg. MoreButton
#include <vcl/morebtn.hxx>
#endif
#ifndef _SV_MSGBOX_HXX //autogen wg. RET_OK
#include <vcl/msgbox.hxx>
#endif
#ifndef _SFXSLSTITM_HXX
#include <svtools/slstitm.hxx>
#endif
#ifndef _SFXITEMITER_HXX
#include <svtools/itemiter.hxx>
#endif
#ifndef _SFXSTYLE_HXX
#include <svtools/style.hxx>
#endif
#ifndef _SVT_SEARCHOPT_HXX_
#include <svtools/searchopt.hxx>
#endif
#ifndef _SFXDISPATCH_HXX
#include <sfx2/dispatch.hxx>
#endif
#ifndef _SFX_OBJSH_HXX //autogen
#include <sfx2/objsh.hxx>
#endif
#ifndef _SFXMODULE_HXX
#include <sfx2/module.hxx>
#endif
#ifndef _SFXVIEWSH_HXX //autogen
#include <sfx2/viewsh.hxx>
#endif
#ifndef _BASEDLGS_HXX
#include <sfx2/basedlgs.hxx>
#endif
#ifndef _SVTOOLS_CJKOPTIONS_HXX
#include <svtools/cjkoptions.hxx>
#endif

#ifndef _COM_SUN_STAR_I18N_TRANSLITERATIONMODULES_HPP_
#include <com/sun/star/i18n/TransliterationModules.hpp>
#endif

#define _CUI_SRCHDLG_CXX
#include "cuisrchdlg.hxx"

#include "dialogs.hrc"
#include "svxitems.hrc"
#include "srchdlg.hrc"

#define ITEMID_SETITEM      0

#include <sfx2/srchitem.hxx>
#include "pageitem.hxx"
#include "srchctrl.hxx"
//CHINA001 #include "srchxtra.hxx"
#include "dialmgr.hxx"
#include "dlgutil.hxx"

#ifndef _SVX_OPTJSEARCH_HXX_
#include <optjsearch.hxx>
#endif

#ifndef _SVX_BRSHITEM_HXX //autogen
#include <brshitem.hxx>
#endif
#ifndef _SVX_BACKGRND_HXX //autogen
#include "backgrnd.hxx"
#endif

// class SvxJSearchOptionsDialog -----------------------------------------

SvxJSearchOptionsDialog::SvxJSearchOptionsDialog(
            Window *pParent,
            const SfxItemSet& rOptionsSet, USHORT /*nUniqueId*/, INT32 nInitialFlags ) :
    SfxSingleTabDialog  ( pParent, rOptionsSet, RID_SVXPAGE_JSEARCH_OPTIONS ),
    nInitialTlFlags( nInitialFlags )
{
    pPage = (SvxJSearchOptionsPage *)
                    SvxJSearchOptionsPage::Create( this, rOptionsSet );
    SetTabPage( pPage );    //! implicitly calls pPage->Reset(...)!
    pPage->EnableSaveOptions( FALSE );
}

SvxJSearchOptionsDialog::~SvxJSearchOptionsDialog()
{
    // pPage will be implicitly destroyed by the
    // SfxSingleTabDialog destructor
}

void SvxJSearchOptionsDialog::Activate()
{
    pPage->SetTransliterationFlags( nInitialTlFlags );
}

INT32 SvxJSearchOptionsDialog::GetTransliterationFlags() const
{
    return pPage->GetTransliterationFlags();
}

void SvxJSearchOptionsDialog::SetTransliterationFlags( INT32 nSettings )
{
    pPage->SetTransliterationFlags( nSettings );
}
<commit_msg>INTEGRATION: CWS vgbugs07 (1.9.32); FILE MERGED 2007/06/04 13:26:15 vg 1.9.32.1: #i76605# Remove -I .../inc/module hack introduced by hedaburemove01<commit_after>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: cuisrchdlg.cxx,v $
 *
 *  $Revision: 1.10 $
 *
 *  last change: $Author: hr $ $Date: 2007-06-27 16:58:43 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License version 2.1, as published by the Free Software Foundation.
 *
 *    This library 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
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/

// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_svx.hxx"

#ifdef SVX_DLLIMPLEMENTATION
#undef SVX_DLLIMPLEMENTATION
#endif

// include ---------------------------------------------------------------

#ifndef _SV_WRKWIN_HXX
#include <vcl/wrkwin.hxx>
#endif
#ifndef _SV_MOREBTN_HXX //autogen wg. MoreButton
#include <vcl/morebtn.hxx>
#endif
#ifndef _SV_MSGBOX_HXX //autogen wg. RET_OK
#include <vcl/msgbox.hxx>
#endif
#ifndef _SFXSLSTITM_HXX
#include <svtools/slstitm.hxx>
#endif
#ifndef _SFXITEMITER_HXX
#include <svtools/itemiter.hxx>
#endif
#ifndef _SFXSTYLE_HXX
#include <svtools/style.hxx>
#endif
#ifndef _SVT_SEARCHOPT_HXX_
#include <svtools/searchopt.hxx>
#endif
#ifndef _SFXDISPATCH_HXX
#include <sfx2/dispatch.hxx>
#endif
#ifndef _SFX_OBJSH_HXX //autogen
#include <sfx2/objsh.hxx>
#endif
#ifndef _SFXMODULE_HXX
#include <sfx2/module.hxx>
#endif
#ifndef _SFXVIEWSH_HXX //autogen
#include <sfx2/viewsh.hxx>
#endif
#ifndef _BASEDLGS_HXX
#include <sfx2/basedlgs.hxx>
#endif
#ifndef _SVTOOLS_CJKOPTIONS_HXX
#include <svtools/cjkoptions.hxx>
#endif

#ifndef _COM_SUN_STAR_I18N_TRANSLITERATIONMODULES_HPP_
#include <com/sun/star/i18n/TransliterationModules.hpp>
#endif

#define _CUI_SRCHDLG_CXX
#include "cuisrchdlg.hxx"

#include <svx/dialogs.hrc>
#include <svx/svxitems.hrc>
#include "srchdlg.hrc"

#define ITEMID_SETITEM      0

#include <sfx2/srchitem.hxx>
#include <svx/pageitem.hxx>
#include "srchctrl.hxx"
//CHINA001 #include "srchxtra.hxx"
#include <svx/dialmgr.hxx>
#include "dlgutil.hxx"

#ifndef _SVX_OPTJSEARCH_HXX_
#include <optjsearch.hxx>
#endif

#ifndef _SVX_BRSHITEM_HXX //autogen
#include <svx/brshitem.hxx>
#endif
#ifndef _SVX_BACKGRND_HXX //autogen
#include "backgrnd.hxx"
#endif

// class SvxJSearchOptionsDialog -----------------------------------------

SvxJSearchOptionsDialog::SvxJSearchOptionsDialog(
            Window *pParent,
            const SfxItemSet& rOptionsSet, USHORT /*nUniqueId*/, INT32 nInitialFlags ) :
    SfxSingleTabDialog  ( pParent, rOptionsSet, RID_SVXPAGE_JSEARCH_OPTIONS ),
    nInitialTlFlags( nInitialFlags )
{
    pPage = (SvxJSearchOptionsPage *)
                    SvxJSearchOptionsPage::Create( this, rOptionsSet );
    SetTabPage( pPage );    //! implicitly calls pPage->Reset(...)!
    pPage->EnableSaveOptions( FALSE );
}

SvxJSearchOptionsDialog::~SvxJSearchOptionsDialog()
{
    // pPage will be implicitly destroyed by the
    // SfxSingleTabDialog destructor
}

void SvxJSearchOptionsDialog::Activate()
{
    pPage->SetTransliterationFlags( nInitialTlFlags );
}

INT32 SvxJSearchOptionsDialog::GetTransliterationFlags() const
{
    return pPage->GetTransliterationFlags();
}

void SvxJSearchOptionsDialog::SetTransliterationFlags( INT32 nSettings )
{
    pPage->SetTransliterationFlags( nSettings );
}
<|endoftext|>


<commit_before>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: msashape.hxx,v $
 *
 *  $Revision: 1.12 $
 *
 *  last change: $Author: hr $ $Date: 2007-06-27 18:34:13 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License version 2.1, as published by the Free Software Foundation.
 *
 *    This library 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
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/

#ifndef _MSASHAPE_HXX
#define _MSASHAPE_HXX

#ifndef _MSDFFDEF_HXX
#include <svx/msdffdef.hxx>
#endif
#ifndef _MSDFFIMP_HXX
#include <svx/msdffimp.hxx>
#endif

#define DFF_CUSTOMSHAPE_FLIP_V      1
#define DFF_CUSTOMSHAPE_FLIP_H      2
#define DFF_CUSTOMSHAPE_EXCH            4

class SdrModel;
class SfxItemSet;
struct SvxMSDffVertPair;
struct SvxMSDffCalculationData;
struct SvxMSDffTextRectangles;
class SvxMSDffAdjustmentHandle;
class SvxMSDffCustomShape
{
        MSFilterTracer*             pTracer;
        MSO_SPT                     eSpType;

        sal_Int32                   nCoordWidth;
        sal_Int32                   nCoordHeight;
        Rectangle                   aSnapRect;

        double                      fXScale;
        double                      fYScale;

        sal_Int32                   nFix16Angle;
        sal_Int32                   nXRef;
        sal_Int32                   nYRef;
        sal_uInt32                  nFlags;

        sal_uInt32                  nNumElemVert;
        sal_uInt32                  nNumElemSeg;

        sal_uInt32                  nColorData;

        SvxMSDffVertPair*           pVertData;
        sal_uInt16*                 pSegData;

        sal_uInt32                  nTextRectData;
        SvxMSDffTextRectangles*     pTextRectData;
        sal_uInt32                  nCalculationData;
        SvxMSDffCalculationData*    pCalculationData;
        sal_uInt32                  nAdjustmentHandles;
        SvxMSDffAdjustmentHandle*   pAdjustmentHandles;
        sal_uInt32                  nGluePoints;
        SvxMSDffVertPair*           pGluePoints;

        sal_Bool                    bIsEmpty        : 1;
        sal_Bool                    bVertAlloc      : 1;
        sal_Bool                    bSegAlloc       : 1;
        sal_Bool                    bCalcAlloc      : 1;
        sal_Bool                    bTextRectAlloc  : 1;

        sal_Bool                    bTextFlow       : 1;
        sal_Bool                    bFilled         : 1;
        sal_Bool                    bFlipH          : 1;
        sal_Bool                    bFlipV          : 1;

        sal_Int32                   GetAdjustValue( sal_uInt32 nIndex ) const;
        sal_Int32                   GetAdjustValue( sal_uInt32 nIndex, sal_Int32 nDefault ) const;
        sal_Int32                   Fix16ToAngle( sal_Int32 nAngle ) const;
        Color                       ImplGetColorData( const Color& rFillColor, sal_uInt32 nIndex );
        double                      ImplGetValue( sal_uInt16 nIndex, sal_uInt32& nGeometryFlags ) const;
        Point                       GetPoint( const SvxMSDffVertPair&, sal_Bool bScale = sal_True ) const;

        static void                 SwapStartAndEndArrow( SdrObject* pObj );

    public :

        SdrObject*                  GetObject( SdrModel* pSdrModel, SfxItemSet& rSet, sal_Bool bSetAdjustmentItem );
        sal_Bool                    IsEmpty() const;

        Rectangle                   GetTextRect() const;
        static sal_Bool             HasGluePointList( const MSO_SPT eShapeType );
        static MSO_SPT              GetShapeTypeFromSdrObject( const SdrObject* );

        SvxMSDffCustomShape( const DffPropertyReader& rPropReader, SvStream&,
                            DffObjData& rObjDat, Rectangle& rSnapRect, sal_Int32 nFix16Angle, MSFilterTracer* pTracer );
        ~SvxMSDffCustomShape();
};

#endif

<commit_msg>INTEGRATION: CWS changefileheader (1.12.368); FILE MERGED 2008/04/01 12:49:21 thb 1.12.368.2: #i85898# Stripping all external header guards 2008/03/31 14:22:51 rt 1.12.368.1: #i87441# Change license header to LPGL v3.<commit_after>/*************************************************************************
 *
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * Copyright 2008 by Sun Microsystems, Inc.
 *
 * OpenOffice.org - a multi-platform office productivity suite
 *
 * $RCSfile: msashape.hxx,v $
 * $Revision: 1.13 $
 *
 * This file is part of OpenOffice.org.
 *
 * OpenOffice.org is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License version 3
 * only, as published by the Free Software Foundation.
 *
 * OpenOffice.org 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 Lesser General Public License version 3 for more details
 * (a copy is included in the LICENSE file that accompanied this code).
 *
 * You should have received a copy of the GNU Lesser General Public License
 * version 3 along with OpenOffice.org.  If not, see
 * <http://www.openoffice.org/license.html>
 * for a copy of the LGPLv3 License.
 *
 ************************************************************************/

#ifndef _MSASHAPE_HXX
#define _MSASHAPE_HXX

#include <svx/msdffdef.hxx>
#include <svx/msdffimp.hxx>

#define DFF_CUSTOMSHAPE_FLIP_V      1
#define DFF_CUSTOMSHAPE_FLIP_H      2
#define DFF_CUSTOMSHAPE_EXCH            4

class SdrModel;
class SfxItemSet;
struct SvxMSDffVertPair;
struct SvxMSDffCalculationData;
struct SvxMSDffTextRectangles;
class SvxMSDffAdjustmentHandle;
class SvxMSDffCustomShape
{
        MSFilterTracer*             pTracer;
        MSO_SPT                     eSpType;

        sal_Int32                   nCoordWidth;
        sal_Int32                   nCoordHeight;
        Rectangle                   aSnapRect;

        double                      fXScale;
        double                      fYScale;

        sal_Int32                   nFix16Angle;
        sal_Int32                   nXRef;
        sal_Int32                   nYRef;
        sal_uInt32                  nFlags;

        sal_uInt32                  nNumElemVert;
        sal_uInt32                  nNumElemSeg;

        sal_uInt32                  nColorData;

        SvxMSDffVertPair*           pVertData;
        sal_uInt16*                 pSegData;

        sal_uInt32                  nTextRectData;
        SvxMSDffTextRectangles*     pTextRectData;
        sal_uInt32                  nCalculationData;
        SvxMSDffCalculationData*    pCalculationData;
        sal_uInt32                  nAdjustmentHandles;
        SvxMSDffAdjustmentHandle*   pAdjustmentHandles;
        sal_uInt32                  nGluePoints;
        SvxMSDffVertPair*           pGluePoints;

        sal_Bool                    bIsEmpty        : 1;
        sal_Bool                    bVertAlloc      : 1;
        sal_Bool                    bSegAlloc       : 1;
        sal_Bool                    bCalcAlloc      : 1;
        sal_Bool                    bTextRectAlloc  : 1;

        sal_Bool                    bTextFlow       : 1;
        sal_Bool                    bFilled         : 1;
        sal_Bool                    bFlipH          : 1;
        sal_Bool                    bFlipV          : 1;

        sal_Int32                   GetAdjustValue( sal_uInt32 nIndex ) const;
        sal_Int32                   GetAdjustValue( sal_uInt32 nIndex, sal_Int32 nDefault ) const;
        sal_Int32                   Fix16ToAngle( sal_Int32 nAngle ) const;
        Color                       ImplGetColorData( const Color& rFillColor, sal_uInt32 nIndex );
        double                      ImplGetValue( sal_uInt16 nIndex, sal_uInt32& nGeometryFlags ) const;
        Point                       GetPoint( const SvxMSDffVertPair&, sal_Bool bScale = sal_True ) const;

        static void                 SwapStartAndEndArrow( SdrObject* pObj );

    public :

        SdrObject*                  GetObject( SdrModel* pSdrModel, SfxItemSet& rSet, sal_Bool bSetAdjustmentItem );
        sal_Bool                    IsEmpty() const;

        Rectangle                   GetTextRect() const;
        static sal_Bool             HasGluePointList( const MSO_SPT eShapeType );
        static MSO_SPT              GetShapeTypeFromSdrObject( const SdrObject* );

        SvxMSDffCustomShape( const DffPropertyReader& rPropReader, SvStream&,
                            DffObjData& rObjDat, Rectangle& rSnapRect, sal_Int32 nFix16Angle, MSFilterTracer* pTracer );
        ~SvxMSDffCustomShape();
};

#endif

<|endoftext|>


<commit_before><commit_msg>fdo#70100 Detect single stream excel files with BOF ID 5<commit_after><|endoftext|>


<commit_before>#include <iostream>
#include <strstream>
#include <stdarg.h>

#include "KAI/KAI.h"
#include "KAI/Translator/Lexer.h"

using namespace std;

KAI_BEGIN

Lexer::Lexer(const char *in)
	: input(in)
{
	CreateLines();
	AddKeywords();
	Run();
}

void Lexer::AddKeywords()
{
	keyWords["if"] = Token::If;
	keyWords["else"] = Token::Else;
	keyWords["for"] = Token::For;
	keyWords["true"] = Token::True;
	keyWords["false"] = Token::False;
	keyWords["return"] = Token::Return;
	keyWords["self"] = Token::Self;
	keyWords["fun"] = Token::Fun;
	keyWords["yield"] = Token::Yield;
	keyWords["in"] = Token::In;
	keyWords["while"] = Token::While;
	keyWords["assert"] = Token::Assert;
}

bool Lexer::Run()
{
	offset = 0;
	lineNumber = 0;

	while (!Failed && NextToken())
		;

	return Add(Token::None, 0);
}

void Lexer::Print() const
{
	//std::copy(tokens.begin(), tokens.end(), ostream_iterator<Token>(std::cout, " "));
	for (auto tok : tokens)
		std::cout << tok << " ";

	std::cout << std::endl;
}

Slice Lexer::Gather(int (*filt)(int))
{
	int start = offset;
	while (filt(Next()))
		;

	return Slice(start, offset);
}

bool Lexer::Add(Token::Type type, Slice slice)
{
	tokens.push_back(Token(type, *this, lineNumber, slice));
	return true;
}

bool Lexer::Add(Token::Type type, int len)
{
	Add(type, Slice(offset, offset + len));
	while (len--)
		Next();

	return true;
}

bool Lexer::LexAlpha()
{
	Token tok(Token::Ident, *this, lineNumber, Gather(isalnum));

	auto kw = keyWords.find(tok.Text());
	if (kw != keyWords.end())
		tok.type = kw->second;

	tokens.push_back(tok);

	return true;
}

int IsSpaceChar(int ch)
{
	return ch == ' ';
}

bool Lexer::NextToken()
{
	auto current = Current();
	if (current == 0)
		return false;

	if (isalpha(current))
		return LexAlpha();

	if (isdigit(current))
		return Add(Token::Int, Gather(isdigit));

	switch (current)
	{
	case '\t': return Add(Token::Tab);
	case '\n': return Add(Token::NewLine);
	case ';': return Add(Token::Semi);
	case '{': return Add(Token::OpenBrace);
	case '}': return Add(Token::CloseBrace);
	case '(': return Add(Token::OpenParan);
	case ')': return Add(Token::CloseParan);
	case ':': return Add(Token::Colon);
	case ' ': return Add(Token::Whitespace, Gather(IsSpaceChar));
	case '@': return Add(Token::Lookup);
	case ',': return Add(Token::Comma);
	case '*': return Add(Token::Mul);
	case '[': return Add(Token::OpenSquareBracket);
	case ']': return Add(Token::CloseSquareBracket);
	case '=': return AddIfNext('=', Token::Equiv, Token::Assign);
	case '!': return AddIfNext('=', Token::NotEquiv, Token::Not);
	case '&': return AddIfNext('&', Token::And, Token::BitAnd);
	case '|': return AddIfNext('|', Token::Or, Token::BitOr);
	case '<': return AddIfNext('=', Token::LessEquiv, Token::Less);
	case '>': return AddIfNext('=', Token::GreaterEquiv, Token::Greater);
	case '"': return LexString();
	case '\'': return LexAlpha();
	case '-':
		if (Peek() == '-')
		{
			Next();
			return Add(Token::Decrement);
		}
		if (Peek() == '=')
		{
			Next();
			return Add(Token::MinusAssign);
		}
		return Add(Token::Minus);

	case '.':
		if (Peek() == '.')
		{
			Next();
			if (Peek() == '.')
			{
				Next();
				return Add(Token::Replace, 3);
			}
			return Fail("Two dots");
		}
		return Add(Token::Dot);

	case '+':
		if (Peek() == '+')
		{
			Next();
			return Add(Token::Increment);
		}
		if (Peek() == '=')
		{
			Next();
			return Add(Token::PlusAssign);
		}
		return Add(Token::Plus);

	case '/':
		if (Peek() == '/')
		{
			Next();
			int start = offset;
			while (Next() != '\n')
				;
			return Add(Token::Comment, offset - start);
		}
		return Add(Token::Divide);
	}

	LexError("Unrecognised %c");

	return false;
}

std::string Lexer::CreateError(Token tok, const char *fmt, ...)
{
	char buff0[2000];
	va_list ap;
	va_start(ap, fmt);
	vsprintf_s(buff0, fmt, ap);

	const char *fmt1 = "%s(%d):[%d]: %s\n";
	char buff[2000];
	sprintf_s(buff, fmt1, "", tok.lineNumber, tok.slice.Start, buff0);
	int beforeContext = 1;
	int afterContext = 0;

	const Lexer &lex = *tok.lexer;
	int start = std::max(0, tok.lineNumber - beforeContext);
	int end = std::min((int)lex.lines.size() - 1, tok.lineNumber + afterContext);

	strstream err;
	err << buff << endl;
	for (int n = start; n <= end; ++n)
	{
		for (auto ch : lex.lines[n])
		{
			if (ch == '\t')
				err << "    ";
			else
				err << ch;
		}

		if (n == tok.lineNumber)
		{
			for (int ch = 0; ch < (int)lex.lines[n].size(); ++ch)
			{
				if (lex.lines[tok.lineNumber][ch] == '\t')
					err << "    ";
				else if (ch == tok.slice.Start)
				{
					err << '^';
					break;
				}
			}

			err << endl;
		}
	}

	err << ends;

	return err.str();
}

bool Process::Fail(const std::string &err)
{
	Failed = true;
	Error = err;

	return false;
}

bool Process::Fail(const char *fmt, ...)
{
	va_list ap;
	va_start(ap, fmt);
	char buffer[1000];
	vsprintf_s(buffer, fmt, ap);
	return Fail(std::string(buffer));
}

char Lexer::Current() const
{
	if (lineNumber == (int)lines.size())
		return 0;

	return Line()[offset];
}

const std::string &Lexer::Line() const
{
	return lines[lineNumber];
}

char Lexer::Next()
{
	if (EndOfLine())
	{
		offset = 0;
		++lineNumber;
	}
	else
		++offset;

	if (lineNumber == (int)lines.size())
		return 0;

	return Line()[offset];
}

char Lexer::Peek() const
{
	if (EndOfLine())
		return 0;

	return Line()[offset + 1];
}

void Lexer::CreateLines()
{
	// ensure we end with a newline.
	input.push_back('\n');

	size_t lineStart = 0;
	for (size_t n = 0; n < input.size(); ++n)
	{
		if (input[n] == '\n')
		{
			lines.push_back(input.substr(lineStart, n - lineStart + 1));
			lineStart = n + 1;
		}
	}
}

bool Lexer::EndOfLine() const
{
	return offset == (int)Line().size() - 1;
}

bool Lexer::AddIfNext(char ch, Token::Type thenType, Token::Type elseType)
{
	if (Peek() == ch)
	{
		Next();
		return Add(thenType, 2);
	}

	return Add(elseType, 1);
}

bool Lexer::AddTwoCharOp(Token::Type ty)
{
	Add(ty, 2);
	Next();

	return true;
}

bool Lexer::LexString()
{
	int start = offset;
	Next();
	while (!Failed && Current() != '"')
	{
		if (Current() == '\\')
		{
			switch (Next())
			{
			case '"':
			case 'n':
			case 't':
				break;

			default:
				LexError("Bad escape sequence %c");
				return false;
			}
		}

		if (Peek() == 0)
		{
			Fail("Bad string literal");
			return false;
		}

		Next();
	}

	Next();

	// the +1 and -1 to remove the start and end double quote characters
	tokens.push_back(Token(Token::String, *this, lineNumber, Slice(start + 1, offset - 1)));
	return true;
}

void Lexer::LexError(const char *text)
{
	Fail(CreateError(Token(Token::None, *this, lineNumber, Slice(offset, offset)), text, Current()));
}

KAI_END

<commit_msg>.<commit_after>#include "KAI/KAI.h"

#include <iostream>
#include <strstream>
#include <stdarg.h>

#include "KAI/Translator/Lexer.h"

using namespace std;

KAI_BEGIN

Lexer::Lexer(const char *in)
	: input(in)
{
	CreateLines();
	AddKeywords();
	Run();
}

void Lexer::AddKeywords()
{
	keyWords["if"] = Token::If;
	keyWords["else"] = Token::Else;
	keyWords["for"] = Token::For;
	keyWords["true"] = Token::True;
	keyWords["false"] = Token::False;
	keyWords["return"] = Token::Return;
	keyWords["self"] = Token::Self;
	keyWords["fun"] = Token::Fun;
	keyWords["yield"] = Token::Yield;
	keyWords["in"] = Token::In;
	keyWords["while"] = Token::While;
	keyWords["assert"] = Token::Assert;
}

bool Lexer::Run()
{
	offset = 0;
	lineNumber = 0;

	while (!Failed && NextToken())
		;

	return Add(Token::None, 0);
}

void Lexer::Print() const
{
	//std::copy(tokens.begin(), tokens.end(), ostream_iterator<Token>(std::cout, " "));
	for (auto tok : tokens)
		std::cout << tok << " ";

	std::cout << std::endl;
}

Slice Lexer::Gather(int (*filt)(int))
{
	int start = offset;
	while (filt(Next()))
		;

	return Slice(start, offset);
}

bool Lexer::Add(Token::Type type, Slice slice)
{
	tokens.push_back(Token(type, *this, lineNumber, slice));
	return true;
}

bool Lexer::Add(Token::Type type, int len)
{
	Add(type, Slice(offset, offset + len));
	while (len--)
		Next();

	return true;
}

bool Lexer::LexAlpha()
{
	Token tok(Token::Ident, *this, lineNumber, Gather(isalnum));

	auto kw = keyWords.find(tok.Text());
	if (kw != keyWords.end())
		tok.type = kw->second;

	tokens.push_back(tok);

	return true;
}

int IsSpaceChar(int ch)
{
	return ch == ' ';
}

bool Lexer::NextToken()
{
	auto current = Current();
	if (current == 0)
		return false;

	if (isalpha(current))
		return LexAlpha();

	if (isdigit(current))
		return Add(Token::Int, Gather(isdigit));

	switch (current)
	{
	case '\t': return Add(Token::Tab);
	case '\n': return Add(Token::NewLine);
	case ';': return Add(Token::Semi);
	case '{': return Add(Token::OpenBrace);
	case '}': return Add(Token::CloseBrace);
	case '(': return Add(Token::OpenParan);
	case ')': return Add(Token::CloseParan);
	case ':': return Add(Token::Colon);
	case ' ': return Add(Token::Whitespace, Gather(IsSpaceChar));
	case '@': return Add(Token::Lookup);
	case ',': return Add(Token::Comma);
	case '*': return Add(Token::Mul);
	case '[': return Add(Token::OpenSquareBracket);
	case ']': return Add(Token::CloseSquareBracket);
	case '=': return AddIfNext('=', Token::Equiv, Token::Assign);
	case '!': return AddIfNext('=', Token::NotEquiv, Token::Not);
	case '&': return AddIfNext('&', Token::And, Token::BitAnd);
	case '|': return AddIfNext('|', Token::Or, Token::BitOr);
	case '<': return AddIfNext('=', Token::LessEquiv, Token::Less);
	case '>': return AddIfNext('=', Token::GreaterEquiv, Token::Greater);
	case '"': return LexString();
	case '\'': return LexAlpha();
	case '-':
		if (Peek() == '-')
			return AddTwoCharOp(Token::Decrement);
		if (Peek() == '=')
			return AddTwoCharOp(Token::MinusAssign);
		return Add(Token::Minus);

	case '.':
		if (Peek() == '.')
		{
			Next();
			if (Peek() == '.')
			{
				Next();
				return Add(Token::Replace, 3);
			}
			return Fail("Two dots doesn't work");
		}
		return Add(Token::Dot);

	case '+':
		if (Peek() == '+')
			return AddTwoCharOp(Token::Increment);
		if (Peek() == '=')
			return AddTwoCharOp(Token::PlusAssign);
		return Add(Token::Plus);

	case '/':
		if (Peek() == '/')
		{
			Next();
			int start = offset;
			while (Next() != '\n')
				;
			return Add(Token::Comment, offset - start);
		}
		return Add(Token::Divide);
	}

	LexError("Unrecognised %c");

	return false;
}

bool Process::Fail(const std::string &err)
{
	Failed = true;
	Error = err;

	return false;
}

bool Process::Fail(const char *fmt, ...)
{
	va_list ap;
	va_start(ap, fmt);
	char buffer[1000];
	vsprintf_s(buffer, fmt, ap);

	return Fail(std::string(buffer));
}

char Lexer::Current() const
{
	if (lineNumber == (int)lines.size())
		return 0;

	return Line()[offset];
}

const std::string &Lexer::Line() const
{
	return lines[lineNumber];
}

char Lexer::Next()
{
	if (EndOfLine())
	{
		offset = 0;
		++lineNumber;
	}
	else
		++offset;

	if (lineNumber == (int)lines.size())
		return 0;

	return Line()[offset];
}

char Lexer::Peek() const
{
	if (EndOfLine())
		return 0;

	return Line()[offset + 1];
}

void Lexer::CreateLines()
{
	// ensure we end with a newline.
	input.push_back('\n');

	size_t lineStart = 0;
	for (size_t n = 0; n < input.size(); ++n)
	{
		if (input[n] == '\n')
		{
			lines.push_back(input.substr(lineStart, n - lineStart + 1));
			lineStart = n + 1;
		}
	}
}

bool Lexer::EndOfLine() const
{
	return offset == (int)Line().size() - 1;
}

bool Lexer::AddIfNext(char ch, Token::Type thenType, Token::Type elseType)
{
	if (Peek() == ch)
	{
		Next();
		return Add(thenType, 2);
	}

	return Add(elseType, 1);
}

bool Lexer::AddTwoCharOp(Token::Type ty)
{
	Add(ty, 2);
	Next();

	return true;
}

bool Lexer::LexString()
{
	int start = offset;
	Next();
	while (!Failed && Current() != '"')
	{
		if (Current() == '\\')
		{
			switch (Next())
			{
			case '"':
			case 'n':
			case 't':
				break;

			default:
				LexError("Bad escape sequence %c");
				return false;
			}
		}

		if (Peek() == 0)
		{
			Fail("Bad string literal");
			return false;
		}

		Next();
	}

	Next();

	// the +1 and -1 to remove the start and end double quote characters
	tokens.push_back(Token(Token::String, *this, lineNumber, Slice(start + 1, offset - 1)));
	return true;
}

void Lexer::LexError(const char *text)
{
	Fail(CreateError(Token(Token::None, *this, lineNumber, Slice(offset, offset)), text, Current()));
}

std::string Lexer::CreateError(Token tok, const char *fmt, ...)
{
	char buff0[2000];
	va_list ap;
	va_start(ap, fmt);
	vsprintf_s(buff0, fmt, ap);

	const char *fmt1 = "%s(%d):[%d]: %s\n";
	char buff[2000];
	sprintf_s(buff, fmt1, "", tok.lineNumber, tok.slice.Start, buff0);
	int beforeContext = 1;
	int afterContext = 0;

	const Lexer &lex = *tok.lexer;
	int start = std::max(0, tok.lineNumber - beforeContext);
	int end = std::min((int)lex.lines.size() - 1, tok.lineNumber + afterContext);

	strstream err;
	err << buff << endl;
	for (int n = start; n <= end; ++n)
	{
		for (auto ch : lex.lines[n])
		{
			if (ch == '\t')
				err << "    ";
			else
				err << ch;
		}

		if (n == tok.lineNumber)
		{
			for (int ch = 0; ch < (int)lex.lines[n].size(); ++ch)
			{
				if (lex.lines[tok.lineNumber][ch] == '\t')
					err << "    ";
				else if (ch == tok.slice.Start)
				{
					err << '^';
					break;
				}
			}

			err << endl;
		}
	}

	err << ends;

	return err.str();
}

KAI_END

<|endoftext|>


<commit_before>#include "pakfile.h"

#include <stdexcept>
#include <iterator>
#include <algorithm>
#include <cstring>

namespace scpak
{
    void PakFile::load(std::istream &stream)
    {
        // read header
        PakHeader header;
        stream.read(reinterpret_cast<char*>(&header), sizeof(header));
        if (!header.checkMagic())
            throw std::runtime_error("bad pak file");
        StreamBinaryReader reader(&stream);
        // read content dictionary
        for (int i=0; i<header.contentCount; ++i)
        {
            PakItem item;
            item.name = reader.readString();
            item.type = reader.readString();
            item.offset = reader.readInt32();
            item.length = reader.readInt32();
            addItem(std::move(item));
        }
        // read all contents
        for (PakItem &item : m_contents)
        {
            stream.seekg(header.contentOffset + item.offset, std::ios::beg);
            item.data.resize(item.length);
            stream.read(reinterpret_cast<char*>(item.data.data()), item.length);
            item.offset = -1; // we will not be able to access the stream
        }
    }

    void PakFile::save(std::ostream &stream)
    {
        // we cannot detect the length of the file and where content begins,
        // so we have to write the header twice
        // write file header for the first time
        PakHeader header;
        header.contentCount = m_contents.size();
        StreamBinaryWriter writer(&stream);
        stream.write(reinterpret_cast<char*>(&header), sizeof(header));
        // we do not know where the content will locate, so it is also
        // necessary to write content dictionary twice
        // write content dictionary for the first time
        for (const PakItem &item : m_contents)
        {
            writer.writeString(item.name);
            writer.writeString(item.type);
            writer.writeInt(item.offset); // should be -1
            writer.writeInt(item.length);
        }
        header.contentOffset = stream.tellp();
        // write content items
        for (PakItem &item : m_contents)
        {
            // there are a magic number before every content data in origin Content.pak
            // it's DEADBEEF
            stream.put(0xDE);
            stream.put(0xAD);
            stream.put(0xBE);
            stream.put(0xEF);
            item.offset = static_cast<int>(stream.tellp()) - header.contentOffset;
            stream.write(reinterpret_cast<char*>(item.data.data()), item.length);
        }

        header.fileLength = stream.tellp();
        // write the header again
        stream.seekp(0, std::ios::beg);
        stream.write(reinterpret_cast<char*>(&header), sizeof(header));
        // write content dictionary again
        for (PakItem &item : m_contents)
        {
            writer.writeString(item.name);
            writer.writeString(item.type);
            writer.writeInt(item.offset);
            writer.writeInt(item.length);
            item.offset = -1; // as items can be modified, it is meaningless to keep a offset
        }
    }

    const std::vector<PakItem>& PakFile::contents() const
    {
        return m_contents;
    }

    void PakFile::addItem(const PakItem &item)
    {
        m_contents.push_back(item);
    }

    void PakFile::addItem(PakItem &&item)
    {
        m_contents.push_back(std::move(item));
    }

    PakItem& PakFile::getItem(std::size_t where)
    {
        return m_contents.at(where);
    }

    void PakFile::removeItem(std::size_t where)
    {
        m_contents.erase(m_contents.begin()+where);
    }
}

<commit_msg>fix a typo<commit_after>#include "pakfile.h"

#include <stdexcept>
#include <iterator>
#include <algorithm>
#include <cstring>

namespace scpak
{
    void PakFile::load(std::istream &stream)
    {
        // read header
        PakHeader header;
        stream.read(reinterpret_cast<char*>(&header), sizeof(header));
        if (!header.checkMagic())
            throw std::runtime_error("bad pak file");
        StreamBinaryReader reader(&stream);
        // read content dictionary
        for (int i=0; i<header.contentCount; ++i)
        {
            PakItem item;
            item.name = reader.readString();
            item.type = reader.readString();
            item.offset = reader.readInt32();
            item.length = reader.readInt32();
            addItem(std::move(item));
        }
        // read all contents
        for (PakItem &item : m_contents)
        {
            stream.seekg(header.contentOffset + item.offset, std::ios::beg);
            item.data.resize(item.length);
            stream.read(reinterpret_cast<char*>(item.data.data()), item.length);
            item.offset = -1; // we will not be able to access the stream
        }
    }

    void PakFile::save(std::ostream &stream)
    {
        // we cannot detect the length of the file and where content begins,
        // so we have to write the header twice
        // write file header for the first time
        PakHeader header;
        header.contentCount = m_contents.size();
        StreamBinaryWriter writer(&stream);
        stream.write(reinterpret_cast<char*>(&header), sizeof(header));
        // we do not know where the content will locate, so it is also
        // necessary to write content dictionary twice
        // write content dictionary for the first time
        for (const PakItem &item : m_contents)
        {
            writer.writeString(item.name);
            writer.writeString(item.type);
            writer.writeInt(item.offset); // should be -1
            writer.writeInt(item.length);
        }
        header.contentOffset = stream.tellp();
        // write content items
        for (PakItem &item : m_contents)
        {
            // there is a magic number before every content data in origin Content.pak
            // it's DEADBEEF
            stream.put(0xDE);
            stream.put(0xAD);
            stream.put(0xBE);
            stream.put(0xEF);
            item.offset = static_cast<int>(stream.tellp()) - header.contentOffset;
            stream.write(reinterpret_cast<char*>(item.data.data()), item.length);
        }

        header.fileLength = stream.tellp();
        // write the header again
        stream.seekp(0, std::ios::beg);
        stream.write(reinterpret_cast<char*>(&header), sizeof(header));
        // write content dictionary again
        for (PakItem &item : m_contents)
        {
            writer.writeString(item.name);
            writer.writeString(item.type);
            writer.writeInt(item.offset);
            writer.writeInt(item.length);
            item.offset = -1; // as items can be modified, it is meaningless to keep a offset
        }
    }

    const std::vector<PakItem>& PakFile::contents() const
    {
        return m_contents;
    }

    void PakFile::addItem(const PakItem &item)
    {
        m_contents.push_back(item);
    }

    void PakFile::addItem(PakItem &&item)
    {
        m_contents.push_back(std::move(item));
    }

    PakItem& PakFile::getItem(std::size_t where)
    {
        return m_contents.at(where);
    }

    void PakFile::removeItem(std::size_t where)
    {
        m_contents.erase(m_contents.begin()+where);
    }
}

<|endoftext|>


<commit_before>
/*
 * From:
 * http://stackoverflow.com/questions/6142576/sample-from-multivariate-normal-gaussian-distribution-in-c
 */

#include <iostream>

#include "bpmf.h"

using namespace std;
using namespace Eigen;

/*
  We need a functor that can pretend it's const,
  but to be a good random number generator
  it needs mutable state.
*/

#ifndef __clang__
thread_local
#endif
static std::mt19937 rng;

#ifndef __clang__
thread_local
#endif
static normal_distribution<> nd;

double randn(double) {
  return nd(rng);
}

auto
nrandn(int n) -> decltype( VectorXd::NullaryExpr(n, ptr_fun(randn)) )
{
    return VectorXd::NullaryExpr(n, ptr_fun(randn));
}

MatrixXd MvNormal_prec(const MatrixXd & Lambda, const VectorXd & mean, int nn = 1)
{
  int size = mean.rows(); // Dimensionality (rows)

  LLT<MatrixXd> chol(Lambda);

  MatrixXd r = MatrixXd::NullaryExpr(size,nn,ptr_fun(randn));
	chol.matrixU().solveInPlace(r);
  return r.colwise() + mean;
}

/*
  Draw nn samples from a size-dimensional normal distribution
  with a specified mean and covariance
*/
MatrixXd MvNormal(MatrixXd covar, VectorXd mean, int nn = 1)
{
  int size = mean.rows(); // Dimensionality (rows)
  MatrixXd normTransform(size,size);

  LLT<MatrixXd> cholSolver(covar);
  normTransform = cholSolver.matrixL();

  auto normSamples = MatrixXd::NullaryExpr(size,nn,ptr_fun(randn));
  MatrixXd samples = (normTransform * normSamples).colwise() + mean;

  return samples;
}

MatrixXd WishartUnit(int m, int df)
{
    MatrixXd c(m,m);
    c.setZero();

    for ( int i = 0; i < m; i++ ) {
        std::gamma_distribution<> gam(0.5*(df - i));
        c(i,i) = sqrt(2.0 * gam(rng));
        VectorXd r = nrandn(m-i-1).transpose();
        c.block(i,i+1,1,m-i-1) = r;
    }

    MatrixXd ret = c.transpose() * c;

#ifdef TEST_MVNORMAL
    cout << "WISHART UNIT {\n" << endl;
    cout << "  m:\n" << m << endl;
    cout << "  df:\n" << df << endl;
    cout << "  ret;\n" << ret << endl;
    cout << "  c:\n" << c << endl;
    cout << "}\n" << ret << endl;
#endif

    return ret;
}

MatrixXd Wishart(const MatrixXd &sigma, int df)
{
//  Get R, the upper triangular Cholesky factor of SIGMA.
  MatrixXd r = sigma.llt().matrixU();

//  Get AU, a sample from the unit Wishart distribution.
  MatrixXd au = WishartUnit(sigma.cols(), df);

//  Construct the matrix A = R' * AU * R.
  MatrixXd a = r.transpose() * au * r;

#ifdef TEST_MVNORMAL
    cout << "WISHART {\n" << endl;
    cout << "  sigma::\n" << sigma << endl;
    cout << "  r:\n" << r << endl;
    cout << "  au:\n" << au << endl;
    cout << "  df:\n" << df << endl;
    cout << "  a:\n" << a << endl;
    cout << "}\n" << endl;
#endif

  return a;
}

// from julia package Distributions: conjugates/normalwishart.jl
std::pair<VectorXd, MatrixXd> NormalWishart(VectorXd mu, double kappa, MatrixXd T, double nu)
{
  MatrixXd Lam = Wishart(T, nu);
  MatrixXd mu_o = MvNormal_prec(Lam * kappa, mu);

#ifdef TEST_MVNORMAL
    cout << "NORMAL WISHART {\n" << endl;
    cout << "  mu:\n" << mu << endl;
    cout << "  kappa:\n" << kappa << endl;
    cout << "  T:\n" << T << endl;
    cout << "  nu:\n" << nu << endl;
    cout << "  mu_o\n" << mu_o << endl;
    cout << "  Lam\n" << Lam << endl;
    cout << "}\n" << endl;
#endif

  return std::make_pair(mu_o , Lam);
}

double acc[9] = { .0 };

std::pair<VectorXd, MatrixXd> OldCondNormalWishart(const MatrixXd &U, const VectorXd &mu, const double kappa, const MatrixXd &T, const int nu)
{
  int N = U.cols();
  auto start = tick();
  auto Um = U.rowwise().mean();

  // http://stackoverflow.com/questions/15138634/eigen-is-there-an-inbuilt-way-to-calculate-sample-covariance
  MatrixXd C = U.colwise() - Um;
  MatrixXd S = (C * C.adjoint()) / double(N - 1);
  VectorXd mu_c = (kappa*mu + N*Um) / (kappa + N);
  double kappa_c = kappa + N;
  MatrixXd T_c = ( T + N * S.transpose() + (kappa * N)/(kappa + N) * (mu - Um) * ((mu - Um).transpose())).inverse();
  int nu_c = nu + N;

#ifdef TEST_MVNORMAL
  cout << "mu_c:\n" << mu_c << endl;
  cout << "kappa_c:\n" << kappa_c << endl;
  cout << "T_c:\n" << T_c << endl;
  cout << "nu_c:\n" << nu_c << endl;
#endif

  auto ret = NormalWishart(mu_c, kappa_c, T_c, nu_c);

  acc[8] += tick() - start;

  return ret;
}

// from bpmf.jl -- verified
std::pair<VectorXd, MatrixXd> CondNormalWishart(const MatrixXd &U, const VectorXd &mu, const double kappa, const MatrixXd &T, const int nu)
{
         double   t[8];

  int N = U.cols();

  t[0] = tick();
  auto Um = U.rowwise().mean();
  t[1] = tick();
  acc[0] += t[1] - t[0];

  // http://stackoverflow.com/questions/15138634/eigen-is-there-an-inbuilt-way-to-calculate-sample-covariance
  auto C = U.colwise() - Um;
  MatrixXd S = (C * C.adjoint()) / double(N - 1);
  VectorXd mu_c = (kappa*mu + N*Um) / (kappa + N);
  double kappa_c = kappa + N;
  t[2] = tick();
  acc[1] += t[2] - t[1];
  t[3] = tick();
  acc[2] += t[3] - t[2];
  t[4] = tick();
  acc[3] += t[4] - t[3];
  auto mu_m = (mu - Um);
  double kappa_m = (kappa * N)/(kappa + N);
  auto X = ( T + N * S + kappa_m * (mu_m * mu_m.transpose()));
  t[5] = tick();
  acc[4] += t[5] - t[4];
  MatrixXd T_c = X.inverse();
  t[6] = tick();
  acc[5] += t[6] - t[5];
  int nu_c = nu + N;

#ifdef TEST_MVNORMAL
  cout << "mu_c:\n" << mu_c << endl;
  cout << "kappa_c:\n" << kappa_c << endl;
  cout << "T_c:\n" << T_c << endl;
  cout << "nu_c:\n" << nu_c << endl;
#endif

  auto ret = NormalWishart(mu_c, kappa_c, T_c, nu_c);

  t[7] = tick();
  acc[6] += t[7] - t[6];
  acc[7] += t[7] - t[0];

  return ret;
}

#if defined(TEST_MVNORMAL) || defined (BENCH_MVNORMAL)

int main()
{

    MatrixXd U(32,32 * 1024);
    U.setOnes();

    VectorXd mu(32);
    mu.setZero();

    double kappa = 2;

    MatrixXd T(32,32);
    T.setIdentity(32,32);
    T.array() /= 4;

    int nu = 3;

    VectorXd mu_out;
    MatrixXd T_out;

#ifdef BENCH_MVNORMAL
    for(int i=0; i<300; ++i) {
        tie(mu_out, T_out) = CondNormalWishart(U, mu, kappa, T, nu);
        cout << i << "\r" << flush;
    }
    cout << endl << flush;

    for(int i=0; i<7; ++i) {
        cout << i << ": " << (int)(100.0 * acc[i] / acc[7])  << endl;
    }
    cout << "total: " << acc[7] << endl;

    for(int i=0; i<300; ++i) {
        tie(mu_out, T_out) = OldCondNormalWishart(U, mu, kappa, T, nu);
        cout << i << "\r" << flush;
    }
    cout << endl << flush;

    cout << "total: " << acc[8] << endl;

#else
#if 1
    cout << "COND NORMAL WISHART\n" << endl;

    tie(mu_out, T_out) = CondNormalWishart(U, mu, kappa, T, nu);

    cout << "mu_out:\n" << mu_out << endl;
    cout << "T_out:\n" << T_out << endl;

    cout << "\n-----\n\n";
#endif

#if 0
    cout << "NORMAL WISHART\n" << endl;

    tie(mu_out, T_out) = NormalWishart(mu, kappa, T, nu);
    cout << "mu_out:\n" << mu_out << endl;
    cout << "T_out:\n" << T_out << endl;

#endif

#if 0
    cout << "MVNORMAL\n" << endl;
    MatrixXd out = MvNormal(T, mu, 10);
    cout << "mu:\n" << mu << endl;
    cout << "T:\n" << T << endl;
    cout << "out:\n" << out << endl;
#endif
#endif
}

#endif
<commit_msg>removed timing<commit_after>
/*
 * From:
 * http://stackoverflow.com/questions/6142576/sample-from-multivariate-normal-gaussian-distribution-in-c
 */

#include <iostream>

#include "bpmf.h"

using namespace std;
using namespace Eigen;

/*
  We need a functor that can pretend it's const,
  but to be a good random number generator
  it needs mutable state.
*/

#ifndef __clang__
thread_local
#endif
static std::mt19937 rng;

#ifndef __clang__
thread_local
#endif
static normal_distribution<> nd;

double randn(double) {
  return nd(rng);
}

auto
nrandn(int n) -> decltype( VectorXd::NullaryExpr(n, ptr_fun(randn)) )
{
    return VectorXd::NullaryExpr(n, ptr_fun(randn));
}

MatrixXd MvNormal_prec(const MatrixXd & Lambda, const VectorXd & mean, int nn = 1)
{
  int size = mean.rows(); // Dimensionality (rows)

  LLT<MatrixXd> chol(Lambda);

  MatrixXd r = MatrixXd::NullaryExpr(size,nn,ptr_fun(randn));
	chol.matrixU().solveInPlace(r);
  return r.colwise() + mean;
}

/*
  Draw nn samples from a size-dimensional normal distribution
  with a specified mean and covariance
*/
MatrixXd MvNormal(MatrixXd covar, VectorXd mean, int nn = 1)
{
  int size = mean.rows(); // Dimensionality (rows)
  MatrixXd normTransform(size,size);

  LLT<MatrixXd> cholSolver(covar);
  normTransform = cholSolver.matrixL();

  auto normSamples = MatrixXd::NullaryExpr(size,nn,ptr_fun(randn));
  MatrixXd samples = (normTransform * normSamples).colwise() + mean;

  return samples;
}

MatrixXd WishartUnit(int m, int df)
{
    MatrixXd c(m,m);
    c.setZero();

    for ( int i = 0; i < m; i++ ) {
        std::gamma_distribution<> gam(0.5*(df - i));
        c(i,i) = sqrt(2.0 * gam(rng));
        VectorXd r = nrandn(m-i-1).transpose();
        c.block(i,i+1,1,m-i-1) = r;
    }

    MatrixXd ret = c.transpose() * c;

#ifdef TEST_MVNORMAL
    cout << "WISHART UNIT {\n" << endl;
    cout << "  m:\n" << m << endl;
    cout << "  df:\n" << df << endl;
    cout << "  ret;\n" << ret << endl;
    cout << "  c:\n" << c << endl;
    cout << "}\n" << ret << endl;
#endif

    return ret;
}

MatrixXd Wishart(const MatrixXd &sigma, int df)
{
//  Get R, the upper triangular Cholesky factor of SIGMA.
  MatrixXd r = sigma.llt().matrixU();

//  Get AU, a sample from the unit Wishart distribution.
  MatrixXd au = WishartUnit(sigma.cols(), df);

//  Construct the matrix A = R' * AU * R.
  MatrixXd a = r.transpose() * au * r;

#ifdef TEST_MVNORMAL
    cout << "WISHART {\n" << endl;
    cout << "  sigma::\n" << sigma << endl;
    cout << "  r:\n" << r << endl;
    cout << "  au:\n" << au << endl;
    cout << "  df:\n" << df << endl;
    cout << "  a:\n" << a << endl;
    cout << "}\n" << endl;
#endif

  return a;
}

// from julia package Distributions: conjugates/normalwishart.jl
std::pair<VectorXd, MatrixXd> NormalWishart(VectorXd mu, double kappa, MatrixXd T, double nu)
{
  MatrixXd Lam = Wishart(T, nu);
  MatrixXd mu_o = MvNormal_prec(Lam * kappa, mu);

#ifdef TEST_MVNORMAL
    cout << "NORMAL WISHART {\n" << endl;
    cout << "  mu:\n" << mu << endl;
    cout << "  kappa:\n" << kappa << endl;
    cout << "  T:\n" << T << endl;
    cout << "  nu:\n" << nu << endl;
    cout << "  mu_o\n" << mu_o << endl;
    cout << "  Lam\n" << Lam << endl;
    cout << "}\n" << endl;
#endif

  return std::make_pair(mu_o , Lam);
}

std::pair<VectorXd, MatrixXd> OldCondNormalWishart(const MatrixXd &U, const VectorXd &mu, const double kappa, const MatrixXd &T, const int nu)
{
  int N = U.cols();

  auto Um = U.rowwise().mean();

  // http://stackoverflow.com/questions/15138634/eigen-is-there-an-inbuilt-way-to-calculate-sample-covariance
  MatrixXd C = U.colwise() - Um;
  MatrixXd S = (C * C.adjoint()) / double(N - 1);
  VectorXd mu_c = (kappa*mu + N*Um) / (kappa + N);
  double kappa_c = kappa + N;
  MatrixXd T_c = ( T + N * S.transpose() + (kappa * N)/(kappa + N) * (mu - Um) * ((mu - Um).transpose())).inverse();
  int nu_c = nu + N;

#ifdef TEST_MVNORMAL
  cout << "mu_c:\n" << mu_c << endl;
  cout << "kappa_c:\n" << kappa_c << endl;
  cout << "T_c:\n" << T_c << endl;
  cout << "nu_c:\n" << nu_c << endl;
#endif

  return NormalWishart(mu_c, kappa_c, T_c, nu_c);
}

// from bpmf.jl -- verified
std::pair<VectorXd, MatrixXd> CondNormalWishart(const MatrixXd &U, const VectorXd &mu, const double kappa, const MatrixXd &T, const int nu)
{
  int N = U.cols();

  auto Um = U.rowwise().mean();

  // http://stackoverflow.com/questions/15138634/eigen-is-there-an-inbuilt-way-to-calculate-sample-covariance
  auto C = U.colwise() - Um;
  MatrixXd S = (C * C.adjoint()) / double(N - 1);
  VectorXd mu_c = (kappa*mu + N*Um) / (kappa + N);
  double kappa_c = kappa + N;
  auto mu_m = (mu - Um);
  double kappa_m = (kappa * N)/(kappa + N);
  auto X = ( T + N * S + kappa_m * (mu_m * mu_m.transpose()));
  MatrixXd T_c = X.inverse();
  int nu_c = nu + N;

#ifdef TEST_MVNORMAL
  cout << "mu_c:\n" << mu_c << endl;
  cout << "kappa_c:\n" << kappa_c << endl;
  cout << "T_c:\n" << T_c << endl;
  cout << "nu_c:\n" << nu_c << endl;
#endif

  return NormalWishart(mu_c, kappa_c, T_c, nu_c);
}

#if defined(TEST_MVNORMAL) || defined (BENCH_MVNORMAL)

int main()
{

    MatrixXd U(32,32 * 1024);
    U.setOnes();

    VectorXd mu(32);
    mu.setZero();

    double kappa = 2;

    MatrixXd T(32,32);
    T.setIdentity(32,32);
    T.array() /= 4;

    int nu = 3;

    VectorXd mu_out;
    MatrixXd T_out;

#ifdef BENCH_MVNORMAL
    for(int i=0; i<300; ++i) {
        tie(mu_out, T_out) = CondNormalWishart(U, mu, kappa, T, nu);
        cout << i << "\r" << flush;
    }
    cout << endl << flush;

    for(int i=0; i<7; ++i) {
        cout << i << ": " << (int)(100.0 * acc[i] / acc[7])  << endl;
    }
    cout << "total: " << acc[7] << endl;

    for(int i=0; i<300; ++i) {
        tie(mu_out, T_out) = OldCondNormalWishart(U, mu, kappa, T, nu);
        cout << i << "\r" << flush;
    }
    cout << endl << flush;

    cout << "total: " << acc[8] << endl;

#else
#if 1
    cout << "COND NORMAL WISHART\n" << endl;

    tie(mu_out, T_out) = CondNormalWishart(U, mu, kappa, T, nu);

    cout << "mu_out:\n" << mu_out << endl;
    cout << "T_out:\n" << T_out << endl;

    cout << "\n-----\n\n";
#endif

#if 0
    cout << "NORMAL WISHART\n" << endl;

    tie(mu_out, T_out) = NormalWishart(mu, kappa, T, nu);
    cout << "mu_out:\n" << mu_out << endl;
    cout << "T_out:\n" << T_out << endl;

#endif

#if 0
    cout << "MVNORMAL\n" << endl;
    MatrixXd out = MvNormal(T, mu, 10);
    cout << "mu:\n" << mu << endl;
    cout << "T:\n" << T << endl;
    cout << "out:\n" << out << endl;
#endif
#endif
}

#endif
<|endoftext|>


<commit_before>/*
 * Copyright (c) 2012, Dennis Hedback
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are met:
 *
 *   * Redistributions of source code must retain the above copyright notice,
 *     this list of conditions and the following disclaimer.
 *   * Redistributions in binary form must reproduce the above copyright
 *     notice, this list of conditions and the following disclaimer in the
 *     documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGE.
 */

#include <iostream>
#include <iterator>
#include <set>
#include <string>
#include <vector>

typedef std::set<std::string> Set;
typedef std::vector<std::string> Tuple;
typedef std::set<Tuple> Product;
typedef std::vector<Set> Generator;
typedef std::set<Generator> Quotient;

struct Options
{
    bool verbose;
};

static Options opts;

#define VPRINT(x) if (opts.verbose) { std::cerr << x << std::endl; }

Product read_tuples(void)
{
    Product prod;
    Tuple current_tuple;
    std::string current_elem;

    for (std::istreambuf_iterator<char> it(std::cin), end; it != end; it++)
    {
        char c = *it;

        if (c == ',' || c == '\n')
        {
            current_tuple.push_back(current_elem);
            current_elem.clear();

            if (c == '\n')
            {
                prod.insert(current_tuple);
                current_tuple.clear();
            }
        }
        else
        {
            current_elem += c;
        }
    }

    return prod;
}

unsigned int product_cardinality(Generator gen)
{
    unsigned int cardinality = 1;

    for (Generator::iterator it = gen.begin(); it != gen.end(); it++)
        cardinality *= (*it).size();

    return cardinality;
}

Product cartesian_product(Generator gen)
{
    Product prod;
    unsigned int counters[gen.size()];
    size_t gen_size;

    gen_size = gen.size();

    for (unsigned int i = 0; i < gen_size; i++)
        counters[i] = 0;

    for (unsigned int i = 0; i < product_cardinality(gen); i++)
    {
        Tuple current_tuple;

        for (unsigned int j = 0; j < gen_size; j++)
        {
            Set current_set = gen[j];
            unsigned int k = 0;

            for (Set::iterator it = current_set.begin(); it != current_set.end(); k++, it++)
                if (k == counters[j])
                    current_tuple.push_back(*it);
        }

        prod.insert(current_tuple);

        for (unsigned int j = 0; j < gen_size; j++)
        {
            counters[j]++;
            if (counters[j] > gen[j].size() - 1)
                counters[j] = 0;
            else
                break;
        }
    }

    return prod;
}

Generator init_generator(size_t size)
{
    Generator gen;
    for (unsigned int i = 0; i < size; i++)
        gen.push_back(Set());
    return gen;
}

Generator reference_generator(Product prod)
{
    Generator ref_generator;

    if (prod.size() > 0)
        ref_generator = init_generator((*prod.begin()).size());

    for (Product::iterator pi = prod.begin(); pi != prod.end(); pi++)
    {
        unsigned int i = 0;

        for (Tuple::const_iterator ti = (*pi).begin(); ti != (*pi).end(); i++, ti++)
        {
            ref_generator[i].insert(*ti);
        }
    }

    return ref_generator;
}

bool product_contains(Product prod, Tuple tuple)
{
    bool found = false;
    for (Product::iterator it = prod.begin(); it != prod.end(); it++)
        if ((*it) == tuple)
            found = true;
    return found;
}

Product difference(Product prod_1, Product prod_2)
{
    Product diff;

    for (Product::iterator pi_1 = prod_1.begin(); pi_1 != prod_1.end(); pi_1++)
        if (!product_contains(prod_2, (*pi_1)))
            diff.insert(*pi_1);

    return diff;
}

void print_product(Product prod)
{
    for (Product::iterator pi = prod.begin(); pi != prod.end(); pi++)
    {
        for (Tuple::const_iterator ti = (*pi).begin(); ti != (*pi).end(); ti++)
        {
            std::cout << *ti;

            if (++ti != (*pi).end())
                std::cout << ',';

            ti--;
        }

        std::cout << std::endl;
    }
}

Quotient generating_sets(Product prod)
{
    Quotient quot;
    Generator ref_generator = reference_generator(prod);
    Product ref_product = cartesian_product(ref_generator);
    Product diff = difference(ref_product, prod);

    for (unsigned int num_generators = 1, inserted = 0; prod.size() > 0; num_generators++)
    {
        Generator current_generator = init_generator((*prod.begin()).size());
        Product to_erase;
        for (Product::iterator pi = prod.begin(); pi != prod.end();)
        {
            Tuple current_tuple = (*pi);
            Generator tmp = current_generator;
            size_t tup_size = current_tuple.size();

            for (unsigned int i = 0; i < tup_size; i++)
            {
                tmp[i].insert(current_tuple[i]);
            }

            Product tmp_product = cartesian_product(tmp);

            if (difference(tmp_product, diff).size() == product_cardinality(tmp)) {
                current_generator = tmp;
                prod.erase(pi++);
                VPRINT(++inserted << " tuples inserted into " << num_generators << " generators ");
            }
            else
            {
                ++pi;
            }
        }
        quot.insert(current_generator);
    }

    return quot;
}

void print_quotient(Quotient quot)
{
    for (Quotient::iterator qi = quot.begin(); qi != quot.end(); qi++)
    {
        for (Generator::const_iterator gi = (*qi).begin(); gi != (*qi).end(); gi++)
        {
            for (Set::iterator si = (*gi).begin(); si != (*gi).end(); si++)
            {
                std::cout << *si;

                if (++si != (*gi).end())
                    std::cout << ',';

                si--;
            }

            std::cout << std::endl;
        }

        std::cout << "%%" << std::endl;
    }
}

int main(int argc, char *argv[])
{
    opts.verbose = true;
    Product prod = read_tuples();
    Quotient quot = generating_sets(prod);
    print_quotient(quot);

    return 0;
}
<commit_msg>Decreased execution time by orders of magnitude<commit_after>/*
 * Copyright (c) 2012, Dennis Hedback
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are met:
 *
 *   * Redistributions of source code must retain the above copyright notice,
 *     this list of conditions and the following disclaimer.
 *   * Redistributions in binary form must reproduce the above copyright
 *     notice, this list of conditions and the following disclaimer in the
 *     documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGE.
 */

#include <iostream>
#include <iterator>
#include <set>
#include <string>
#include <vector>

typedef std::set<std::string> Set;
typedef std::vector<std::string> Tuple;
typedef std::set<Tuple> Product;
typedef std::vector<Set> Generator;
typedef std::set<Generator> Quotient;

struct Options
{
    bool verbose;
};

static Options opts;

#define VPRINT(x) if (opts.verbose) { std::cerr << x << std::endl; }

Product read_tuples(void)
{
    Product prod;
    Tuple current_tuple;
    std::string current_elem;

    for (std::istreambuf_iterator<char> it(std::cin), end; it != end; it++)
    {
        char c = *it;

        if (c == ',' || c == '\n')
        {
            current_tuple.push_back(current_elem);
            current_elem.clear();

            if (c == '\n')
            {
                prod.insert(current_tuple);
                current_tuple.clear();
            }
        }
        else
        {
            current_elem += c;
        }
    }

    return prod;
}

unsigned int product_cardinality(Generator gen)
{
    unsigned int cardinality = 1;

    for (Generator::iterator it = gen.begin(); it != gen.end(); it++)
        cardinality *= (*it).size();

    return cardinality;
}

Product cartesian_product(Generator gen)
{
    Product prod;
    unsigned int counters[gen.size()];
    size_t gen_size;

    gen_size = gen.size();

    for (unsigned int i = 0; i < gen_size; i++)
        counters[i] = 0;

    for (unsigned int i = 0; i < product_cardinality(gen); i++)
    {
        Tuple current_tuple;

        for (unsigned int j = 0; j < gen_size; j++)
        {
            Set current_set = gen[j];
            unsigned int k = 0;

            for (Set::iterator it = current_set.begin(); it != current_set.end(); k++, it++)
                if (k == counters[j])
                    current_tuple.push_back(*it);
        }

        prod.insert(current_tuple);

        for (unsigned int j = 0; j < gen_size; j++)
        {
            counters[j]++;
            if (counters[j] > gen[j].size() - 1)
                counters[j] = 0;
            else
                break;
        }
    }

    return prod;
}

Generator init_generator(size_t size)
{
    Generator gen;
    for (unsigned int i = 0; i < size; i++)
        gen.push_back(Set());
    return gen;
}

Generator reference_generator(Product prod)
{
    Generator ref_generator;

    if (prod.size() > 0)
        ref_generator = init_generator((*prod.begin()).size());

    for (Product::iterator pi = prod.begin(); pi != prod.end(); pi++)
    {
        unsigned int i = 0;

        for (Tuple::const_iterator ti = (*pi).begin(); ti != (*pi).end(); i++, ti++)
        {
            ref_generator[i].insert(*ti);
        }
    }

    return ref_generator;
}

bool product_contains(Product prod, Tuple tuple)
{
    bool found = false;
    for (Product::iterator it = prod.begin(); it != prod.end(); it++)
        if ((*it) == tuple)
            found = true;
    return found;
}

Product difference(Product prod_1, Product prod_2)
{
    Product diff;

    for (Product::iterator pi_1 = prod_1.begin(); pi_1 != prod_1.end(); pi_1++)
        if (!product_contains(prod_2, (*pi_1)))
            diff.insert(*pi_1);

    return diff;
}

void print_product(Product prod)
{
    for (Product::iterator pi = prod.begin(); pi != prod.end(); pi++)
    {
        for (Tuple::const_iterator ti = (*pi).begin(); ti != (*pi).end(); ti++)
        {
            std::cout << *ti;

            if (++ti != (*pi).end())
                std::cout << ',';

            ti--;
        }

        std::cout << std::endl;
    }
}

Quotient generating_sets(Product prod)
{
    Quotient quot;
    Product ref_prod = prod;

    /*
    Generator ref_generator = reference_generator(prod);
    Product ref_product = cartesian_product(ref_generator);
    Product diff = difference(ref_product, prod);
    */

    for (unsigned int num_generators = 1, inserted = 0; prod.size() > 0; num_generators++)
    {
        Generator current_generator = init_generator((*prod.begin()).size());
        Product to_erase;
        for (Product::iterator pi = prod.begin(); pi != prod.end();)
        {
            Tuple current_tuple = (*pi);
            Generator tmp = current_generator;
            size_t tup_size = current_tuple.size();

            for (unsigned int i = 0; i < tup_size; i++)
            {
                tmp[i].insert(current_tuple[i]);
            }

            Product tmp_product = cartesian_product(tmp);

            for (Product::iterator tmpi = tmp_product.begin(); tmpi != tmp_product.end(); tmpi++)
            {
                if (!product_contains(ref_prod, *tmpi))
                {
                    ++pi;
                    // FIXME: Go away ugly goto, go away!
                    goto foo;
                }
            }

            current_generator = tmp;
            prod.erase(pi++);
                VPRINT(++inserted << " tuples inserted into " << num_generators << " generators ");
        foo:
            if (1 == 2) break;
        }
        quot.insert(current_generator);
    }

    return quot;
}

void print_quotient(Quotient quot)
{
    for (Quotient::iterator qi = quot.begin(); qi != quot.end(); qi++)
    {
        for (Generator::const_iterator gi = (*qi).begin(); gi != (*qi).end(); gi++)
        {
            for (Set::iterator si = (*gi).begin(); si != (*gi).end(); si++)
            {
                std::cout << *si;

                if (++si != (*gi).end())
                    std::cout << ',';

                si--;
            }

            std::cout << std::endl;
        }

        std::cout << "%%" << std::endl;
    }
}

int main(int argc, char *argv[])
{
    opts.verbose = true;
    Product prod = read_tuples();
    Quotient quot = generating_sets(prod);
    print_quotient(quot);

    return 0;
}
<|endoftext|>