// Copyright 2016 The Cobalt Authors. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "cobalt/renderer/backend/blitter/display.h"

#include "base/trace_event/trace_event.h"
#include "cobalt/base/polymorphic_downcast.h"
#include "cobalt/renderer/backend/blitter/render_target.h"
#include "cobalt/system_window/system_window.h"

#if SB_API_VERSION >= SB_ALL_RENDERERS_REQUIRED_VERSION || SB_HAS(BLITTER)

namespace cobalt {
namespace renderer {
namespace backend {

namespace {

class DisplayRenderTargetBlitter : public RenderTargetBlitter {
 public:
  // The DisplayRenderTargetBlitter is constructed with a handle to a native
  // window to use as the render target.
  DisplayRenderTargetBlitter(SbBlitterDevice device,
                             system_window::SystemWindow* system_window);

  const math::Size& GetSize() const override;

  SbBlitterRenderTarget GetSbRenderTarget() const override;

  void Flip() override;

  bool CreationError() override { return false; }

 private:
  ~DisplayRenderTargetBlitter() override;

  SbBlitterSwapChain swap_chain_;
  SbBlitterRenderTarget render_target_;

  math::Size size_;
};

DisplayRenderTargetBlitter::DisplayRenderTargetBlitter(
    SbBlitterDevice device, system_window::SystemWindow* system_window) {
  SbWindow starboard_window = system_window->GetSbWindow();

  swap_chain_ = SbBlitterCreateSwapChainFromWindow(device, starboard_window);
  CHECK(SbBlitterIsSwapChainValid(swap_chain_));

  render_target_ = SbBlitterGetRenderTargetFromSwapChain(swap_chain_);
  CHECK(SbBlitterIsRenderTargetValid(render_target_));

  SbWindowSize window_size;
  SbWindowGetSize(starboard_window, &window_size);
  size_.SetSize(window_size.width, window_size.height);
}

const math::Size& DisplayRenderTargetBlitter::GetSize() const { return size_; }

DisplayRenderTargetBlitter::~DisplayRenderTargetBlitter() {
  SbBlitterDestroySwapChain(swap_chain_);
}

SbBlitterRenderTarget DisplayRenderTargetBlitter::GetSbRenderTarget() const {
  return render_target_;
}

void DisplayRenderTargetBlitter::Flip() {
  TRACE_EVENT0("cobalt::renderer", "DisplayRenderTargetBlitter::Flip()");
  SbBlitterFlipSwapChain(swap_chain_);
}

}  // namespace

DisplayBlitter::DisplayBlitter(SbBlitterDevice device,
                               system_window::SystemWindow* system_window) {
  // A display effectively just hosts a DisplayRenderTargetBlitter.
  render_target_ = new DisplayRenderTargetBlitter(device, system_window);
}

scoped_refptr<RenderTarget> DisplayBlitter::GetRenderTarget() {
  return render_target_;
}

}  // namespace backend
}  // namespace renderer
}  // namespace cobalt

#endif  // #if SB_API_VERSION >= SB_ALL_RENDERERS_REQUIRED_VERSION ||
        // SB_HAS(BLITTER)
