• skia 将网页录制成 skp 文件 通过skia的dm或者其他方式重放


    https://skia.org/docs/user/tips/

    1,Use the script experimental/tools/web_to_skp , or do the following:

    1. Launch Chrome or Chromium with --no-sandbox --enable-gpu-benchmarking
    2. Open the JS console (Ctrl+Shift+J (Windows / Linux) or Cmd+Opt+J (MacOS))
    3. Execute: chrome.gpuBenchmarking.printToSkPicture('/tmp') This returns “undefined” on success.

    /tmp是个存放的目录。windows可以写成 chrome.gpuBenchmarking.printToSkPicture('d:\mySkp')

    Open the resulting file in the Skia Debugger, rasterize it with dm, or use Skia’s viewer to view it:

    out/Release/dm --src skp --skps /tmp/layer_0.skp -w /tmp 
        --config 8888 gpu pdf --verbose
    ls -l /tmp/*/skp/layer_0.skp.*
    
    out/Release/viewer --skps /tmp --slide layer_0.skp

     1.1 在源码中的实现:

    
    

    #include "base/base64.h"
    #include "base/bind.h"
    #include "base/command_line.h"
    #include "base/debug/profiler.h"
    #include "base/files/file_path.h"
    #include "base/files/file_util.h"

    
    

    #include "third_party/skia/include/core/SkPicture.h"
    #include "third_party/skia/include/core/SkPictureRecorder.h"



    void
    GpuBenchmarking::PrintToSkPicture(v8::Isolate* isolate, const std::string& dirname) { GpuBenchmarkingContext context(render_frame_.get()); const cc::Layer* root_layer = context.layer_tree_host()->root_layer(); if (!root_layer) return; base::FilePath dirpath = base::FilePath::FromUTF8Unsafe(dirname); if (!base::CreateDirectory(dirpath) || !base::PathIsWritable(dirpath)) { std::string msg("Path is not writable: "); msg.append(dirpath.MaybeAsASCII()); isolate->ThrowException(v8::Exception::Error( v8::String::NewFromUtf8(isolate, msg.c_str(), v8::NewStringType::kNormal, msg.length()) .ToLocalChecked())); return; } SkPictureSerializer serializer(dirpath); serializer.Serialize(root_layer); }
    serializer:
    void Serialize(const cc::Layer* root_layer) {
        for (auto* layer : *root_layer->layer_tree_host()) {
          sk_sp<SkPicture> picture = layer->GetPicture();
          if (!picture)
            continue;
    
          // Serialize picture to file.
          // TODO(alokp): Note that for this to work Chrome needs to be launched
          // with
          // --no-sandbox command-line flag. Get rid of this limitation.
          // CRBUG: 139640.
          std::string filename =
              "layer_" + base::NumberToString(layer_id_++) + ".skp";
          std::string filepath = dirpath_.AppendASCII(filename).MaybeAsASCII();
          DCHECK(!filepath.empty());
          SkFILEWStream file(filepath.c_str());
          DCHECK(file.isValid());
    
          auto data = picture->serialize();
          file.write(data->data(), data->size());
          file.fsync();
        }
      }
    GetPicture:
    sk_sp<SkPicture> PictureLayer::GetPicture() const {
      if (!DrawsContent() || bounds().IsEmpty())
        return nullptr;
    
      scoped_refptr<DisplayItemList> display_list =
          picture_layer_inputs_.client->PaintContentsToDisplayList();
      SkPictureRecorder recorder;
      SkCanvas* canvas =
          recorder.beginRecording(bounds().width(), bounds().height());
      canvas->clear(SK_ColorTRANSPARENT);
      display_list->Raster(canvas);
      return recorder.finishRecordingAsPicture();
    }

    1.2 draw paint录制:

    void SkCanvas::drawPaint(const SkPaint& paint) {
        TRACE_EVENT0("skia", TRACE_FUNC);
        this->onDrawPaint(paint);
    }

     重放,参考 canvaskit/node_build/extra.html

    canvaskit draw skp

    function SkpExample(CanvasKit, skpData) {
    
    if (!skpData || !CanvasKit) {
    
    return;
    
    }
    
     
    
    const surface = CanvasKit.MakeSWCanvasSurface('skp');
    
    if (!surface) {
    
    console.error('Could not make surface');
    
    return;
    
    }
    
     
    
    const pic = CanvasKit.MakePicture(skpData);
    
     
    
    function drawFrame(canvas) {
    
    canvas.clear(CanvasKit.TRANSPARENT);
    
    // this particular file has a path drawing at (68,582) that's 1300x1300 pixels
    
    // scale it down to 500x500 and translate it to fit.
    
    const scale = 500.0/1300;
    
    canvas.scale(scale, scale);
    
    canvas.translate(-68, -582);
    
    canvas.drawPicture(pic);
    
    }
    
    // Intentionally just draw frame once
    
    surface.drawOnce(drawFrame);
    
    }
    
     

    2, 也可录制多个页面,还原成pdf

    Capture a .mskp file on a web page in Chromium

    Multipage Skia Picture files capture the commands sent to produce PDFs and printed documents.

    Use the script experimental/tools/web_to_mskp , or do the following:

    1. Launch Chrome or Chromium with --no-sandbox --enable-gpu-benchmarking
    2. Open the JS console (Ctrl+Shift+J (Windows / Linux) or Cmd+Opt+J (MacOS))
    3. Execute: chrome.gpuBenchmarking.printPagesToSkPictures('/tmp/filename.mskp') This returns “undefined” on success.

    Open the resulting file in the Skia Debugger or process it with dm.

    experimental/tools/mskp_parser.py /tmp/filename.mskp /tmp/filename.mskp.skp
    ls -l /tmp/filename.mskp.skp
    # open filename.mskp.skp in the debugger.
    
    out/Release/dm --src mskp --mskps /tmp/filename.mskp -w /tmp 
        --config pdf --verbose
    ls -l /tmp/pdf/mskp/filename.mskp.pdf
    

    How to add hardware acceleration in Skia

    There are two ways Skia takes advantage of specific hardware.

    1. Custom bottleneck routines

      There are sets of bottleneck routines inside the blits of Skia that can be replace on a platform in order to take advantage of specific CPU features. One such example is the NEON SIMD instructions on ARM v7 devices. See src/opts/


    Does Skia support Font hinting?

    Skia has a built-in font cache, but it does not know how to actually render font files like TrueType into its cache. For that it relies on the platform to supply an instance of SkScalerContext. This is Skia’s abstract interface for communicating with a font scaler engine. In src/ports you can see support files for FreeType, macOS, and Windows GDI font engines. Other font engines can easily be supported in a like manner.


    Does Skia shape text (kerning)?

    Shaping is the process that translates a span of Unicode text into a span of positioned glyphs with the appropriate typefaces.

    Skia does not shape text. Skia provides interfaces to draw glyphs, but does not implement a text shaper. Skia’s client’s often use HarfBuzz to generate the glyphs and their positions, including kerning.

    Here is an example of how to use Skia and HarfBuzz together. In the example, a SkTypeface and a hb_face_t are created using the same mmap()ed .ttf font file. The HarfBuzz face is used to shape unicode text into a sequence of glyphs and positions, and the SkTypeface can then be used to draw those glyphs.


    How do I add drop shadow on text?

    void draw(SkCanvas* canvas) {
        const SkScalar sigma = 1.65f;
        const SkScalar xDrop = 2.0f;
        const SkScalar yDrop = 2.0f;
        const SkScalar x = 8.0f;
        const SkScalar y = 52.0f;
        const SkScalar textSize = 48.0f;
        const uint8_t blurAlpha = 127;
        auto blob = SkTextBlob::MakeFromString("Skia", SkFont(nullptr, textSize));
        SkPaint paint;
        paint.setAntiAlias(true);
        SkPaint blur(paint);
        blur.setAlpha(blurAlpha);
        blur.setMaskFilter(SkMaskFilter::MakeBlur(kNormal_SkBlurStyle, sigma, 0));
        canvas->drawColor(SK_ColorWHITE);
        canvas->drawTextBlob(blob.get(), x + xDrop, y + yDrop, blur);
        canvas->drawTextBlob(blob.get(), x,         y,         paint);
    }
  • 相关阅读:
    【转】正则基础之——/b 单词边界
    【转】空格变成问号的怪问题
    【转】正则基础之——NFA引擎匹配原理
    【转】 .NET正则基础之——平衡组
    【转】正则基础之——环视
    【转】正则应用之——日期正则表达式
    【转】正则基础之——小数点
    【转】[ ] 字符组(Character Classes)
    【转】正则表达式30分钟入教程
    【转】正则基础之——非捕获组
  • 原文地址:https://www.cnblogs.com/bigben0123/p/14890350.html
Copyright © 2020-2023  润新知