1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3  * This file is part of the LibreOffice project.
4  *
5  * This Source Code Form is subject to the terms of the Mozilla Public
6  * License, v. 2.0. If a copy of the MPL was not distributed with this
7  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8  *
9  * This file incorporates work covered by the following license notice:
10  *
11  *   Licensed to the Apache Software Foundation (ASF) under one or more
12  *   contributor license agreements. See the NOTICE file distributed
13  *   with this work for additional information regarding copyright
14  *   ownership. The ASF licenses this file to you under the Apache
15  *   License, Version 2.0 (the "License"); you may not use this file
16  *   except in compliance with the License. You may obtain a copy of
17  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
18  */
19 
20 #pragma once
21 
22 #include "MasterPageContainer.hxx"
23 #include "MasterPageDescriptor.hxx"
24 
25 #include <vcl/timer.hxx>
26 
27 #include <memory>
28 
29 namespace sd::sidebar {
30 
31 /** The queue stores and processes all requests from a MasterPageContainer
32     for the creation of previews.
33     The order of request processing and its timing is controlled by a
34     heuristic that uses values given with each request and which is
35     controlled by various parameters that are described below.
36 */
37 class MasterPageContainerQueue final
38 {
39 public:
40     class ContainerAdapter {
41     public:
42         virtual bool UpdateDescriptor (
43             const SharedMasterPageDescriptor& rpDescriptor,
44             bool bForcePageObject,
45             bool bForcePreview,
46             bool bSendEvents) = 0;
47 
48     protected:
~ContainerAdapter()49         ~ContainerAdapter() {}
50     };
51 
52     static MasterPageContainerQueue* Create (
53         const std::weak_ptr<ContainerAdapter>& rpContainer);
54     ~MasterPageContainerQueue();
55 
56     /** This method is typically called for entries in the container for
57         which GetPreviewState() returns OS_CREATABLE.  The creation of the
58         preview is then scheduled to be executed asynchronously at a later
59         point in time.  When the preview is available the change listeners
60         will be notified.
61     */
62     bool RequestPreview (const SharedMasterPageDescriptor& rDescriptor);
63 
64     /** Return <TRUE/> when there is a request currently in the queue for
65         the given token.
66     */
67     bool HasRequest (MasterPageContainer::Token aToken) const;
68 
69     /** Return <TRUE/> when there is at least one request in the queue.
70     */
71     bool IsEmpty() const;
72 
73     /** After this call the queue does not wait anymore for requests with
74         higher priority when only a small number of requests with lower
75         priority are present.  This method should be called when all
76         templates are inserted into the MasterPageContainer.
77     */
78     void ProcessAllRequests();
79 
80 private:
81     std::weak_ptr<ContainerAdapter> mpWeakContainer;
82     class PreviewCreationRequest;
83     class RequestQueue;
84     std::unique_ptr<RequestQueue> mpRequestQueue;
85     Timer maDelayedPreviewCreationTimer;
86     sal_uInt32 mnRequestsServedCount;
87 
88     // There are a couple of values that define various aspects of the
89     // heuristic that defines the order and timing in which requests for
90     // preview creation are processed.
91 
92     /** The time to wait (in milliseconds) between the creation of previews.
93     */
94     static const sal_Int32 snDelayedCreationTimeout;
95 
96     /** The time to wait when the system is not idle.
97     */
98     static const sal_Int32 snDelayedCreationTimeoutWhenNotIdle;
99 
100     /** Requests for previews of master pages in a document have their
101         priority increased by this value.
102     */
103     static const sal_Int32 snMasterPagePriorityBoost;
104 
105     /** When only requests which a priority lower than this threshold exist
106         and not many requests have been made yet then wait with processing
107         them until more requests are present.
108     */
109     static const sal_Int32 snWaitForMoreRequestsPriorityThreshold;
110 
111     /** When only requests which a priority lower than a threshold exist
112         and not more requests than this number have been made or already
113         processed then wait with processing them until more requests are
114         present.
115     */
116     static sal_uInt32 snWaitForMoreRequestsCount;
117 
118     explicit MasterPageContainerQueue (const std::weak_ptr<ContainerAdapter>& rpContainer);
119     void LateInit();
120 
121     /** Calculate the priority that defines the order in which requests
122         are processed.
123     */
124     static sal_Int32 CalculatePriority (const SharedMasterPageDescriptor& rDescriptor);
125 
126     DECL_LINK(DelayedPreviewCreation, Timer *, void);
127 };
128 
129 } // end of namespace sd::sidebar
130 
131 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
132