<commit_before>//------------------------------------------------------------------------------
// Copyright (c) 2016 John D. Haughton
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
//------------------------------------------------------------------------------

#include <cstring>

#include "PLT/Image.h"

namespace PLT {

unsigned Image::getPixelBits() { return 4; }

uint32_t Image::getPixel(unsigned x, unsigned y) const
{
   uint8_t pair = buffer[(x + y * pitch) / 2];
   uint8_t grey = x & 1 ? (pair << 4) : (pair & 0xF0);
   return (grey << 16) | (grey << 8) | grey;
}

void Image::point(STB::Colour rgb, unsigned x, unsigned y)
{
   uint8_t& pair = buffer[(x + y * pitch) / 2];
   uint8_t grey = 0xF - (STB::ColourDecode(rgb).grn() >> 4);
   if(x & 1)
   {
      pair = (pair & 0xF0) | grey;
   }
   else
   {
      pair = (pair & 0x0F) | (grey << 4);
   }
}

void Image::clear(STB::Colour rgb)
{
   defaultClear(rgb);
}

void Image::span(STB::Colour rgb, unsigned x1, unsigned y, unsigned x2)
{
   defaultSpan(rgb, x1, y, x2);
}

void Image::blit(const Image& source,
                 unsigned x, unsigned y,
                 unsigned w, unsigned h,
                 unsigned src_x, unsigned src_y)
{
   defaultBlit(source, x, y, w, h, src_x, src_y);
}

void Image::lineBlit(uint8_t pixel_mask, STB::Colour one, STB::Colour zero,
                     unsigned x, unsigned y)
{
   defaultLineBlit(pixel_mask, one, zero, x, y);
}

bool Image::save(const char* name)
{
   return defaultSave(name);
}

} // namespace PLT
<commit_msg>Fix Kindle3 SDL2 build issue<commit_after>//------------------------------------------------------------------------------
// Copyright (c) 2016 John D. Haughton
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
//------------------------------------------------------------------------------

#include <cstring>

#include "PLT/Image.h"

namespace PLT {

unsigned Image::getPixelBits() { return 4; }

uint32_t Image::getPixel(unsigned x, unsigned y) const
{
   uint8_t pair = buffer[(x + y * pitch) / 2];
   uint8_t grey = x & 1 ? (pair << 4) : (pair & 0xF0);
   return (grey << 16) | (grey << 8) | grey;
}

void Image::point(STB::Colour rgb, unsigned x, unsigned y)
{
   uint8_t& pair = buffer[(x + y * pitch) / 2];
   uint8_t grey = 0xF - (STB::ColourDecode(rgb).grn() >> 4);
   if(x & 1)
   {
      pair = (pair & 0xF0) | grey;
   }
   else
   {
      pair = (pair & 0x0F) | (grey << 4);
   }
}

void Image::clear(STB::Colour rgb)
{
   defaultClear(rgb);
}

void Image::span(STB::Colour rgb, unsigned x1, unsigned y, unsigned x2)
{
   defaultSpan(rgb, x1, y, x2);
}

void Image::blit(const Image& source,
                 unsigned x, unsigned y,
                 unsigned w, unsigned h,
                 unsigned src_x, unsigned src_y)
{
   defaultBlit(source, x, y, w, h, src_x, src_y);
}

void Image::lineBlit(uint8_t pixel_mask, STB::Colour one, STB::Colour zero,
                     unsigned x, unsigned y)
{
   defaultLineBlit(pixel_mask, one, zero, x, y);
}

bool Image::save(const char* name) const
{
   return defaultSave(name);
}

} // namespace PLT
<|endoftext|>


<commit_before>
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <semaphore.h>
#include <unistd.h>
#include <pthread.h>

#include "EchoIndicationWrapper.h"
#include "EchoRequestProxy.h"
#include "GeneratedTypes.h"
#include "SwallowProxy.h"
#include <sys/ioctl.h>
#include "zynqportal.h"
#include <errno.h>

#define LOOP_COUNT 5
#define SEPARATE_EVENT_THREAD

EchoRequestProxy *echoRequestProxy = 0;

#ifdef SEPARATE_EVENT_THREAD
#define CHECKSEM(A) 1
#else // use inline sync
#define CHECKSEM(A) (!(A))
#endif

static int silent;
static int flag_heard;
static sem_t sem_heard;
static pthread_mutex_t mutex_heard;

PortalPoller *poller = 0;
static int use_mutex = 0;
static int use_inline = 0;
pthread_t threaddata;

static void *pthread_worker(void *p)
{
    void *rc = NULL;
    while (CHECKSEM(sem_heard) && !rc && !poller->stopping) {
        rc = poller->portalExec_poll(poller->portalExec_timeout);
        if ((long) rc >= 0)
            rc = poller->portalExec_event();
    }
    return rc;
}
class EchoIndication : public EchoIndicationWrapper
{
public:
    virtual void heard(uint32_t v) {
        if (!silent)
            fprintf(stderr, "heard an echo: %d\n", v);
        flag_heard++;
        if (use_mutex)
            pthread_mutex_unlock(&mutex_heard);
        else
            sem_post(&sem_heard);
    }
    virtual void heard2(uint32_t v1, uint32_t v2) {}
    EchoIndication(unsigned int id, PortalPoller *poller) : EchoIndicationWrapper(id, poller) {}
};

static void run_test(void)
{
#define PCYC_LEN 20
  int i;
  uint64_t pcyc[PCYC_LEN];
  uint64_t lastp;
  PortalInterruptTime inttime;

  memset(pcyc, 0, sizeof(pcyc));
  pcyc[0] = portalCycleCount();
  flag_heard = 0;
  pcyc[3] = portalCycleCount();
    echoRequestProxy->say(22);
  pcyc[8] = portalCycleCount();
  if (use_inline) {
    while (!flag_heard) {
        //void *rc = poller->portalExec_poll(poller->portalExec_timeout);
        //if ((long) rc >= 0)
        poller->portalExec_event();
    }
    pcyc[9] = pcyc[8];
    pcyc[12] = pcyc[8];
    pcyc[17] = pcyc[8];
  }
  else {
  if (use_mutex)
    pthread_mutex_lock(&mutex_heard);
  else
    sem_wait(&sem_heard);
  ioctl(globalDirectory.fpga_fd, PORTAL_INTERRUPT_TIME, &inttime);
  pcyc[9] = (((uint64_t)inttime.msb)<<32) | ((uint64_t)inttime.lsb);
  pcyc[12] = poll_return_time; // time after poll() returns
  pcyc[17] = poll_enter_time; // time poll() reentered
  }
  pcyc[18] = portalCycleCount();
  for (i = 0; i < PCYC_LEN; i++)
      if (pcyc[i]) {
          if (i)
              printf("  %d:%5lld;", i, (long long)(pcyc[i] - lastp));
          lastp = pcyc[i];
      }
  printf("\n");
}

int main(int argc, const char **argv)
{
    int i;

    poller = new PortalPoller();
    EchoIndication *echoIndication = new EchoIndication(IfcNames_EchoIndication, poller);
    // these use the default poller
    SwallowProxy *swallowProxy = new SwallowProxy(IfcNames_Swallow);
    echoRequestProxy = new EchoRequestProxy(IfcNames_EchoRequest);
    pthread_mutex_lock(&mutex_heard);
    sem_init(&sem_heard, 0, 0);

    poller->portalExec_init();
    pthread_create(&threaddata, NULL, &pthread_worker, (void*)poller);
    portalExec_start();
#ifdef ZYNQ
    uint64_t portcyc2 = portalCycleCount();
    unsigned int high_bits = ioctl(globalDirectory.fpga_fd, PORTAL_DIRECTORY_READ, ((unsigned long)PORTAL_DIRECTORY_COUNTER_MSB) - (unsigned long) &globalDirectory.map_base[0]);
    unsigned int low_bits = ioctl(globalDirectory.fpga_fd, PORTAL_DIRECTORY_READ, ((unsigned long)PORTAL_DIRECTORY_COUNTER_LSB) - (unsigned long) &globalDirectory.map_base[0]);
    uint64_t portcyc = portalCycleCount();
    printf("kernel crossing fpga cycles IN: %lld BACK: %lld\n", (long long)low_bits - portcyc2, (long long)portcyc - low_bits);
#endif

    run_test();
    printf("turn off printf in responder\n");
    silent = 1;
    for (i = 0; i < LOOP_COUNT; i++)
        run_test();
    printf("now try as mutex\n");
    use_mutex = 1;
    for (i = 0; i < LOOP_COUNT; i++)
        run_test();
    use_mutex = 0;

    struct sched_param sched_param;
    int sched_policy;
    pthread_getschedparam(pthread_self(), &sched_policy, &sched_param);
    sched_param.sched_priority = sched_get_priority_max(SCHED_RR);
    pthread_setschedparam(pthread_self(), SCHED_RR, &sched_param);
    printf("[%s:%d] scheduling policy changed to SCHED_RR\n", __FUNCTION__, __LINE__);
    for (i = 0; i < LOOP_COUNT; i++)
        run_test();
    printf("disable interrupts for echoIndication\n");
    poller->portalExec_end();
    printf("now try inline\n");
    use_inline = 1;
    for (i = 0; i < LOOP_COUNT; i++)
        run_test();
    portalExec_end();
printf("[%s:%d] end\n", __FUNCTION__, __LINE__);
    return 0;
}
<commit_msg>include string.h into ipcperf/testecho.cpp<commit_after>
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <semaphore.h>
#include <unistd.h>
#include <pthread.h>
#include <string.h>

#include "EchoIndicationWrapper.h"
#include "EchoRequestProxy.h"
#include "GeneratedTypes.h"
#include "SwallowProxy.h"
#include <sys/ioctl.h>
#include "zynqportal.h"
#include <errno.h>

#define LOOP_COUNT 5
#define SEPARATE_EVENT_THREAD

EchoRequestProxy *echoRequestProxy = 0;

#ifdef SEPARATE_EVENT_THREAD
#define CHECKSEM(A) 1
#else // use inline sync
#define CHECKSEM(A) (!(A))
#endif

static int silent;
static int flag_heard;
static sem_t sem_heard;
static pthread_mutex_t mutex_heard;

PortalPoller *poller = 0;
static int use_mutex = 0;
static int use_inline = 0;
pthread_t threaddata;

static void *pthread_worker(void *p)
{
    void *rc = NULL;
    while (CHECKSEM(sem_heard) && !rc && !poller->stopping) {
        rc = poller->portalExec_poll(poller->portalExec_timeout);
        if ((long) rc >= 0)
            rc = poller->portalExec_event();
    }
    return rc;
}
class EchoIndication : public EchoIndicationWrapper
{
public:
    virtual void heard(uint32_t v) {
        if (!silent)
            fprintf(stderr, "heard an echo: %d\n", v);
        flag_heard++;
        if (use_mutex)
            pthread_mutex_unlock(&mutex_heard);
        else
            sem_post(&sem_heard);
    }
    virtual void heard2(uint32_t v1, uint32_t v2) {}
    EchoIndication(unsigned int id, PortalPoller *poller) : EchoIndicationWrapper(id, poller) {}
};

static void run_test(void)
{
#define PCYC_LEN 20
  int i;
  uint64_t pcyc[PCYC_LEN];
  uint64_t lastp;
  PortalInterruptTime inttime;

  memset(pcyc, 0, sizeof(pcyc));
  pcyc[0] = portalCycleCount();
  flag_heard = 0;
  pcyc[3] = portalCycleCount();
    echoRequestProxy->say(22);
  pcyc[8] = portalCycleCount();
  if (use_inline) {
    while (!flag_heard) {
        //void *rc = poller->portalExec_poll(poller->portalExec_timeout);
        //if ((long) rc >= 0)
        poller->portalExec_event();
    }
    pcyc[9] = pcyc[8];
    pcyc[12] = pcyc[8];
    pcyc[17] = pcyc[8];
  }
  else {
  if (use_mutex)
    pthread_mutex_lock(&mutex_heard);
  else
    sem_wait(&sem_heard);
  ioctl(globalDirectory.fpga_fd, PORTAL_INTERRUPT_TIME, &inttime);
  pcyc[9] = (((uint64_t)inttime.msb)<<32) | ((uint64_t)inttime.lsb);
  pcyc[12] = poll_return_time; // time after poll() returns
  pcyc[17] = poll_enter_time; // time poll() reentered
  }
  pcyc[18] = portalCycleCount();
  for (i = 0; i < PCYC_LEN; i++)
      if (pcyc[i]) {
          if (i)
              printf("  %d:%5lld;", i, (long long)(pcyc[i] - lastp));
          lastp = pcyc[i];
      }
  printf("\n");
}

int main(int argc, const char **argv)
{
    int i;

    poller = new PortalPoller();
    EchoIndication *echoIndication = new EchoIndication(IfcNames_EchoIndication, poller);
    // these use the default poller
    SwallowProxy *swallowProxy = new SwallowProxy(IfcNames_Swallow);
    echoRequestProxy = new EchoRequestProxy(IfcNames_EchoRequest);
    pthread_mutex_lock(&mutex_heard);
    sem_init(&sem_heard, 0, 0);

    poller->portalExec_init();
    pthread_create(&threaddata, NULL, &pthread_worker, (void*)poller);
    portalExec_start();
#ifdef ZYNQ
    uint64_t portcyc2 = portalCycleCount();
    unsigned int high_bits = ioctl(globalDirectory.fpga_fd, PORTAL_DIRECTORY_READ, ((unsigned long)PORTAL_DIRECTORY_COUNTER_MSB) - (unsigned long) &globalDirectory.map_base[0]);
    unsigned int low_bits = ioctl(globalDirectory.fpga_fd, PORTAL_DIRECTORY_READ, ((unsigned long)PORTAL_DIRECTORY_COUNTER_LSB) - (unsigned long) &globalDirectory.map_base[0]);
    uint64_t portcyc = portalCycleCount();
    printf("kernel crossing fpga cycles IN: %lld BACK: %lld\n", (long long)low_bits - portcyc2, (long long)portcyc - low_bits);
#endif

    run_test();
    printf("turn off printf in responder\n");
    silent = 1;
    for (i = 0; i < LOOP_COUNT; i++)
        run_test();
    printf("now try as mutex\n");
    use_mutex = 1;
    for (i = 0; i < LOOP_COUNT; i++)
        run_test();
    use_mutex = 0;

    struct sched_param sched_param;
    int sched_policy;
    pthread_getschedparam(pthread_self(), &sched_policy, &sched_param);
    sched_param.sched_priority = sched_get_priority_max(SCHED_RR);
    pthread_setschedparam(pthread_self(), SCHED_RR, &sched_param);
    printf("[%s:%d] scheduling policy changed to SCHED_RR\n", __FUNCTION__, __LINE__);
    for (i = 0; i < LOOP_COUNT; i++)
        run_test();
    printf("disable interrupts for echoIndication\n");
    poller->portalExec_end();
    printf("now try inline\n");
    use_inline = 1;
    for (i = 0; i < LOOP_COUNT; i++)
        run_test();
    portalExec_end();
printf("[%s:%d] end\n", __FUNCTION__, __LINE__);
    return 0;
}
<|endoftext|>


<commit_before>#include <vector>
#include <iostream>
#include <iterator>

#include <libport/condition.hh>
#include <libport/foreach.hh>
#include <libport/unit-test.hh>
#include <libport/thread.hh>
#include <libport/unistd.h>

using namespace libport;

static bool die = false;
static const int NTHREAD = 10;
static const int NITER = 20;
std::vector<int> nCall;
static int targetId = 0;
libport::Condition cond;

namespace std
{
  static ostream&
  operator<<(ostream& o, const vector<int>& ms)
  {
    std::copy(ms.begin(), ms.end(), ostream_iterator<int>(o, " "));
    return o;
  }
}

static void cond_thread(int idx)
{
  while (!die)
  {
    BlockLock bl(cond);
    cond.wait();
    if (targetId == idx || targetId == -1)
      nCall[idx]++;
  }
}

static inline void clear()
{
  nCall.clear();
  nCall.resize(NTHREAD, 0);
}

static void test_condition_broadcast_one()
{
  std::vector<int> expect;
  clear();
  for (int i = 0; i < NTHREAD; i++)
    libport::startThread(boost::bind(&cond_thread, i));

  // Give time to those threads to reach the waiting-on-cond state
  usleep(200000);
  BOOST_TEST_MESSAGE("Singlethread broadcast with specific target");
  for (int i = 0; i < NITER; i++)
    for (int j = 0; j < NTHREAD; j++)
    {
      {
	BlockLock bl(cond);
	targetId = j;
	cond.broadcast();
      }
      // Give time to all threads to execute and wait.
      usleep(100000);
    }
  usleep(200000);

  expect.resize(NTHREAD, NITER);
  BOOST_CHECK_EQUAL(nCall, expect);
}

static void test_condition_broadcast_all()
{
  BOOST_TEST_MESSAGE("Singlethread broadcast without specific target");
  clear();
  targetId = -1;
  for (int i = 0; i < NITER; i++)
  {
    {
      BlockLock bl(cond);
      cond.broadcast();
    }
    //FIXME: a bit bogus, we have no waranty that all listener threads
    // will be back in the wait state, however this is what we test.
    usleep(100000);
  }
  usleep(200000);
  int sumHit = 0;
  foreach(int i, nCall)
    sumHit += i;
  BOOST_TEST_MESSAGE("Distribution: " << nCall);
  BOOST_CHECK_EQUAL(sumHit, NITER * NTHREAD);
}

static void test_condition_signal()
{
  BOOST_TEST_MESSAGE("singlethread signal without specific target");
  clear();
  targetId = -1;
  for (int i = 0; i < NITER * NTHREAD; ++i)
  {
    cond.signal();
    usleep(100000);
  }
  int sumHit = 0;
  foreach(int i, nCall)
    sumHit += i;
  BOOST_TEST_MESSAGE("Distribution: " << nCall);
  BOOST_CHECK_EQUAL(sumHit, NITER * NTHREAD);
}

test_suite*
init_test_suite()
{
  test_suite* suite = BOOST_TEST_SUITE("libport::condition");
  suite->add(BOOST_TEST_CASE(test_condition_broadcast_one));
  suite->add(BOOST_TEST_CASE(test_condition_broadcast_all));
  suite->add(BOOST_TEST_CASE(test_condition_signal));
  die = true;
  cond.broadcast();
  return suite;
}
<commit_msg>Make condition test deterministic.<commit_after>#include <vector>
#include <iostream>
#include <iterator>

#include <libport/condition.hh>
#include <libport/foreach.hh>
#include <libport/unit-test.hh>
#include <libport/thread.hh>
#include <libport/unistd.h>

using namespace libport;

static const int NTHREAD = 3;
static const int NITER = 3;
bool die = false;

namespace std
{
  static ostream&
  operator<<(ostream& o, const vector<int>& ms)
  {
    std::copy(ms.begin(), ms.end(), ostream_iterator<int>(o, " "));
    return o;
  }
}

static void cond_thread(int idx,
                        std::vector<int>& output,
                        int& targetId,
                        libport::Condition& cond,
                        libport::Semaphore& sem)
{
  BlockLock bl(cond);
  while (true)
  {
    cond.wait();
    if (targetId == idx || targetId == -1)
      output[idx]++;
    if (die)
    {
      sem++;
      break;
    }
    sem++;
  }
}

static void start_threads(std::vector<int>& output,
                          int& targetId,
                          libport::Condition& cond,
                          libport::Semaphore& sem)
{
  for (int i = 0; i < NTHREAD; i++)
    libport::startThread(boost::bind(&cond_thread, i,
                                     boost::ref(output),
                                     boost::ref(targetId),
                                     boost::ref(cond),
                                     boost::ref(sem)));
}

static void clear(libport::Condition& cond,
                  libport::Semaphore& sem)
{
  die = true;
  cond.broadcast();
  sem -= NTHREAD;
  die = false;
}

static void test_condition_broadcast_one()
{
  libport::Condition cond;
  libport::Semaphore sem;
  std::vector<int> output(NTHREAD, 0);
  int tgt = 0;
  start_threads(output, tgt, cond, sem);

  for (int i = 0; i < NITER; i++)
    for (int j = 0; j < NTHREAD; j++)
    {
      {
        BlockLock bl(cond);
        tgt = j;
        cond.broadcast();
      }
      sem -= NTHREAD;
    }

  std::vector<int> expect(NTHREAD, NITER);
  BOOST_CHECK_EQUAL(output, expect);
  clear(cond, sem);
}

static void test_condition_broadcast_all()
{
  libport::Condition cond;
  libport::Semaphore sem;
  std::vector<int> output(NTHREAD, 0);
  int tgt = -1;
  start_threads(output, tgt, cond, sem);

  for (int i = 0; i < NITER; i++)
  {
    {
      BlockLock bl(cond);
      cond.broadcast();
    }
    sem -= NTHREAD;
  }

  int sumHit = 0;
  foreach(int i, output)
    sumHit += i;
  BOOST_TEST_MESSAGE("Distribution: " << output);
  BOOST_CHECK_EQUAL(sumHit, NITER * NTHREAD);
  clear(cond, sem);
}

static void test_condition_signal()
{
  libport::Condition cond;
  libport::Semaphore sem;
  std::vector<int> output(NTHREAD, 0);
  int tgt = -1;
  start_threads(output, tgt, cond, sem);

  for (int i = 0; i < NITER * NTHREAD; ++i)
  {
    cond.signal();
    sem--;
  }

  int sumHit = 0;
  foreach(int i, output)
    sumHit += i;
  BOOST_TEST_MESSAGE("Distribution: " << output);
  BOOST_CHECK_EQUAL(sumHit, NITER * NTHREAD);
  clear(cond, sem);
}

test_suite*
init_test_suite()
{
  test_suite* suite = BOOST_TEST_SUITE("libport::condition");
  suite->add(BOOST_TEST_CASE(test_condition_broadcast_one));
  suite->add(BOOST_TEST_CASE(test_condition_broadcast_all));
  suite->add(BOOST_TEST_CASE(test_condition_signal));
  return suite;
}
<|endoftext|>


<commit_before>/* BEGIN_COMMON_COPYRIGHT_HEADER
 * (c)LGPL2+
 *
 * LXQt - a lightweight, Qt based, desktop toolset
 * http://razor-qt.org
 *
 * Copyright: 2012 Razor team
 * Authors:
 *   Alexander Sokoloff <sokoloff.a@gmail.com>
 *
 * This program or library is free software; you can redistribute it
 * and/or modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * 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., 51 Franklin Street, Fifth Floor,
 * Boston, MA 02110-1301 USA
 *
 * END_COMMON_COPYRIGHT_HEADER */

#include "lxqtgridlayout.h"
#include <QDebug>
#include <math.h>
#include <QWidget>
#include <QVariantAnimation>

using namespace LXQt;

namespace
{
    class ItemMoveAnimation : public QVariantAnimation
    {
    public:
        static void animate(QLayoutItem * item, QRect const & geometry)
        {
            ItemMoveAnimation* animation = new ItemMoveAnimation(item);
            animation->setStartValue(item->geometry());
            animation->setEndValue(geometry);
            animation->start(DeleteWhenStopped);
        }

        ItemMoveAnimation(QLayoutItem *item)
            : mItem(item)
        {
            setDuration(150);
        }

        void updateCurrentValue(const QVariant &current)
        {
            mItem->setGeometry(current.toRect());
        }

    private:
        QLayoutItem* mItem;

    };
}

class LXQt::GridLayoutPrivate
{
public:
    GridLayoutPrivate();

    QList<QLayoutItem*> mItems;
    int mRowCount;
    int mColumnCount;
    GridLayout::Direction mDirection;

    bool mIsValid;
    QSize mCellSizeHint;
    QSize mCellMaxSize;
    int mVisibleCount;
    GridLayout::Stretch mStretch;
    bool mAnimate;

    void updateCache();
    int rows() const;
    int cols() const;
    void setItemGeometry(QLayoutItem * item, QRect const & geometry);
    QSize mPrefCellMinSize;
    QSize mPrefCellMaxSize;
    QRect mOccupiedGeometry;
};

/************************************************

 ************************************************/
GridLayoutPrivate::GridLayoutPrivate()
{
    mColumnCount = 0;
    mRowCount = 0;
    mDirection = GridLayout::LeftToRight;
    mIsValid = false;
    mVisibleCount = 0;
    mStretch = GridLayout::StretchHorizontal | GridLayout::StretchVertical;
    mAnimate = false;
    mPrefCellMinSize = QSize(0,0);
    mPrefCellMaxSize = QSize(QWIDGETSIZE_MAX, QWIDGETSIZE_MAX);
}

/************************************************

 ************************************************/
void GridLayoutPrivate::updateCache()
{
    mCellSizeHint = QSize(0, 0);
    mCellMaxSize = QSize(0, 0);
    mVisibleCount = 0;

    for (int i=0; i<mItems.count(); ++i)
    {
        QLayoutItem *item = mItems.at(i);
        if (!item->widget() || item->widget()->isHidden())
            continue;

        int h = qBound(item->minimumSize().height(),
                       item->sizeHint().height(),
                       item->maximumSize().height());

        int w = qBound(item->minimumSize().width(),
                       item->sizeHint().width(),
                       item->maximumSize().width());

        mCellSizeHint.rheight() = qMax(mCellSizeHint.height(), h);
        mCellSizeHint.rwidth()  = qMax(mCellSizeHint.width(), w);

        mCellMaxSize.rheight() = qMax(mCellMaxSize.height(), item->maximumSize().height());
        mCellMaxSize.rwidth()  = qMax(mCellMaxSize.width(), item->maximumSize().width());
        mVisibleCount++;

#if 0
        qDebug() << "-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-";
        qDebug() << "item.min" << item->minimumSize().width();
        qDebug() << "item.sz " << item->sizeHint().width();
        qDebug() << "item.max" << item->maximumSize().width();
        qDebug() << "w h" << w << h;
        qDebug() << "wid.sizeHint" << item->widget()->sizeHint();
        qDebug() << "mCellSizeHint:" << mCellSizeHint;
        qDebug() << "mCellMaxSize: " << mCellMaxSize;
        qDebug() << "-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-";
#endif

    }
    mCellSizeHint.rwidth() = qBound(mPrefCellMinSize.width(),  mCellSizeHint.width(),  mPrefCellMaxSize.width());
    mCellSizeHint.rheight()= qBound(mPrefCellMinSize.height(), mCellSizeHint.height(), mPrefCellMaxSize.height());
    mIsValid = !mCellSizeHint.isEmpty();
}

/************************************************

 ************************************************/
int GridLayoutPrivate::rows() const
{
    if (mRowCount)
        return mRowCount;

    if (!mColumnCount)
        return 1;

    return ceil(mVisibleCount * 1.0 / mColumnCount);
}

/************************************************

 ************************************************/
int GridLayoutPrivate::cols() const
{
    if (mColumnCount)
        return mColumnCount;

    int rows = mRowCount;
    if (!rows)
        rows = 1;

    return ceil(mVisibleCount * 1.0 / rows);
}

void GridLayoutPrivate::setItemGeometry(QLayoutItem * item, QRect const & geometry)
{
    mOccupiedGeometry |= geometry;
    if (mAnimate)
    {
        ItemMoveAnimation::animate(item, geometry);
    } else
    {
        item->setGeometry(geometry);
    }
}

/************************************************

 ************************************************/
GridLayout::GridLayout(QWidget *parent):
    QLayout(parent),
    d_ptr(new GridLayoutPrivate())
{
}

/************************************************

 ************************************************/
GridLayout::~GridLayout()
{
    delete d_ptr;
}

/************************************************

 ************************************************/
void GridLayout::addItem(QLayoutItem *item)
{
    d_ptr->mItems.append(item);
}

/************************************************

 ************************************************/
QLayoutItem *GridLayout::itemAt(int index) const
{
    Q_D(const GridLayout);
    if (index < 0 || index >= d->mItems.count())
        return 0;

    return d->mItems.at(index);
}

/************************************************

 ************************************************/
QLayoutItem *GridLayout::takeAt(int index)
{
    Q_D(GridLayout);
    if (index < 0 || index >= d->mItems.count())
        return 0;

    QLayoutItem *item = d->mItems.takeAt(index);
    return item;
}

/************************************************

 ************************************************/
int GridLayout::count() const
{
    Q_D(const GridLayout);
    return d->mItems.count();
}

/************************************************

 ************************************************/
void GridLayout::invalidate()
{
    Q_D(GridLayout);
    d->mIsValid = false;
    QLayout::invalidate();
}

/************************************************

 ************************************************/
int GridLayout::rowCount() const
{
    Q_D(const GridLayout);
    return d->mRowCount;
}

/************************************************

 ************************************************/
void GridLayout::setRowCount(int value)
{
    Q_D(GridLayout);
    if (d->mRowCount != value)
    {
        d->mRowCount = value;
        invalidate();
    }
}

/************************************************

 ************************************************/
int GridLayout::columnCount() const
{
    Q_D(const GridLayout);
    return d->mColumnCount;
}

/************************************************

 ************************************************/
void GridLayout::setColumnCount(int value)
{
    Q_D(GridLayout);
    if (d->mColumnCount != value)
    {
        d->mColumnCount = value;
        invalidate();
    }
}

/************************************************

 ************************************************/
GridLayout::Direction GridLayout::direction() const
{
    Q_D(const GridLayout);
    return d->mDirection;
}

/************************************************

 ************************************************/
void GridLayout::setDirection(GridLayout::Direction value)
{
    Q_D(GridLayout);
    if (d->mDirection != value)
    {
        d->mDirection = value;
        invalidate();
    }
}

/************************************************

 ************************************************/
GridLayout::Stretch GridLayout::stretch() const
{
    Q_D(const GridLayout);
    return d->mStretch;
}

/************************************************

 ************************************************/
void GridLayout::setStretch(Stretch value)
{
    Q_D(GridLayout);
    if (d->mStretch != value)
    {
        d->mStretch = value;
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::moveItem(int from, int to, bool withAnimation /*= false*/)
{
    Q_D(GridLayout);
    d->mAnimate = withAnimation;
    d->mItems.move(from, to);
    invalidate();
}

/************************************************

 ************************************************/
QSize GridLayout::cellMinimumSize() const
{
    Q_D(const GridLayout);
    return d->mPrefCellMinSize;
}

/************************************************

 ************************************************/
void GridLayout::setCellMinimumSize(QSize minSize)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize != minSize)
    {
        d->mPrefCellMinSize = minSize;
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellMinimumHeight(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize.height() != value)
    {
        d->mPrefCellMinSize.setHeight(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellMinimumWidth(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize.width() != value)
    {
        d->mPrefCellMinSize.setWidth(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
QSize GridLayout::cellMaximumSize() const
{
    Q_D(const GridLayout);
    return d->mPrefCellMaxSize;
}

/************************************************

 ************************************************/
void GridLayout::setCellMaximumSize(QSize maxSize)
{
    Q_D(GridLayout);
    if (d->mPrefCellMaxSize != maxSize)
    {
        d->mPrefCellMaxSize = maxSize;
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellMaximumHeight(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMaxSize.height() != value)
    {
        d->mPrefCellMaxSize.setHeight(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellMaximumWidth(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMaxSize.width() != value)
    {
        d->mPrefCellMaxSize.setWidth(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellFixedSize(QSize size)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize != size ||
        d->mPrefCellMaxSize != size)
    {
        d->mPrefCellMinSize = size;
        d->mPrefCellMaxSize = size;
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellFixedHeight(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize.height() != value ||
        d->mPrefCellMaxSize.height() != value)
    {
        d->mPrefCellMinSize.setHeight(value);
        d->mPrefCellMaxSize.setHeight(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellFixedWidth(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize.width() != value ||
        d->mPrefCellMaxSize.width() != value)
    {
        d->mPrefCellMinSize.setWidth(value);
        d->mPrefCellMaxSize.setWidth(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
QSize GridLayout::sizeHint() const
{
    Q_D(const GridLayout);

    if (!d->mIsValid)
        const_cast<GridLayoutPrivate*>(d)->updateCache();

    return QSize(d->cols() * d->mCellSizeHint.width(),
                 d->rows() * d->mCellSizeHint.height());
}

/************************************************

 ************************************************/
void GridLayout::setGeometry(const QRect &geometry)
{
    Q_D(GridLayout);

    QLayout::setGeometry(geometry);
    d->mOccupiedGeometry.setTopLeft(geometry.topLeft());
    d->mOccupiedGeometry.setBottomRight(geometry.topLeft());

    if (!d->mIsValid)
        d->updateCache();

    int y = geometry.top();
    int x = geometry.left();

    // For historical reasons QRect::right returns left() + width() - 1
    // and QRect::bottom() returns top() + height() - 1;
    // So we use left() + height() and top() + height()
    //
    // http://qt-project.org/doc/qt-4.8/qrect.html

    const int maxX = geometry.left() + geometry.width();
    const int maxY = geometry.top() + geometry.height();

    const bool stretch_h = d->mStretch.testFlag(StretchHorizontal);
    const bool stretch_v = d->mStretch.testFlag(StretchVertical);

    const int cols = d->cols();
    int itemWidth = 0;
    if (stretch_h && 0 < cols)
        itemWidth = qMin(geometry.width() / cols, d->mCellMaxSize.width());
    else
        itemWidth = d->mCellSizeHint.width();
    itemWidth = qBound(qMin(d->mPrefCellMinSize.width(), maxX), itemWidth, d->mPrefCellMaxSize.width());
    const int widthRemain = stretch_h && 0 < itemWidth ? geometry.width() % itemWidth : 0;

    const int rows = d->rows();
    int itemHeight = 0;
    if (stretch_v && 0 < rows)
        itemHeight = qMin(geometry.height() / rows, d->mCellMaxSize.height());
    else
        itemHeight = d->mCellSizeHint.height();
    itemHeight = qBound(qMin(d->mPrefCellMinSize.height(), maxY), itemHeight, d->mPrefCellMaxSize.height());
    const int heightRemain = stretch_v && 0 < itemHeight ? geometry.height() % itemHeight : 0;

#if 0
    qDebug() << "** GridLayout::setGeometry *******************************";
    qDebug() << "Geometry:" << geometry;
    qDebug() << "CellSize:" << d->mCellSizeHint;
    qDebug() << "Constraints:" << "min" << d->mPrefCellMinSize << "max" << d->mPrefCellMaxSize;
    qDebug() << "Count" << count();
    qDebug() << "Cols:" << d->cols() << "(" << d->mColumnCount << ")";
    qDebug() << "Rows:" << d->rows() << "(" << d->mRowCount << ")";
    qDebug() << "Stretch:" << "h:" << (d->mStretch.testFlag(StretchHorizontal)) << " v:" << (d->mStretch.testFlag(StretchVertical));
    qDebug() << "Item:" << "h:" << itemHeight << " w:" << itemWidth;
#endif

    int remain_height = heightRemain;
    int remain_width = widthRemain;
    if (d->mDirection == LeftToRight)
    {
        int height = itemHeight + (0 < remain_height-- ? 1 : 0);
        foreach(QLayoutItem *item, d->mItems)
        {
            if (!item->widget() || item->widget()->isHidden())
                continue;
            int width = itemWidth + (0 < remain_width-- ? 1 : 0);

            if (x + width > maxX)
            {
                x = geometry.left();
                y += height;

                height = itemHeight + (0 < remain_height-- ? 1 : 0);
                remain_width = widthRemain;
            }

            d->setItemGeometry(item, QRect(x, y, width, height));
            x += width;
        }
    }
    else
    {
        int width = itemWidth + (0 < remain_width-- ? 1 : 0);
        foreach(QLayoutItem *item, d->mItems)
        {
            if (!item->widget() || item->widget()->isHidden())
                continue;
            int height = itemHeight + (0 < remain_height-- ? 1 : 0);

            if (y + height > maxY)
            {
                y = geometry.top();
                x += width;

                width = itemWidth + (0 < remain_width-- ? 1 : 0);
                remain_height = heightRemain;
            }
            d->setItemGeometry(item, QRect(x, y, width, height));
            y += height;
        }
    }
    d->mAnimate = false;
}

/************************************************

 ************************************************/
QRect GridLayout::occupiedGeometry() const
{
    return d_func()->mOccupiedGeometry;
}
<commit_msg>GridLayout: Fix memory leak<commit_after>/* BEGIN_COMMON_COPYRIGHT_HEADER
 * (c)LGPL2+
 *
 * LXQt - a lightweight, Qt based, desktop toolset
 * http://razor-qt.org
 *
 * Copyright: 2012 Razor team
 * Authors:
 *   Alexander Sokoloff <sokoloff.a@gmail.com>
 *
 * This program or library is free software; you can redistribute it
 * and/or modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * 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., 51 Franklin Street, Fifth Floor,
 * Boston, MA 02110-1301 USA
 *
 * END_COMMON_COPYRIGHT_HEADER */

#include "lxqtgridlayout.h"
#include <QDebug>
#include <math.h>
#include <QWidget>
#include <QVariantAnimation>

using namespace LXQt;

namespace
{
    class ItemMoveAnimation : public QVariantAnimation
    {
    public:
        static void animate(QLayoutItem * item, QRect const & geometry)
        {
            ItemMoveAnimation* animation = new ItemMoveAnimation(item);
            animation->setStartValue(item->geometry());
            animation->setEndValue(geometry);
            animation->start(DeleteWhenStopped);
        }

        ItemMoveAnimation(QLayoutItem *item)
            : mItem(item)
        {
            setDuration(150);
        }

        void updateCurrentValue(const QVariant &current)
        {
            mItem->setGeometry(current.toRect());
        }

    private:
        QLayoutItem* mItem;

    };
}

class LXQt::GridLayoutPrivate
{
public:
    GridLayoutPrivate();
    ~GridLayoutPrivate();

    QList<QLayoutItem*> mItems;
    int mRowCount;
    int mColumnCount;
    GridLayout::Direction mDirection;

    bool mIsValid;
    QSize mCellSizeHint;
    QSize mCellMaxSize;
    int mVisibleCount;
    GridLayout::Stretch mStretch;
    bool mAnimate;

    void updateCache();
    int rows() const;
    int cols() const;
    void setItemGeometry(QLayoutItem * item, QRect const & geometry);
    QSize mPrefCellMinSize;
    QSize mPrefCellMaxSize;
    QRect mOccupiedGeometry;
};

/************************************************

 ************************************************/
GridLayoutPrivate::GridLayoutPrivate()
{
    mColumnCount = 0;
    mRowCount = 0;
    mDirection = GridLayout::LeftToRight;
    mIsValid = false;
    mVisibleCount = 0;
    mStretch = GridLayout::StretchHorizontal | GridLayout::StretchVertical;
    mAnimate = false;
    mPrefCellMinSize = QSize(0,0);
    mPrefCellMaxSize = QSize(QWIDGETSIZE_MAX, QWIDGETSIZE_MAX);
}

/************************************************

 ************************************************/
GridLayoutPrivate::~GridLayoutPrivate()
{
    qDeleteAll(mItems);
}

/************************************************

 ************************************************/
void GridLayoutPrivate::updateCache()
{
    mCellSizeHint = QSize(0, 0);
    mCellMaxSize = QSize(0, 0);
    mVisibleCount = 0;

    for (int i=0; i<mItems.count(); ++i)
    {
        QLayoutItem *item = mItems.at(i);
        if (!item->widget() || item->widget()->isHidden())
            continue;

        int h = qBound(item->minimumSize().height(),
                       item->sizeHint().height(),
                       item->maximumSize().height());

        int w = qBound(item->minimumSize().width(),
                       item->sizeHint().width(),
                       item->maximumSize().width());

        mCellSizeHint.rheight() = qMax(mCellSizeHint.height(), h);
        mCellSizeHint.rwidth()  = qMax(mCellSizeHint.width(), w);

        mCellMaxSize.rheight() = qMax(mCellMaxSize.height(), item->maximumSize().height());
        mCellMaxSize.rwidth()  = qMax(mCellMaxSize.width(), item->maximumSize().width());
        mVisibleCount++;

#if 0
        qDebug() << "-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-";
        qDebug() << "item.min" << item->minimumSize().width();
        qDebug() << "item.sz " << item->sizeHint().width();
        qDebug() << "item.max" << item->maximumSize().width();
        qDebug() << "w h" << w << h;
        qDebug() << "wid.sizeHint" << item->widget()->sizeHint();
        qDebug() << "mCellSizeHint:" << mCellSizeHint;
        qDebug() << "mCellMaxSize: " << mCellMaxSize;
        qDebug() << "-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-";
#endif

    }
    mCellSizeHint.rwidth() = qBound(mPrefCellMinSize.width(),  mCellSizeHint.width(),  mPrefCellMaxSize.width());
    mCellSizeHint.rheight()= qBound(mPrefCellMinSize.height(), mCellSizeHint.height(), mPrefCellMaxSize.height());
    mIsValid = !mCellSizeHint.isEmpty();
}

/************************************************

 ************************************************/
int GridLayoutPrivate::rows() const
{
    if (mRowCount)
        return mRowCount;

    if (!mColumnCount)
        return 1;

    return ceil(mVisibleCount * 1.0 / mColumnCount);
}

/************************************************

 ************************************************/
int GridLayoutPrivate::cols() const
{
    if (mColumnCount)
        return mColumnCount;

    int rows = mRowCount;
    if (!rows)
        rows = 1;

    return ceil(mVisibleCount * 1.0 / rows);
}

void GridLayoutPrivate::setItemGeometry(QLayoutItem * item, QRect const & geometry)
{
    mOccupiedGeometry |= geometry;
    if (mAnimate)
    {
        ItemMoveAnimation::animate(item, geometry);
    } else
    {
        item->setGeometry(geometry);
    }
}

/************************************************

 ************************************************/
GridLayout::GridLayout(QWidget *parent):
    QLayout(parent),
    d_ptr(new GridLayoutPrivate())
{
}

/************************************************

 ************************************************/
GridLayout::~GridLayout()
{
    delete d_ptr;
}

/************************************************

 ************************************************/
void GridLayout::addItem(QLayoutItem *item)
{
    d_ptr->mItems.append(item);
}

/************************************************

 ************************************************/
QLayoutItem *GridLayout::itemAt(int index) const
{
    Q_D(const GridLayout);
    if (index < 0 || index >= d->mItems.count())
        return 0;

    return d->mItems.at(index);
}

/************************************************

 ************************************************/
QLayoutItem *GridLayout::takeAt(int index)
{
    Q_D(GridLayout);
    if (index < 0 || index >= d->mItems.count())
        return 0;

    QLayoutItem *item = d->mItems.takeAt(index);
    return item;
}

/************************************************

 ************************************************/
int GridLayout::count() const
{
    Q_D(const GridLayout);
    return d->mItems.count();
}

/************************************************

 ************************************************/
void GridLayout::invalidate()
{
    Q_D(GridLayout);
    d->mIsValid = false;
    QLayout::invalidate();
}

/************************************************

 ************************************************/
int GridLayout::rowCount() const
{
    Q_D(const GridLayout);
    return d->mRowCount;
}

/************************************************

 ************************************************/
void GridLayout::setRowCount(int value)
{
    Q_D(GridLayout);
    if (d->mRowCount != value)
    {
        d->mRowCount = value;
        invalidate();
    }
}

/************************************************

 ************************************************/
int GridLayout::columnCount() const
{
    Q_D(const GridLayout);
    return d->mColumnCount;
}

/************************************************

 ************************************************/
void GridLayout::setColumnCount(int value)
{
    Q_D(GridLayout);
    if (d->mColumnCount != value)
    {
        d->mColumnCount = value;
        invalidate();
    }
}

/************************************************

 ************************************************/
GridLayout::Direction GridLayout::direction() const
{
    Q_D(const GridLayout);
    return d->mDirection;
}

/************************************************

 ************************************************/
void GridLayout::setDirection(GridLayout::Direction value)
{
    Q_D(GridLayout);
    if (d->mDirection != value)
    {
        d->mDirection = value;
        invalidate();
    }
}

/************************************************

 ************************************************/
GridLayout::Stretch GridLayout::stretch() const
{
    Q_D(const GridLayout);
    return d->mStretch;
}

/************************************************

 ************************************************/
void GridLayout::setStretch(Stretch value)
{
    Q_D(GridLayout);
    if (d->mStretch != value)
    {
        d->mStretch = value;
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::moveItem(int from, int to, bool withAnimation /*= false*/)
{
    Q_D(GridLayout);
    d->mAnimate = withAnimation;
    d->mItems.move(from, to);
    invalidate();
}

/************************************************

 ************************************************/
QSize GridLayout::cellMinimumSize() const
{
    Q_D(const GridLayout);
    return d->mPrefCellMinSize;
}

/************************************************

 ************************************************/
void GridLayout::setCellMinimumSize(QSize minSize)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize != minSize)
    {
        d->mPrefCellMinSize = minSize;
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellMinimumHeight(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize.height() != value)
    {
        d->mPrefCellMinSize.setHeight(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellMinimumWidth(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize.width() != value)
    {
        d->mPrefCellMinSize.setWidth(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
QSize GridLayout::cellMaximumSize() const
{
    Q_D(const GridLayout);
    return d->mPrefCellMaxSize;
}

/************************************************

 ************************************************/
void GridLayout::setCellMaximumSize(QSize maxSize)
{
    Q_D(GridLayout);
    if (d->mPrefCellMaxSize != maxSize)
    {
        d->mPrefCellMaxSize = maxSize;
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellMaximumHeight(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMaxSize.height() != value)
    {
        d->mPrefCellMaxSize.setHeight(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellMaximumWidth(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMaxSize.width() != value)
    {
        d->mPrefCellMaxSize.setWidth(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellFixedSize(QSize size)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize != size ||
        d->mPrefCellMaxSize != size)
    {
        d->mPrefCellMinSize = size;
        d->mPrefCellMaxSize = size;
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellFixedHeight(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize.height() != value ||
        d->mPrefCellMaxSize.height() != value)
    {
        d->mPrefCellMinSize.setHeight(value);
        d->mPrefCellMaxSize.setHeight(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
void GridLayout::setCellFixedWidth(int value)
{
    Q_D(GridLayout);
    if (d->mPrefCellMinSize.width() != value ||
        d->mPrefCellMaxSize.width() != value)
    {
        d->mPrefCellMinSize.setWidth(value);
        d->mPrefCellMaxSize.setWidth(value);
        invalidate();
    }
}

/************************************************

 ************************************************/
QSize GridLayout::sizeHint() const
{
    Q_D(const GridLayout);

    if (!d->mIsValid)
        const_cast<GridLayoutPrivate*>(d)->updateCache();

    return QSize(d->cols() * d->mCellSizeHint.width(),
                 d->rows() * d->mCellSizeHint.height());
}

/************************************************

 ************************************************/
void GridLayout::setGeometry(const QRect &geometry)
{
    Q_D(GridLayout);

    QLayout::setGeometry(geometry);
    d->mOccupiedGeometry.setTopLeft(geometry.topLeft());
    d->mOccupiedGeometry.setBottomRight(geometry.topLeft());

    if (!d->mIsValid)
        d->updateCache();

    int y = geometry.top();
    int x = geometry.left();

    // For historical reasons QRect::right returns left() + width() - 1
    // and QRect::bottom() returns top() + height() - 1;
    // So we use left() + height() and top() + height()
    //
    // http://qt-project.org/doc/qt-4.8/qrect.html

    const int maxX = geometry.left() + geometry.width();
    const int maxY = geometry.top() + geometry.height();

    const bool stretch_h = d->mStretch.testFlag(StretchHorizontal);
    const bool stretch_v = d->mStretch.testFlag(StretchVertical);

    const int cols = d->cols();
    int itemWidth = 0;
    if (stretch_h && 0 < cols)
        itemWidth = qMin(geometry.width() / cols, d->mCellMaxSize.width());
    else
        itemWidth = d->mCellSizeHint.width();
    itemWidth = qBound(qMin(d->mPrefCellMinSize.width(), maxX), itemWidth, d->mPrefCellMaxSize.width());
    const int widthRemain = stretch_h && 0 < itemWidth ? geometry.width() % itemWidth : 0;

    const int rows = d->rows();
    int itemHeight = 0;
    if (stretch_v && 0 < rows)
        itemHeight = qMin(geometry.height() / rows, d->mCellMaxSize.height());
    else
        itemHeight = d->mCellSizeHint.height();
    itemHeight = qBound(qMin(d->mPrefCellMinSize.height(), maxY), itemHeight, d->mPrefCellMaxSize.height());
    const int heightRemain = stretch_v && 0 < itemHeight ? geometry.height() % itemHeight : 0;

#if 0
    qDebug() << "** GridLayout::setGeometry *******************************";
    qDebug() << "Geometry:" << geometry;
    qDebug() << "CellSize:" << d->mCellSizeHint;
    qDebug() << "Constraints:" << "min" << d->mPrefCellMinSize << "max" << d->mPrefCellMaxSize;
    qDebug() << "Count" << count();
    qDebug() << "Cols:" << d->cols() << "(" << d->mColumnCount << ")";
    qDebug() << "Rows:" << d->rows() << "(" << d->mRowCount << ")";
    qDebug() << "Stretch:" << "h:" << (d->mStretch.testFlag(StretchHorizontal)) << " v:" << (d->mStretch.testFlag(StretchVertical));
    qDebug() << "Item:" << "h:" << itemHeight << " w:" << itemWidth;
#endif

    int remain_height = heightRemain;
    int remain_width = widthRemain;
    if (d->mDirection == LeftToRight)
    {
        int height = itemHeight + (0 < remain_height-- ? 1 : 0);
        foreach(QLayoutItem *item, d->mItems)
        {
            if (!item->widget() || item->widget()->isHidden())
                continue;
            int width = itemWidth + (0 < remain_width-- ? 1 : 0);

            if (x + width > maxX)
            {
                x = geometry.left();
                y += height;

                height = itemHeight + (0 < remain_height-- ? 1 : 0);
                remain_width = widthRemain;
            }

            d->setItemGeometry(item, QRect(x, y, width, height));
            x += width;
        }
    }
    else
    {
        int width = itemWidth + (0 < remain_width-- ? 1 : 0);
        foreach(QLayoutItem *item, d->mItems)
        {
            if (!item->widget() || item->widget()->isHidden())
                continue;
            int height = itemHeight + (0 < remain_height-- ? 1 : 0);

            if (y + height > maxY)
            {
                y = geometry.top();
                x += width;

                width = itemWidth + (0 < remain_width-- ? 1 : 0);
                remain_height = heightRemain;
            }
            d->setItemGeometry(item, QRect(x, y, width, height));
            y += height;
        }
    }
    d->mAnimate = false;
}

/************************************************

 ************************************************/
QRect GridLayout::occupiedGeometry() const
{
    return d_func()->mOccupiedGeometry;
}
<|endoftext|>


<commit_before>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: globalx.cxx,v $
 *
 *  $Revision: 1.9 $
 *
 *  last change: $Author: rt $ $Date: 2005-09-08 18:26:23 $
 *
 *  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
 *
 ************************************************************************/

#include "callform.hxx"
#include "global.hxx"

#ifndef _URLOBJ_HXX
#include <tools/urlobj.hxx>
#endif
#ifndef _UCBHELPER_CONTENTBROKER_HXX
#include <ucbhelper/contentbroker.hxx>
#endif
#ifndef _UCBHELPER_CONTENT_HXX
#include <ucbhelper/content.hxx>
#endif
#ifndef _UNOTOOLS_LOCALFILEHELPER_HXX
#include <unotools/localfilehelper.hxx>
#endif

#include <tools/debug.hxx>
#include <svtools/pathoptions.hxx>

#include <com/sun/star/sdbc/XResultSet.hpp>
#include <com/sun/star/sdbc/XRow.hpp>
#include <com/sun/star/ucb/XCommandEnvironment.hpp>
#include <com/sun/star/ucb/XContentAccess.hpp>

#pragma hdrstop

using namespace ::com::sun::star;
using namespace ::com::sun::star::uno;
using namespace ::com::sun::star::ucb;

// static
void ScGlobal::InitAddIns()
{
    // multi paths separated by semicolons
    SvtPathOptions aPathOpt;
    String aMultiPath = aPathOpt.GetAddinPath();
    if ( aMultiPath.Len() > 0 )
    {
        xub_StrLen nTokens = aMultiPath.GetTokenCount( ';' );
        xub_StrLen nIndex = 0;
        for ( xub_StrLen j=0; j<nTokens; j++ )
        {
            String aPath( aMultiPath.GetToken( 0, ';', nIndex ) );
            if ( aPath.Len() > 0 )
            {
                //  use LocalFileHelper to convert the path to a URL that always points
                //  to the file on the server
                String aUrl;
                if ( utl::LocalFileHelper::ConvertPhysicalNameToURL( aPath, aUrl ) )
                    aPath = aUrl;

                INetURLObject aObj;
                aObj.SetSmartURL( aPath );
                aObj.setFinalSlash();
                try
                {
                    ::ucb::Content aCnt( aObj.GetMainURL(INetURLObject::NO_DECODE),
                        Reference< XCommandEnvironment > () );
                    Reference< sdbc::XResultSet > xResultSet;
                    Sequence< rtl::OUString > aProps;
                    try
                    {
                        xResultSet = aCnt.createCursor(
                            aProps, ::ucb::INCLUDE_DOCUMENTS_ONLY );
                    }
                    catch ( Exception& )
                    {
                        // ucb may throw different exceptions on failure now
                        // no assertion if AddIn directory doesn't exist
                    }

                    if ( xResultSet.is() )
                    {
                        Reference< sdbc::XRow > xRow( xResultSet, UNO_QUERY );
                        Reference< XContentAccess >
                            xContentAccess( xResultSet, UNO_QUERY );
                        try
                        {
                            if ( xResultSet->first() )
                            {
                                do
                                {
#if SUPD>611
                                    rtl::OUString aId( xContentAccess->queryContentIdentifierString() );
#else
                                    rtl::OUString aId( xContentAccess->queryContentIdentfierString() );
#endif
                                    InitExternalFunc( aId );
                                }
                                while ( xResultSet->next() );
                            }
                        }
                        catch ( Exception& )
                        {
                            DBG_ERRORFILE( "ResultSetException catched!" );
                        }
                    }
                }
                catch ( Exception& )
                {
                    DBG_ERRORFILE( "Exception catched!" );
                }
                catch ( ... )
                {

                    DBG_ERRORFILE( "unexpected exception caught!" );
                }
            }
        }
    }
}

<commit_msg>INTEGRATION: CWS pchfix01 (1.9.216); FILE MERGED 2006/07/12 10:01:34 kaib 1.9.216.1: #i67080# Converted cxx files in sc, added initial project level pch and stripped old PCH definitions.<commit_after>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: globalx.cxx,v $
 *
 *  $Revision: 1.10 $
 *
 *  last change: $Author: kz $ $Date: 2006-07-21 11:05:48 $
 *
 *  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_sc.hxx"

#include "callform.hxx"
#include "global.hxx"

#ifndef _URLOBJ_HXX
#include <tools/urlobj.hxx>
#endif
#ifndef _UCBHELPER_CONTENTBROKER_HXX
#include <ucbhelper/contentbroker.hxx>
#endif
#ifndef _UCBHELPER_CONTENT_HXX
#include <ucbhelper/content.hxx>
#endif
#ifndef _UNOTOOLS_LOCALFILEHELPER_HXX
#include <unotools/localfilehelper.hxx>
#endif

#include <tools/debug.hxx>
#include <svtools/pathoptions.hxx>

#include <com/sun/star/sdbc/XResultSet.hpp>
#include <com/sun/star/sdbc/XRow.hpp>
#include <com/sun/star/ucb/XCommandEnvironment.hpp>
#include <com/sun/star/ucb/XContentAccess.hpp>

using namespace ::com::sun::star;
using namespace ::com::sun::star::uno;
using namespace ::com::sun::star::ucb;

// static
void ScGlobal::InitAddIns()
{
    // multi paths separated by semicolons
    SvtPathOptions aPathOpt;
    String aMultiPath = aPathOpt.GetAddinPath();
    if ( aMultiPath.Len() > 0 )
    {
        xub_StrLen nTokens = aMultiPath.GetTokenCount( ';' );
        xub_StrLen nIndex = 0;
        for ( xub_StrLen j=0; j<nTokens; j++ )
        {
            String aPath( aMultiPath.GetToken( 0, ';', nIndex ) );
            if ( aPath.Len() > 0 )
            {
                //  use LocalFileHelper to convert the path to a URL that always points
                //  to the file on the server
                String aUrl;
                if ( utl::LocalFileHelper::ConvertPhysicalNameToURL( aPath, aUrl ) )
                    aPath = aUrl;

                INetURLObject aObj;
                aObj.SetSmartURL( aPath );
                aObj.setFinalSlash();
                try
                {
                    ::ucb::Content aCnt( aObj.GetMainURL(INetURLObject::NO_DECODE),
                        Reference< XCommandEnvironment > () );
                    Reference< sdbc::XResultSet > xResultSet;
                    Sequence< rtl::OUString > aProps;
                    try
                    {
                        xResultSet = aCnt.createCursor(
                            aProps, ::ucb::INCLUDE_DOCUMENTS_ONLY );
                    }
                    catch ( Exception& )
                    {
                        // ucb may throw different exceptions on failure now
                        // no assertion if AddIn directory doesn't exist
                    }

                    if ( xResultSet.is() )
                    {
                        Reference< sdbc::XRow > xRow( xResultSet, UNO_QUERY );
                        Reference< XContentAccess >
                            xContentAccess( xResultSet, UNO_QUERY );
                        try
                        {
                            if ( xResultSet->first() )
                            {
                                do
                                {
#if SUPD>611
                                    rtl::OUString aId( xContentAccess->queryContentIdentifierString() );
#else
                                    rtl::OUString aId( xContentAccess->queryContentIdentfierString() );
#endif
                                    InitExternalFunc( aId );
                                }
                                while ( xResultSet->next() );
                            }
                        }
                        catch ( Exception& )
                        {
                            DBG_ERRORFILE( "ResultSetException catched!" );
                        }
                    }
                }
                catch ( Exception& )
                {
                    DBG_ERRORFILE( "Exception catched!" );
                }
                catch ( ... )
                {

                    DBG_ERRORFILE( "unexpected exception caught!" );
                }
            }
        }
    }
}

<|endoftext|>


<commit_before><commit_msg>Antialiasing on Grid<commit_after><|endoftext|>


<commit_before>/*************************************************************************
 *
 *  $RCSfile: xelink.hxx,v $
 *
 *  $Revision: 1.6 $
 *
 *  last change: $Author: rt $ $Date: 2004-03-02 09:43:22 $
 *
 *  The Contents of this file are made available subject to the terms of
 *  either of the following licenses
 *
 *         - GNU Lesser General Public License Version 2.1
 *         - Sun Industry Standards Source License Version 1.1
 *
 *  Sun Microsystems Inc., October, 2000
 *
 *  GNU Lesser General Public License Version 2.1
 *  =============================================
 *  Copyright 2000 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
 *
 *
 *  Sun Industry Standards Source License Version 1.1
 *  =================================================
 *  The contents of this file are subject to the Sun Industry Standards
 *  Source License Version 1.1 (the "License"); You may not use this file
 *  except in compliance with the License. You may obtain a copy of the
 *  License at http://www.openoffice.org/license.html.
 *
 *  Software provided under this License is provided on an "AS IS" basis,
 *  WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
 *  WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
 *  MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
 *  See the License for the specific provisions governing your rights and
 *  obligations concerning the Software.
 *
 *  The Initial Developer of the Original Code is: Sun Microsystems, Inc.
 *
 *  Copyright: 2000 by Sun Microsystems, Inc.
 *
 *  All Rights Reserved.
 *
 *  Contributor(s): _______________________________________
 *
 *
 ************************************************************************/

#ifndef SC_XELINK_HXX
#define SC_XELINK_HXX

#ifndef SC_MARKDATA_HXX
#include "markdata.hxx"
#endif

#ifndef SC_XLLINK_HXX
#include "xllink.hxx"
#endif
#ifndef SC_XEHELPER_HXX
#include "xehelper.hxx"
#endif
#ifndef SC_XERECORD_HXX
#include "xerecord.hxx"
#endif

class ScRange;
struct SingleRefData;

/* ============================================================================
Classes for export of different kinds of internal/external references.
- 3D cell and cell range links
- External cell and cell range links
- Internal and external defined names
- Add-in functions
- DDE links
- OLE object links
============================================================================ */

// Excel sheet indexes ========================================================

typedef ::std::pair< sal_uInt16, sal_uInt16 >   XclExpRefLogEntry;
typedef ::std::vector< XclExpRefLogEntry >      XclExpRefLogVec;

/** Stores the correct Excel sheet index for each Calc sheet.
    @descr  The class knows all sheets which will not exported
    (i.e. external link sheets, scenario sheets). */
class XclExpTabInfo
{
public:
    /** Initializes the complete buffer from the current exported document. */
    explicit                    XclExpTabInfo( const XclExpRoot& rRoot );

    /** Returns true, if the specified Calc sheet will be exported. */
    bool                        IsExportTab( USHORT nScTab ) const;
    /** Returns true, if the specified Calc sheet is used to store external cell contents. */
    bool                        IsExternalTab( USHORT nScTab ) const;
    /** Returns true, if the specified Calc sheet is visible and will be exported. */
    bool                        IsVisibleTab( USHORT nScTab ) const;
    /** Returns true, if the specified Calc sheet is selected and will be exported. */
    bool                        IsSelectedTab( USHORT nScTab ) const;
    /** Returns true, if the specified Calc sheet is the active displayed sheet. */
    bool                        IsActiveTab( USHORT nScTab ) const;

    /** Returns the Excel sheet index for a given Calc sheet. */
    sal_uInt16                  GetXclTab( USHORT nScTab ) const;

    /** Returns the Calc sheet index of the nSortedTab-th entry in the sorted sheet names list. */
    USHORT                      GetRealScTab( USHORT nSortedTab ) const;
    /** Returns the index of the passed Calc sheet in the sorted sheet names list. */
    USHORT                      GetSortedScTab( USHORT nScTab ) const;

    /** Returns the number of Calc sheets. */
    inline USHORT               GetScTabCount() const { return mnScCnt; }

    /** Returns the number of Excel sheets to be exported. */
    inline sal_uInt16           GetXclTabCount() const { return mnXclCnt; }
    /** Returns the number of external linked sheets. */
    inline sal_uInt16           GetXclExtTabCount() const { return mnXclExtCnt; }
    /** Returns the number of codepages (VBA modules). */
    inline sal_uInt16           GetXclCodenameCount() const { return mnXclCodeCnt; }
    /** Returns the number of exported selected sheets. */
    inline sal_uInt16           GetXclSelectedCount() const { return mnXclSelected; }

    /** Returns the Excel index of the active, displayed sheet. */
    inline sal_uInt16           GetXclActiveTab() const { return mnXclActive; }
    /** Returns the Excel index of the first visible sheet. */
    inline sal_uInt16           GetXclFirstVisTab() const { return mnXclFirstVis; }

    // *** for change tracking ***

    /** Enables logging of Excel sheet indexes in each 3D-reference. */
    void                        StartRefLog();
    /** Appends sheet index pair (called by formula compiler). */
    void                        AppendTabRef( sal_uInt16 nXclFirst, sal_uInt16 nXclLast );
    /** Disables logging of Excel sheet indexes. */
    const XclExpRefLogVec&      EndRefLog();

private:
    /** Returns true, if any of the passed flags is set for the specified Calc sheet. */
    bool                        GetFlag( USHORT nScTab, sal_uInt8 nFlags ) const;
    /** Sets or clears (depending on bSet) all passed flags for the specified Calc sheet. */
    void                        SetFlag( USHORT nScTab, sal_uInt8 nFlags, bool bSet = true );

    /** Searches for sheets not to be exported. */
    void                        CalcXclIndexes();
    /** Sorts the names of all tables and stores the indexes of the sorted indexes. */
    void                        CalcSortedIndexes( ScDocument& rDoc );

private:
    typedef ::std::pair< sal_uInt16, sal_uInt8 >    ScTabInfoEntry;
    typedef ::std::vector< ScTabInfoEntry >         ScTabInfoVec;

    ScTabInfoVec                maTabInfoVec;       /// Array of Calc sheet index information.

    USHORT                      mnScCnt;            /// Count of Calc sheets.
    sal_uInt16                  mnXclCnt;           /// Count of Excel sheets to be exported.
    sal_uInt16                  mnXclExtCnt;        /// Count of external link sheets.
    sal_uInt16                  mnXclCodeCnt;       /// Count of codepages.
    sal_uInt16                  mnXclSelected;      /// Count of selected and exported sheets.
    sal_uInt16                  mnXclActive;        /// Active (selected) sheet.
    sal_uInt16                  mnXclFirstVis;      /// First visible sheet.

    ScfUInt16Vec                maFromSortedVec;    /// Sorted index -> real index.
    ScfUInt16Vec                maToSortedVec;      /// Real index -> sorted index.

    XclExpRefLogVec             maRefLog;           /// A log for each requested Excel sheet index.
    bool                        mbEnableLog;        /// true = log all sheet indexes (for formula compiler).
};

// Export link manager ========================================================

class XclExpLinkManager_Impl;

/** Stores all data for internal/external references (the link table).
    @descr  Contents in BIFF8:
    - Record SUPBOOK: Contains the name of an external workbook and the names of its sheets.
        This record is followed by EXTERNNAME, XCT and CRN records.
    - Record XCT: Contains the sheet index of the following CRN records.
    - Record CRN: Contains addresses (row and column) and values of external referenced cells.
    - Record NAME: Contains defined names of the own workbook. This record follows the
        EXTERNSHEET record.
    - Record EXTERNNAME: Contains external defined names or DDE links or OLE object links.
    - Record EXTERNSHEET: Contains indexes to URLs of external documents (SUPBOOKs)
        and sheet indexes for each external reference used anywhere in the workbook.
        This record follows a list of SUPBOOK records (it is the last record of the link table).
*/
class XclExpLinkManager : public XclExpRecordBase
{
public:
    explicit                    XclExpLinkManager( const XclExpRoot& rRoot );
    virtual                     ~XclExpLinkManager();

    /** Searches for XTI structure with the given Excel sheet range. Adds new XTI if not found.
        @return  The list index of the XTI structure. */
    sal_uInt16                  FindXti( sal_uInt16 nXclFirst, sal_uInt16 nXclLast );

    /** Returns the external document URL of the specified Excel sheet. */
    const XclExpString*         GetUrl( sal_uInt16 nXclTab ) const;
    /** Returns the external sheet name of the specified Excel sheet. */
    const XclExpString*         GetTabName( sal_uInt16 nXclTab ) const;

    /** Stores the cell with the given address in a CRN record list. */
    void                        StoreCell( const SingleRefData& rRef );
    /** Stores all cells in the given range in a CRN record list. */
    void                        StoreCellRange( const SingleRefData& rRef1, const SingleRefData& rRef2 );

    /** Finds or inserts an EXTERNNAME record for an add-in function name.
        @param rnXti  Returns the index of the XTI structure which contains the add-in function name.
        @param rnExtName  Returns the 1-based EXTERNNAME record index. */
    void                        InsertAddIn(
                                    sal_uInt16& rnXti, sal_uInt16& rnExtName,
                                    const String& rName );
    /** Finds or inserts an EXTERNNAME record for DDE links.
        @param rnXti  Returns the index of the XTI structure which contains the DDE link.
        @param rnExtName  Returns the 1-based EXTERNNAME record index. */
    bool                        InsertDde(
                                    sal_uInt16& rnXti, sal_uInt16& rnExtName,
                                    const String& rApplic, const String& rTopic, const String& rItem );

    /** Writes the entire Link table. */
    virtual void                Save( XclExpStream& rStrm );

private:
    typedef ::std::auto_ptr< XclExpLinkManager_Impl > XclExpLinkManager_ImplPtr;
    XclExpLinkManager_ImplPtr   mpImpl;
};

// ============================================================================

#endif

<commit_msg>INTEGRATION: CWS rowlimit (1.6.18); FILE MERGED 2004/03/19 17:10:44 er 1.6.18.3: #i1967# type correctness 2004/03/19 13:47:11 er 1.6.18.2: #i1967# type correctness 2004/03/19 12:15:36 jmarmion 1.6.18.1: #i1967# step 5 changes.<commit_after>/*************************************************************************
 *
 *  $RCSfile: xelink.hxx,v $
 *
 *  $Revision: 1.7 $
 *
 *  last change: $Author: obo $ $Date: 2004-06-04 10:59:08 $
 *
 *  The Contents of this file are made available subject to the terms of
 *  either of the following licenses
 *
 *         - GNU Lesser General Public License Version 2.1
 *         - Sun Industry Standards Source License Version 1.1
 *
 *  Sun Microsystems Inc., October, 2000
 *
 *  GNU Lesser General Public License Version 2.1
 *  =============================================
 *  Copyright 2000 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
 *
 *
 *  Sun Industry Standards Source License Version 1.1
 *  =================================================
 *  The contents of this file are subject to the Sun Industry Standards
 *  Source License Version 1.1 (the "License"); You may not use this file
 *  except in compliance with the License. You may obtain a copy of the
 *  License at http://www.openoffice.org/license.html.
 *
 *  Software provided under this License is provided on an "AS IS" basis,
 *  WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
 *  WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
 *  MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
 *  See the License for the specific provisions governing your rights and
 *  obligations concerning the Software.
 *
 *  The Initial Developer of the Original Code is: Sun Microsystems, Inc.
 *
 *  Copyright: 2000 by Sun Microsystems, Inc.
 *
 *  All Rights Reserved.
 *
 *  Contributor(s): _______________________________________
 *
 *
 ************************************************************************/

#ifndef SC_XELINK_HXX
#define SC_XELINK_HXX

#ifndef SC_MARKDATA_HXX
#include "markdata.hxx"
#endif

#ifndef SC_XLLINK_HXX
#include "xllink.hxx"
#endif
#ifndef SC_XEHELPER_HXX
#include "xehelper.hxx"
#endif
#ifndef SC_XERECORD_HXX
#include "xerecord.hxx"
#endif

class ScRange;
struct SingleRefData;

/* ============================================================================
Classes for export of different kinds of internal/external references.
- 3D cell and cell range links
- External cell and cell range links
- Internal and external defined names
- Add-in functions
- DDE links
- OLE object links
============================================================================ */

// Excel sheet indexes ========================================================

typedef ::std::pair< sal_uInt16, sal_uInt16 >   XclExpRefLogEntry;
typedef ::std::vector< XclExpRefLogEntry >      XclExpRefLogVec;

/** Stores the correct Excel sheet index for each Calc sheet.
    @descr  The class knows all sheets which will not exported
    (i.e. external link sheets, scenario sheets). */
class XclExpTabInfo
{
public:
    /** Initializes the complete buffer from the current exported document. */
    explicit                    XclExpTabInfo( const XclExpRoot& rRoot );

    /** Returns true, if the specified Calc sheet will be exported. */
    bool                        IsExportTab( SCTAB nScTab ) const;
    /** Returns true, if the specified Calc sheet is used to store external cell contents. */
    bool                        IsExternalTab( SCTAB nScTab ) const;
    /** Returns true, if the specified Calc sheet is visible and will be exported. */
    bool                        IsVisibleTab( SCTAB nScTab ) const;
    /** Returns true, if the specified Calc sheet is selected and will be exported. */
    bool                        IsSelectedTab( SCTAB nScTab ) const;
    /** Returns true, if the specified Calc sheet is the active displayed sheet. */
    bool                        IsActiveTab( SCTAB nScTab ) const;

    /** Returns the Excel sheet index for a given Calc sheet. */
    sal_uInt16                  GetXclTab( SCTAB nScTab ) const;

    /** Returns the Calc sheet index of the nSortedTab-th entry in the sorted sheet names list. */
    SCTAB                       GetRealScTab( sal_uInt16 nSortedTab ) const;
    /** Returns the index of the passed Calc sheet in the sorted sheet names list. */
    sal_uInt16                  GetSortedScTab( SCTAB nScTab ) const;

    /** Returns the number of Calc sheets. */
    inline SCTAB               GetScTabCount() const { return mnScCnt; }

    /** Returns the number of Excel sheets to be exported. */
    inline sal_uInt16           GetXclTabCount() const { return mnXclCnt; }
    /** Returns the number of external linked sheets. */
    inline sal_uInt16           GetXclExtTabCount() const { return mnXclExtCnt; }
    /** Returns the number of codepages (VBA modules). */
    inline sal_uInt16           GetXclCodenameCount() const { return mnXclCodeCnt; }
    /** Returns the number of exported selected sheets. */
    inline sal_uInt16           GetXclSelectedCount() const { return mnXclSelected; }

    /** Returns the Excel index of the active, displayed sheet. */
    inline sal_uInt16           GetXclActiveTab() const { return mnXclActive; }
    /** Returns the Excel index of the first visible sheet. */
    inline sal_uInt16           GetXclFirstVisTab() const { return mnXclFirstVis; }

    // *** for change tracking ***

    /** Enables logging of Excel sheet indexes in each 3D-reference. */
    void                        StartRefLog();
    /** Appends sheet index pair (called by formula compiler). */
    void                        AppendTabRef( sal_uInt16 nXclFirst, sal_uInt16 nXclLast );
    /** Disables logging of Excel sheet indexes. */
    const XclExpRefLogVec&      EndRefLog();

private:
    /** Returns true, if any of the passed flags is set for the specified Calc sheet. */
    bool                        GetFlag( SCTAB nScTab, sal_uInt8 nFlags ) const;
    /** Sets or clears (depending on bSet) all passed flags for the specified Calc sheet. */
    void                        SetFlag( SCTAB nScTab, sal_uInt8 nFlags, bool bSet = true );

    /** Searches for sheets not to be exported. */
    void                        CalcXclIndexes();
    /** Sorts the names of all tables and stores the indexes of the sorted indexes. */
    void                        CalcSortedIndexes( ScDocument& rDoc );

private:
    typedef ::std::pair< sal_uInt16, sal_uInt8 >    ScTabInfoEntry;
    typedef ::std::vector< ScTabInfoEntry >         ScTabInfoVec;

    ScTabInfoVec                maTabInfoVec;       /// Array of Calc sheet index information.

    SCTAB                       mnScCnt;            /// Count of Calc sheets.
    sal_uInt16                  mnXclCnt;           /// Count of Excel sheets to be exported.
    sal_uInt16                  mnXclExtCnt;        /// Count of external link sheets.
    sal_uInt16                  mnXclCodeCnt;       /// Count of codepages.
    sal_uInt16                  mnXclSelected;      /// Count of selected and exported sheets.
    sal_uInt16                  mnXclActive;        /// Active (selected) sheet.
    sal_uInt16                  mnXclFirstVis;      /// First visible sheet.

    ScfUInt16Vec                maFromSortedVec;    /// Sorted index -> real index.
    ScfUInt16Vec                maToSortedVec;      /// Real index -> sorted index.

    XclExpRefLogVec             maRefLog;           /// A log for each requested Excel sheet index.
    bool                        mbEnableLog;        /// true = log all sheet indexes (for formula compiler).
};

// Export link manager ========================================================

class XclExpLinkManager_Impl;

/** Stores all data for internal/external references (the link table).
    @descr  Contents in BIFF8:
    - Record SUPBOOK: Contains the name of an external workbook and the names of its sheets.
        This record is followed by EXTERNNAME, XCT and CRN records.
    - Record XCT: Contains the sheet index of the following CRN records.
    - Record CRN: Contains addresses (row and column) and values of external referenced cells.
    - Record NAME: Contains defined names of the own workbook. This record follows the
        EXTERNSHEET record.
    - Record EXTERNNAME: Contains external defined names or DDE links or OLE object links.
    - Record EXTERNSHEET: Contains indexes to URLs of external documents (SUPBOOKs)
        and sheet indexes for each external reference used anywhere in the workbook.
        This record follows a list of SUPBOOK records (it is the last record of the link table).
*/
class XclExpLinkManager : public XclExpRecordBase
{
public:
    explicit                    XclExpLinkManager( const XclExpRoot& rRoot );
    virtual                     ~XclExpLinkManager();

    /** Searches for XTI structure with the given Excel sheet range. Adds new XTI if not found.
        @return  The list index of the XTI structure. */
    sal_uInt16                  FindXti( sal_uInt16 nXclFirst, sal_uInt16 nXclLast );

    /** Returns the external document URL of the specified Excel sheet. */
    const XclExpString*         GetUrl( sal_uInt16 nXclTab ) const;
    /** Returns the external sheet name of the specified Excel sheet. */
    const XclExpString*         GetTabName( sal_uInt16 nXclTab ) const;

    /** Stores the cell with the given address in a CRN record list. */
    void                        StoreCell( const SingleRefData& rRef );
    /** Stores all cells in the given range in a CRN record list. */
    void                        StoreCellRange( const SingleRefData& rRef1, const SingleRefData& rRef2 );

    /** Finds or inserts an EXTERNNAME record for an add-in function name.
        @param rnXti  Returns the index of the XTI structure which contains the add-in function name.
        @param rnExtName  Returns the 1-based EXTERNNAME record index. */
    void                        InsertAddIn(
                                    sal_uInt16& rnXti, sal_uInt16& rnExtName,
                                    const String& rName );
    /** Finds or inserts an EXTERNNAME record for DDE links.
        @param rnXti  Returns the index of the XTI structure which contains the DDE link.
        @param rnExtName  Returns the 1-based EXTERNNAME record index. */
    bool                        InsertDde(
                                    sal_uInt16& rnXti, sal_uInt16& rnExtName,
                                    const String& rApplic, const String& rTopic, const String& rItem );

    /** Writes the entire Link table. */
    virtual void                Save( XclExpStream& rStrm );

private:
    typedef ::std::auto_ptr< XclExpLinkManager_Impl > XclExpLinkManager_ImplPtr;
    XclExpLinkManager_ImplPtr   mpImpl;
};

// ============================================================================

#endif

<|endoftext|>


<commit_before>// Copyright (c) 2012 The Bitcoin developers
// Distributed under the MIT/X11 software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
#include <string>

#include "version.h"

// Name of client reported in the 'version' message. Report the same name
// for both bitcoind and bitcoin-qt, to make it harder for attackers to
// target servers or GUI users specifically.
const std::string CLIENT_NAME("Satoshi");

// Client version number
#define CLIENT_VERSION_SUFFIX   "-beta"

// The following part of the code determines the CLIENT_BUILD variable.
// Several mechanisms are used for this:
// * first, if HAVE_BUILD_INFO is defined, include build.h, a file that is
//   generated by the build environment, possibly containing the output
//   of git-describe in a macro called BUILD_DESC
// * secondly, if this is an exported version of the code, GIT_ARCHIVE will
//   be defined (automatically using the export-subst git attribute), and
//   GIT_COMMIT will contain the commit id.
// * then, three options exist for determining CLIENT_BUILD:
//   * if BUILD_DESC is defined, use that literally (output of git-describe)
//   * if not, but GIT_COMMIT is defined, use v[maj].[min].[rev].[build]-g[commit]
//   * otherwise, use v[maj].[min].[rev].[build]-unk
// finally CLIENT_VERSION_SUFFIX is added

// First, include build.h if requested
#ifdef HAVE_BUILD_INFO
#    include "build.h"
#endif

// git will put "#define GIT_ARCHIVE 1" on the next line inside archives. $Format:%n#define GIT_ARCHIVE 1$
#ifdef GIT_ARCHIVE
#    define GIT_COMMIT_ID "$Format:%h$"
#    define GIT_COMMIT_DATE "$Format:%cD"
#endif

#define BUILD_DESC_FROM_COMMIT(maj,min,rev,build,commit) \
    "v" DO_STRINGIZE(maj) "." DO_STRINGIZE(min) "." DO_STRINGIZE(rev) "." DO_STRINGIZE(build) "-g" commit

#define BUILD_DESC_FROM_UNKNOWN(maj,min,rev,build) \
    "v" DO_STRINGIZE(maj) "." DO_STRINGIZE(min) "." DO_STRINGIZE(rev) "." DO_STRINGIZE(build) "-unk"

#ifndef BUILD_DESC
#    ifdef GIT_COMMIT_ID
#        define BUILD_DESC BUILD_DESC_FROM_COMMIT(CLIENT_VERSION_MAJOR, CLIENT_VERSION_MINOR, CLIENT_VERSION_REVISION, CLIENT_VERSION_BUILD, GIT_COMMIT_ID)
#    else
#        define BUILD_DESC BUILD_DESC_FROM_UNKNOWN(CLIENT_VERSION_MAJOR, CLIENT_VERSION_MINOR, CLIENT_VERSION_REVISION, CLIENT_VERSION_BUILD)
#    endif
#endif

#ifndef BUILD_DATE
#    ifdef GIT_COMMIT_DATE
#        define BUILD_DATE GIT_COMMIT_DATE
#    else
#        define BUILD_DATE __DATE__ ", " __TIME__
#    endif
#endif

const std::string CLIENT_BUILD(BUILD_DESC CLIENT_VERSION_SUFFIX);
const std::string CLIENT_DATE(BUILD_DATE);
<commit_msg>Fix build date for from-tarball builds<commit_after>// Copyright (c) 2012 The Bitcoin developers
// Distributed under the MIT/X11 software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
#include <string>

#include "version.h"

// Name of client reported in the 'version' message. Report the same name
// for both bitcoind and bitcoin-qt, to make it harder for attackers to
// target servers or GUI users specifically.
const std::string CLIENT_NAME("Satoshi");

// Client version number
#define CLIENT_VERSION_SUFFIX   "-beta"

// The following part of the code determines the CLIENT_BUILD variable.
// Several mechanisms are used for this:
// * first, if HAVE_BUILD_INFO is defined, include build.h, a file that is
//   generated by the build environment, possibly containing the output
//   of git-describe in a macro called BUILD_DESC
// * secondly, if this is an exported version of the code, GIT_ARCHIVE will
//   be defined (automatically using the export-subst git attribute), and
//   GIT_COMMIT will contain the commit id.
// * then, three options exist for determining CLIENT_BUILD:
//   * if BUILD_DESC is defined, use that literally (output of git-describe)
//   * if not, but GIT_COMMIT is defined, use v[maj].[min].[rev].[build]-g[commit]
//   * otherwise, use v[maj].[min].[rev].[build]-unk
// finally CLIENT_VERSION_SUFFIX is added

// First, include build.h if requested
#ifdef HAVE_BUILD_INFO
#    include "build.h"
#endif

// git will put "#define GIT_ARCHIVE 1" on the next line inside archives. $Format:%n#define GIT_ARCHIVE 1$
#ifdef GIT_ARCHIVE
#    define GIT_COMMIT_ID "$Format:%h$"
#    define GIT_COMMIT_DATE "$Format:%cD$"
#endif

#define BUILD_DESC_FROM_COMMIT(maj,min,rev,build,commit) \
    "v" DO_STRINGIZE(maj) "." DO_STRINGIZE(min) "." DO_STRINGIZE(rev) "." DO_STRINGIZE(build) "-g" commit

#define BUILD_DESC_FROM_UNKNOWN(maj,min,rev,build) \
    "v" DO_STRINGIZE(maj) "." DO_STRINGIZE(min) "." DO_STRINGIZE(rev) "." DO_STRINGIZE(build) "-unk"

#ifndef BUILD_DESC
#    ifdef GIT_COMMIT_ID
#        define BUILD_DESC BUILD_DESC_FROM_COMMIT(CLIENT_VERSION_MAJOR, CLIENT_VERSION_MINOR, CLIENT_VERSION_REVISION, CLIENT_VERSION_BUILD, GIT_COMMIT_ID)
#    else
#        define BUILD_DESC BUILD_DESC_FROM_UNKNOWN(CLIENT_VERSION_MAJOR, CLIENT_VERSION_MINOR, CLIENT_VERSION_REVISION, CLIENT_VERSION_BUILD)
#    endif
#endif

#ifndef BUILD_DATE
#    ifdef GIT_COMMIT_DATE
#        define BUILD_DATE GIT_COMMIT_DATE
#    else
#        define BUILD_DATE __DATE__ ", " __TIME__
#    endif
#endif

const std::string CLIENT_BUILD(BUILD_DESC CLIENT_VERSION_SUFFIX);
const std::string CLIENT_DATE(BUILD_DATE);
<|endoftext|>