mirror of
https://github.com/aseprite/aseprite.git
synced 2025-04-05 13:20:21 +00:00
120 lines
2.4 KiB
C++
120 lines
2.4 KiB
C++
// Aseprite Document Library
|
|
// Copyright (c) 2016 David Capello
|
|
//
|
|
// This file is released under the terms of the MIT license.
|
|
// Read LICENSE.txt for more information.
|
|
|
|
#ifdef HAVE_CONFIG_H
|
|
#include "config.h"
|
|
#endif
|
|
|
|
#include "doc/selected_frames.h"
|
|
|
|
#include <algorithm>
|
|
|
|
namespace doc {
|
|
|
|
std::size_t SelectedFrames::size() const
|
|
{
|
|
std::size_t size = 0;
|
|
for (auto& range : m_ranges)
|
|
size += (range.toFrame - range.fromFrame + 1);
|
|
return size;
|
|
}
|
|
|
|
void SelectedFrames::clear()
|
|
{
|
|
m_ranges.clear();
|
|
}
|
|
|
|
void SelectedFrames::insert(frame_t frame)
|
|
{
|
|
ASSERT(frame >= 0);
|
|
|
|
if (m_ranges.empty()) {
|
|
m_ranges.push_back(FrameRange(frame));
|
|
return;
|
|
}
|
|
|
|
auto it = m_ranges.begin();
|
|
auto end = m_ranges.end();
|
|
auto next = it;
|
|
|
|
for (; it!=end; it=next) {
|
|
if (frame >= it->fromFrame &&
|
|
frame <= it->toFrame)
|
|
break;
|
|
|
|
if (frame < it->fromFrame) {
|
|
if (frame == it->fromFrame-1)
|
|
--it->fromFrame;
|
|
else
|
|
m_ranges.insert(it, FrameRange(frame));
|
|
break;
|
|
}
|
|
|
|
++next;
|
|
|
|
if (frame > it->toFrame && (next == end || frame < next->fromFrame-1)) {
|
|
if (frame == it->toFrame+1)
|
|
++it->toFrame;
|
|
else
|
|
m_ranges.insert(next, FrameRange(frame));
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
void SelectedFrames::insert(frame_t fromFrame, frame_t toFrame)
|
|
{
|
|
if (fromFrame > toFrame)
|
|
std::swap(fromFrame, toFrame);
|
|
|
|
// TODO improve this
|
|
for (frame_t frame = fromFrame; frame <= toFrame; ++frame) {
|
|
insert(frame);
|
|
}
|
|
}
|
|
|
|
void SelectedFrames::filter(frame_t fromFrame, frame_t toFrame)
|
|
{
|
|
if (fromFrame > toFrame)
|
|
std::swap(fromFrame, toFrame);
|
|
|
|
// TODO improve this, avoid copying
|
|
SelectedFrames original = *this;
|
|
for (frame_t frame : original) {
|
|
if (frame >= fromFrame && frame <= toFrame)
|
|
insert(frame);
|
|
}
|
|
}
|
|
|
|
bool SelectedFrames::contains(frame_t frame) const
|
|
{
|
|
return std::binary_search(
|
|
m_ranges.begin(),
|
|
m_ranges.end(),
|
|
FrameRange(frame),
|
|
[](const FrameRange& a,
|
|
const FrameRange& b) -> bool {
|
|
return (a.toFrame < b.fromFrame);
|
|
});
|
|
}
|
|
|
|
void SelectedFrames::displace(frame_t frameDelta)
|
|
{
|
|
// Avoid setting negative numbers in frame ranges
|
|
if (firstFrame()+frameDelta < 0)
|
|
frameDelta = -firstFrame();
|
|
|
|
for (auto& range : m_ranges) {
|
|
range.fromFrame += frameDelta;
|
|
range.toFrame += frameDelta;
|
|
|
|
ASSERT(range.fromFrame >= 0);
|
|
ASSERT(range.toFrame >= 0);
|
|
}
|
|
}
|
|
|
|
} // namespace doc
|