summaryrefslogtreecommitdiff
path: root/platform/winrt
diff options
context:
space:
mode:
Diffstat (limited to 'platform/winrt')
-rw-r--r--platform/winrt/mupdf_cpp/MainPage.xaml2
-rw-r--r--platform/winrt/mupdf_cpp/MainPage.xaml.cpp75
-rw-r--r--platform/winrt/mupdf_cpp/MainPage.xaml.h5
-rw-r--r--platform/winrt/mupdfwinrt/Cache.cpp10
-rw-r--r--platform/winrt/mupdfwinrt/Cache.h8
-rw-r--r--platform/winrt/mupdfwinrt/muctx.cpp202
-rw-r--r--platform/winrt/mupdfwinrt/muctx.h10
-rw-r--r--platform/winrt/mupdfwinrt/mudocument.cpp82
-rw-r--r--platform/winrt/mupdfwinrt/mudocument.h3
9 files changed, 224 insertions, 173 deletions
diff --git a/platform/winrt/mupdf_cpp/MainPage.xaml b/platform/winrt/mupdf_cpp/MainPage.xaml
index 22fbe5da..eaf096e3 100644
--- a/platform/winrt/mupdf_cpp/MainPage.xaml
+++ b/platform/winrt/mupdf_cpp/MainPage.xaml
@@ -14,7 +14,7 @@
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
- <Slider x:Name="xaml_PageSlider" Minimum="0" Maximum="10" ValueChanged="Slider_ValueChanged" Grid.Column="0" Margin="10,0" VerticalAlignment="Center" />
+ <Slider x:Name="xaml_PageSlider" Minimum="0" Maximum="10" PointerCaptureLost="Slider_ValueChanged" Grid.Column="0" Margin="10,0" VerticalAlignment="Center" />
<Button x:Name="Find_File" Style="{StaticResource OpenFileAppBarButtonStyle}" Tag="OpenFile" HorizontalAlignment="Right" Grid.Column="1" Click="Picker"/>
</Grid>
</AppBar>
diff --git a/platform/winrt/mupdf_cpp/MainPage.xaml.cpp b/platform/winrt/mupdf_cpp/MainPage.xaml.cpp
index d31c2b94..166d81cf 100644
--- a/platform/winrt/mupdf_cpp/MainPage.xaml.cpp
+++ b/platform/winrt/mupdf_cpp/MainPage.xaml.cpp
@@ -6,7 +6,7 @@
#include "pch.h"
#include "MainPage.xaml.h"
-#define LOOK_AHEAD 0 /* A +/- count on the pages to pre-render */
+#define LOOK_AHEAD 1 /* A +/- count on the pages to pre-render */
#define THUMB_PREADD 10
#define MIN_SCALE 0.5
@@ -737,18 +737,44 @@ void mupdf_cpp::MainPage::RenderRange(int curr_page)
}
}
-void mupdf_cpp::MainPage::Slider_ValueChanged(Platform::Object^ sender, Windows::UI::Xaml::Controls::Primitives::RangeBaseValueChangedEventArgs^ e)
+void mupdf_cpp::MainPage::FlipView_SelectionChanged(Object^ sender, SelectionChangedEventArgs^ e)
+{
+ if (m_init_done && !m_page_update)
+ {
+ int pos = this->m_curr_flipView->SelectedIndex;
+
+ if (pos >= 0)
+ {
+ if (xaml_PageSlider->IsEnabled)
+ {
+ xaml_PageSlider->Value = pos;
+ }
+ if (m_sliderchange)
+ {
+ m_sliderchange = false;
+ return;
+ }
+ else
+ {
+ /* Make sure to clear any text search */
+ auto doc_old = this->m_docPages->GetAt(m_currpage);
+ doc_old->TextBox = nullptr;
+ }
+ /* Get the current page */
+ int curr_page = this->m_currpage;
+ this->RenderRange(pos);
+ this->ReleasePages(curr_page, pos);
+ }
+ }
+}
+
+void mupdf_cpp::MainPage::Slider_ValueChanged(Platform::Object^ sender, Windows::UI::Xaml::Input::PointerRoutedEventArgs^ e)
{
int newValue = (int) this->xaml_PageSlider->Value - 1; /* zero based */
if (IsNotStandardView())
return;
- if (m_update_flip)
- {
- m_update_flip = false;
- return;
- }
if (m_init_done && this->xaml_PageSlider->IsEnabled)
{
/* Make sure to clear any text search */
@@ -778,38 +804,6 @@ void mupdf_cpp::MainPage::Slider_ValueChanged(Platform::Object^ sender, Windows:
}
}
-void mupdf_cpp::MainPage::FlipView_SelectionChanged(Object^ sender, SelectionChangedEventArgs^ e)
-{
- if (m_init_done && !m_page_update)
- {
- int pos = this->m_curr_flipView->SelectedIndex;
-
- if (pos >= 0)
- {
- m_update_flip = true;
- if (xaml_PageSlider->IsEnabled)
- {
- xaml_PageSlider->Value = pos;
- }
- if (m_sliderchange)
- {
- m_sliderchange = false;
- return;
- }
- else
- {
- /* Make sure to clear any text search */
- auto doc_old = this->m_docPages->GetAt(m_currpage);
- doc_old->TextBox = nullptr;
- }
- /* Get the current page */
- int curr_page = this->m_currpage;
- this->RenderRange(pos);
- this->ReleasePages(curr_page, pos);
- }
- }
-}
-
/* Search Related Code */
void mupdf_cpp::MainPage::Searcher(Platform::Object^ sender, Windows::UI::Xaml::RoutedEventArgs^ e)
{
@@ -975,7 +969,8 @@ void mupdf_cpp::MainPage::SearchInDirection(int dir, String^ textToFind)
ProgressBar^ my_xaml_Progress = (ProgressBar^) (this->FindName("xaml_Progress"));
xaml_ProgressStack->Visibility = Windows::UI::Xaml::Visibility::Visible;
- auto temp = mu_doc->SearchDocumentWithProgressAsync(textToFind, dir, start);
+ auto temp = mu_doc->SearchDocumentWithProgressAsync(textToFind, dir, start,
+ m_num_pages);
temp->Progress = ref new AsyncOperationProgressHandler<int, double>(this, &MainPage::SearchProgress);
auto search_task = create_task(temp, token);
diff --git a/platform/winrt/mupdf_cpp/MainPage.xaml.h b/platform/winrt/mupdf_cpp/MainPage.xaml.h
index 80978bc8..417073e4 100644
--- a/platform/winrt/mupdf_cpp/MainPage.xaml.h
+++ b/platform/winrt/mupdf_cpp/MainPage.xaml.h
@@ -109,7 +109,6 @@ namespace mupdf_cpp
bool m_insearch; /* Used for UI display */
bool m_search_active; /* Used to avoid multiple UI clicks */
bool m_sliderchange;
- bool m_update_flip;
double m_Progress;
void ReplaceImage(int page_num, InMemoryRandomAccessStream^ ras, Point ras_size);
@@ -125,7 +124,6 @@ namespace mupdf_cpp
void HandleFileNotFoundException(Platform::COMException^ e);
void NotifyUserFileNotExist();
void SetFlipView();
- void Slider_ValueChanged(Platform::Object^ sender, Windows::UI::Xaml::Controls::Primitives::RangeBaseValueChangedEventArgs^ e);
void Slider_Released(Platform::Object^ sender, Windows::UI::Xaml::Controls::Primitives::RangeBaseValueChangedEventArgs^ e);
void FlipView_SelectionChanged(Object^ sender, SelectionChangedEventArgs^ e);
void SearchNext(Platform::Object^ sender, Windows::UI::Xaml::RoutedEventArgs^ e);
@@ -173,5 +171,6 @@ namespace mupdf_cpp
void Page_Loaded(Object^ sender, RoutedEventArgs^ e);
Windows::ApplicationModel::Activation::ProtocolActivatedEventArgs^ _protocolEventArgs;
Windows::ApplicationModel::Activation::FileActivatedEventArgs^ _fileEventArgs;
- };
+ void Slider_ValueChanged(Platform::Object^ sender, Windows::UI::Xaml::Input::PointerRoutedEventArgs^ e);
+};
}
diff --git a/platform/winrt/mupdfwinrt/Cache.cpp b/platform/winrt/mupdfwinrt/Cache.cpp
index 77e253f0..b129710f 100644
--- a/platform/winrt/mupdfwinrt/Cache.cpp
+++ b/platform/winrt/mupdfwinrt/Cache.cpp
@@ -22,6 +22,7 @@ void Cache::Empty(fz_context *mu_ctx)
cache_entry_t *old_entry = curr_entry;
curr_entry = old_entry->next;
fz_drop_display_list(mu_ctx, old_entry->dlist);
+
delete old_entry;
}
this->size = 0;
@@ -30,7 +31,8 @@ void Cache::Empty(fz_context *mu_ctx)
}
}
-void Cache::AddEntry(int value, fz_display_list *dlist, fz_context *mu_ctx)
+void Cache::Add(int value, int width_in, int height_in, fz_display_list *dlist,
+ fz_context *mu_ctx)
{
std::lock_guard<std::mutex> lock(cache_lock);
@@ -58,6 +60,8 @@ void Cache::AddEntry(int value, fz_display_list *dlist, fz_context *mu_ctx)
new_entry->dlist = dlist;
new_entry->index = value;
+ new_entry->width = width_in;
+ new_entry->height = height_in;
new_entry->prev = NULL;
if (head == NULL)
{
@@ -76,7 +80,7 @@ void Cache::AddEntry(int value, fz_display_list *dlist, fz_context *mu_ctx)
fz_keep_display_list(mu_ctx, new_entry->dlist);
}
-fz_display_list* Cache::UseEntry(int value, fz_context *mu_ctx)
+fz_display_list* Cache::Use(int value, int *width_out, int *height_out, fz_context *mu_ctx)
{
std::lock_guard<std::mutex> lock(cache_lock);
cache_entry_t *curr_entry = this->head;
@@ -107,6 +111,8 @@ fz_display_list* Cache::UseEntry(int value, fz_context *mu_ctx)
head->prev = curr_entry;
head = curr_entry;
}
+ *width_out = curr_entry->width;
+ *height_out = curr_entry->height;
return curr_entry->dlist;
}
else
diff --git a/platform/winrt/mupdfwinrt/Cache.h b/platform/winrt/mupdfwinrt/Cache.h
index 0763dba4..e8c9801d 100644
--- a/platform/winrt/mupdfwinrt/Cache.h
+++ b/platform/winrt/mupdfwinrt/Cache.h
@@ -11,6 +11,9 @@ typedef struct cache_entry_s cache_entry_t;
struct cache_entry_s
{
+ int number;
+ int width;
+ int height;
fz_display_list *dlist;
cache_entry_t *next;
cache_entry_t *prev;
@@ -28,7 +31,8 @@ private:
public:
Cache(void);
~Cache(void);
- fz_display_list* UseEntry(int value, fz_context *mu_ctx);
- void AddEntry(int value, fz_display_list *dlist, fz_context *mu_ctx);
+ void GetSize(int *width, int *height);
+ fz_display_list* Use(int value, int *width, int *height, fz_context *mu_ctx);
+ void Add(int value, int width, int height, fz_display_list *dlist, fz_context *mu_ctx);
void Empty(fz_context *mu_ctx);
};
diff --git a/platform/winrt/mupdfwinrt/muctx.cpp b/platform/winrt/mupdfwinrt/muctx.cpp
index 56c6f3a9..98aa7fc6 100644
--- a/platform/winrt/mupdfwinrt/muctx.cpp
+++ b/platform/winrt/mupdfwinrt/muctx.cpp
@@ -93,11 +93,11 @@ void muctx::CleanUp(void)
{
fz_free_outline(mu_ctx, mu_outline);
fz_close_document(mu_doc);
- display_list_cache->Empty(mu_ctx);
+ page_cache->Empty(mu_ctx);
fz_free_context(mu_ctx);
- delete display_list_cache;
- display_list_cache = NULL;
+ delete page_cache;
+ page_cache = NULL;
this->mu_ctx = NULL;
this->mu_doc = NULL;
this->mu_outline = NULL;
@@ -133,7 +133,7 @@ muctx::muctx(void)
mu_ctx = NULL;
mu_doc = NULL;
mu_outline = NULL;
- display_list_cache = new Cache();
+ page_cache = new Cache();
}
/* Destructor */
@@ -141,14 +141,14 @@ muctx::~muctx(void)
{
fz_free_outline(mu_ctx, mu_outline);
fz_close_document(mu_doc);
- display_list_cache->Empty(mu_ctx);
+ page_cache->Empty(mu_ctx);
fz_free_context(mu_ctx);
mu_ctx = NULL;
mu_doc = NULL;
mu_outline = NULL;
- delete display_list_cache;
- display_list_cache = NULL;
+ delete page_cache;
+ page_cache = NULL;
}
/* Set up the stream access */
@@ -250,13 +250,10 @@ void muctx::FlattenOutline(fz_outline *outline, int level,
int muctx::GetContents(sh_vector_content contents_vec)
{
fz_outline *root = NULL;
- fz_context *ctx_clone = NULL;
int has_content = 0;
- ctx_clone = fz_clone_context(mu_ctx);
-
fz_var(root);
- fz_try(ctx_clone)
+ fz_try(mu_ctx)
{
root = fz_load_outline(mu_doc);
if (root != NULL)
@@ -265,16 +262,14 @@ int muctx::GetContents(sh_vector_content contents_vec)
FlattenOutline(root, 0, contents_vec);
}
}
- fz_always(ctx_clone)
+ fz_always(mu_ctx)
{
- fz_free_outline(ctx_clone, root);
+ fz_free_outline(mu_ctx, root);
}
- fz_catch(ctx_clone)
+ fz_catch(mu_ctx)
{
- fz_free_context(ctx_clone);
return E_FAIL;
}
- fz_free_context(ctx_clone);
return has_content;
}
@@ -283,26 +278,23 @@ int muctx::GetTextSearch(int page_num, char* needle, sh_vector_text texts_vec)
fz_page *page = NULL;
fz_text_sheet *sheet = NULL;
fz_device *dev = NULL;
- fz_context *ctx_clone = NULL;
fz_text_page *text = NULL;
int hit_count = 0;
int k;
- ctx_clone = fz_clone_context(mu_ctx);
-
fz_var(page);
fz_var(sheet);
fz_var(dev);
- fz_try(ctx_clone)
+ fz_try(mu_ctx)
{
page = fz_load_page(mu_doc, page_num);
- sheet = fz_new_text_sheet(ctx_clone);
- text = fz_new_text_page(ctx_clone);
- dev = fz_new_text_device(ctx_clone, sheet, text);
+ sheet = fz_new_text_sheet(mu_ctx);
+ text = fz_new_text_page(mu_ctx);
+ dev = fz_new_text_device(mu_ctx, sheet, text);
fz_run_page(mu_doc, page, dev, &fz_identity, NULL);
fz_free_device(dev); /* Why does this need to be done here? Seems odd */
dev = NULL;
- hit_count = fz_search_text_page(ctx_clone, text, needle, mu_hit_bbox, nelem(mu_hit_bbox));
+ hit_count = fz_search_text_page(mu_ctx, text, needle, mu_hit_bbox, nelem(mu_hit_bbox));
for (k = 0; k < hit_count; k++)
{
@@ -314,19 +306,17 @@ int muctx::GetTextSearch(int page_num, char* needle, sh_vector_text texts_vec)
texts_vec->push_back(text_search);
}
}
- fz_always(ctx_clone)
+ fz_always(mu_ctx)
{
fz_free_page(mu_doc, page);
fz_free_device(dev);
- fz_free_text_sheet(ctx_clone, sheet);
- fz_free_text_page(ctx_clone, text);
+ fz_free_text_sheet(mu_ctx, sheet);
+ fz_free_text_page(mu_ctx, text);
}
- fz_catch(ctx_clone)
+ fz_catch(mu_ctx)
{
- fz_free_context(ctx_clone);
return E_FAIL;
}
- fz_free_context(ctx_clone);
return hit_count;
}
@@ -335,15 +325,12 @@ int muctx::GetLinks(int page_num, sh_vector_link links_vec)
{
fz_page *page = NULL;
fz_link *links = NULL;
- fz_context *ctx_clone = NULL;
int k = 0;
int num_links = 0;
- ctx_clone = fz_clone_context(mu_ctx);
-
fz_var(page);
fz_var(links);
- fz_try(ctx_clone)
+ fz_try(mu_ctx)
{
page = fz_load_page(mu_doc, page_num);
links = fz_load_links(mu_doc, page);
@@ -390,30 +377,26 @@ int muctx::GetLinks(int page_num, sh_vector_link links_vec)
}
}
}
- fz_always(ctx_clone)
+ fz_always(mu_ctx)
{
fz_free_page(mu_doc, page);
- fz_drop_link(ctx_clone, links);
+ fz_drop_link(mu_ctx, links);
}
- fz_catch(ctx_clone)
+ fz_catch(mu_ctx)
{
- fz_free_context(ctx_clone);
return E_FAIL;
}
- fz_free_context(ctx_clone);
return num_links;
}
-fz_display_list * muctx::CreateDisplayList(int page_num)
+fz_display_list * muctx::CreateDisplayList(int page_num, int *width, int *height)
{
- fz_context *ctx_clone = NULL;
fz_device *dev = NULL;
fz_page *page = NULL;
-
- ctx_clone = fz_clone_context(mu_ctx);
+ Point page_size;
/* First see if we have this one in the cache */
- fz_display_list *dlist = display_list_cache->UseEntry(page_num, ctx_clone);
+ fz_display_list *dlist = page_cache->Use(page_num, width, height, mu_ctx);
if (dlist != NULL)
return dlist;
@@ -422,80 +405,67 @@ fz_display_list * muctx::CreateDisplayList(int page_num)
fz_var(page);
fz_var(dlist);
- fz_try(ctx_clone)
+ fz_try(mu_ctx)
{
page = fz_load_page(mu_doc, page_num);
/* Create a new list */
- dlist = fz_new_display_list(ctx_clone);
- dev = fz_new_list_device(ctx_clone, dlist);
+ dlist = fz_new_display_list(mu_ctx);
+ dev = fz_new_list_device(mu_ctx, dlist);
fz_run_page_contents(mu_doc, page, dev, &fz_identity, NULL);
+ page_size = MeasurePage(page);
+ *width = page_size.X;
+ *height = page_size.Y;
/* Add it to the cache and set that it is in use */
- display_list_cache->AddEntry(page_num, dlist, ctx_clone);
+ page_cache->Add(page_num, *width, *height, dlist, mu_ctx);
}
- fz_always(ctx_clone)
+ fz_always(mu_ctx)
{
fz_free_device(dev);
fz_free_page(mu_doc, page);
}
- fz_catch(ctx_clone)
+ fz_catch(mu_ctx)
{
- fz_drop_display_list(ctx_clone, dlist);
- fz_free_context(ctx_clone);
+ fz_drop_display_list(mu_ctx, dlist);
return NULL;
}
return dlist;
}
-/* Render page_num to size width by height into bmp_data buffer */
-status_t muctx::RenderPage(int page_num, int width, int height,
- unsigned char *bmp_data, bool use_dlist)
+/* Render display list bmp_data buffer. No lock needed for this operation */
+status_t muctx::RenderPageMT(void *dlist, int page_width, int page_height,
+ unsigned char *bmp_data, int bmp_width, int bmp_height)
{
fz_device *dev = NULL;
fz_pixmap *pix = NULL;
- fz_page *page = NULL;
fz_matrix ctm, *pctm = &ctm;
- Point page_size;
fz_context *ctx_clone = NULL;
- fz_display_list *dlist = NULL;
-
- if (use_dlist)
- if ((dlist = CreateDisplayList(page_num)) == NULL)
- return E_FAILURE;
+ fz_display_list *display_list = (fz_display_list*) dlist;
ctx_clone = fz_clone_context(mu_ctx);
fz_var(dev);
fz_var(pix);
- fz_var(page);
- fz_var(dlist);
+ fz_var(display_list);
fz_try(ctx_clone)
{
- page = fz_load_page(mu_doc, page_num);
- page_size = MeasurePage(page);
-
/* Figure out scale factors so that we get the desired size */
- pctm = fz_scale(pctm, (float) width / page_size.X, (float) height / page_size.Y);
+ pctm = fz_scale(pctm, (float) bmp_width / page_width, (float) bmp_height / page_height);
/* Flip on Y */
- ctm.f = height;
+ ctm.f = bmp_height;
ctm.d = -ctm.d;
- pix = fz_new_pixmap_with_data(ctx_clone, fz_device_bgr(ctx_clone), width, height, bmp_data);
+ pix = fz_new_pixmap_with_data(ctx_clone, fz_device_bgr(ctx_clone), bmp_width,
+ bmp_height, bmp_data);
fz_clear_pixmap_with_value(ctx_clone, pix, 255);
dev = fz_new_draw_device(ctx_clone, pix);
- if (use_dlist)
- fz_run_display_list(dlist, dev, pctm, NULL, NULL);
- else
- fz_run_page(mu_doc, page, dev, pctm, NULL);
+ fz_run_display_list(display_list, dev, pctm, NULL, NULL);
}
fz_always(ctx_clone)
{
fz_free_device(dev);
fz_drop_pixmap(ctx_clone, pix);
- fz_free_page(mu_doc, page);
- if (use_dlist)
- fz_drop_display_list(ctx_clone, dlist);
-
+ fz_drop_display_list(ctx_clone, display_list);
}
fz_catch(ctx_clone)
{
@@ -507,6 +477,50 @@ status_t muctx::RenderPage(int page_num, int width, int height,
return S_ISOK;
}
+/* Render page_num to size width by height into bmp_data buffer. Lock needed. */
+status_t muctx::RenderPage(int page_num, unsigned char *bmp_data, int bmp_width,
+ int bmp_height)
+{
+ fz_device *dev = NULL;
+ fz_pixmap *pix = NULL;
+ fz_page *page = NULL;
+ fz_matrix ctm, *pctm = &ctm;
+ Point page_size;
+
+ fz_var(dev);
+ fz_var(pix);
+ fz_var(page);
+
+ fz_try(mu_ctx)
+ {
+ page = fz_load_page(mu_doc, page_num);
+ page_size = MeasurePage(page);
+
+ /* Figure out scale factors so that we get the desired size */
+ pctm = fz_scale(pctm, (float) bmp_width / page_size.X,
+ (float) bmp_height / page_size.Y);
+ /* Flip on Y */
+ ctm.f = bmp_height;
+ ctm.d = -ctm.d;
+ pix = fz_new_pixmap_with_data(mu_ctx, fz_device_bgr(mu_ctx), bmp_width,
+ bmp_height, bmp_data);
+ fz_clear_pixmap_with_value(mu_ctx, pix, 255);
+ dev = fz_new_draw_device(mu_ctx, pix);
+ fz_run_page(mu_doc, page, dev, pctm, NULL);
+ }
+ fz_always(mu_ctx)
+ {
+ fz_free_device(dev);
+ fz_drop_pixmap(mu_ctx, pix);
+ fz_free_page(mu_doc, page);
+ }
+ fz_catch(mu_ctx)
+ {
+ return E_FAILURE;
+ }
+ return S_ISOK;
+}
+
bool muctx::RequiresPassword(void)
{
return fz_needs_password(mu_doc);
@@ -524,46 +538,40 @@ String^ muctx::GetHTML(int page_num)
fz_page *page = NULL;
fz_text_sheet *sheet = NULL;
fz_text_page *text = NULL;
- fz_context *ctx_clone = NULL;
fz_buffer *buf = NULL;
String^ html;
- ctx_clone = fz_clone_context(mu_ctx);
-
fz_var(dev);
fz_var(page);
fz_var(sheet);
fz_var(text);
fz_var(buf);
- fz_try(ctx_clone)
+ fz_try(mu_ctx)
{
page = fz_load_page(mu_doc, page_num);
- sheet = fz_new_text_sheet(ctx_clone);
- text = fz_new_text_page(ctx_clone);
- dev = fz_new_text_device(ctx_clone, sheet, text);
+ sheet = fz_new_text_sheet(mu_ctx);
+ text = fz_new_text_page(mu_ctx);
+ dev = fz_new_text_device(mu_ctx, sheet, text);
fz_run_page(mu_doc, page, dev, &fz_identity, NULL);
fz_free_device(dev);
dev = NULL;
- fz_analyze_text(ctx_clone, sheet, text);
- buf = fz_new_buffer(ctx_clone, 256);
- out = fz_new_output_with_buffer(ctx_clone, buf);
- fz_print_text_page_html(ctx_clone, out, text);
+ fz_analyze_text(mu_ctx, sheet, text);
+ buf = fz_new_buffer(mu_ctx, 256);
+ out = fz_new_output_with_buffer(mu_ctx, buf);
+ fz_print_text_page_html(mu_ctx, out, text);
html = char_to_String((char*) buf->data);
}
- fz_always(ctx_clone)
+ fz_always(mu_ctx)
{
fz_free_device(dev);
fz_free_page(mu_doc, page);
- fz_free_text_sheet(ctx_clone, sheet);
- fz_free_text_page(ctx_clone, text);
- fz_drop_buffer(ctx_clone, buf);
+ fz_free_text_sheet(mu_ctx, sheet);
+ fz_free_text_page(mu_ctx, text);
+ fz_drop_buffer(mu_ctx, buf);
}
- fz_catch(ctx_clone)
+ fz_catch(mu_ctx)
{
- fz_free_context(ctx_clone);
return nullptr;
}
-
- fz_free_context(ctx_clone);
return html;
}
diff --git a/platform/winrt/mupdfwinrt/muctx.h b/platform/winrt/mupdfwinrt/muctx.h
index 826fa45b..cce78a29 100644
--- a/platform/winrt/mupdfwinrt/muctx.h
+++ b/platform/winrt/mupdfwinrt/muctx.h
@@ -76,8 +76,7 @@ private:
fz_rect mu_hit_bbox[MAX_SEARCH];
void FlattenOutline(fz_outline *outline, int level,
sh_vector_content contents_vec);
- Cache *display_list_cache;
- fz_display_list* CreateDisplayList(int page_num);
+ Cache *page_cache;
public:
muctx(void);
@@ -86,8 +85,11 @@ public:
status_t InitializeStream(IRandomAccessStream^ readStream, char *ext);
int GetPageCount();
status_t InitializeContext();
- status_t RenderPage(int page_num, int width, int height, unsigned char *bmp_data,
- bool use_dlist);
+ status_t RenderPage(int page_num, unsigned char *bmp_data, int bmp_width,
+ int bmp_height);
+ status_t RenderPageMT(void *dlist, int page_width, int page_height,
+ unsigned char *bmp_data, int bmp_width, int bmp_height);
+ fz_display_list* CreateDisplayList(int page_num, int *width, int *height);
Point MeasurePage(int page_num);
Point MeasurePage(fz_page *page);
int GetLinks(int page_num, sh_vector_link links_vec);
diff --git a/platform/winrt/mupdfwinrt/mudocument.cpp b/platform/winrt/mupdfwinrt/mudocument.cpp
index 92c24e24..7c90ba18 100644
--- a/platform/winrt/mupdfwinrt/mudocument.cpp
+++ b/platform/winrt/mupdfwinrt/mudocument.cpp
@@ -43,8 +43,12 @@ int mudocument::GetNumPages()
Point mudocument::GetPageSize(int page_num)
{
- std::lock_guard<std::mutex> lock(mutex_lock);
- return this->mu_object.MeasurePage(page_num);
+ Point size;
+
+ mutex_lock.lock();
+ size = this->mu_object.MeasurePage(page_num);
+ mutex_lock.unlock();
+ return size;
}
Windows::Foundation::IAsyncOperation<int>^ mudocument::OpenFileAsync(StorageFile^ file)
@@ -116,11 +120,12 @@ static void Prepare_bmp(int width, int height, DataWriter ^dw)
/* Do the search through the pages with an async task with progress callback */
Windows::Foundation::IAsyncOperationWithProgress<int, double>^
- mudocument::SearchDocumentWithProgressAsync(String^ textToFind, int dir, int start_page)
+ mudocument::SearchDocumentWithProgressAsync(String^ textToFind, int dir,
+ int start_page, int num_pages)
{
- return create_async([this, textToFind, dir, start_page](progress_reporter<double> reporter) -> int
+ return create_async([this, textToFind, dir, start_page, num_pages]
+ (progress_reporter<double> reporter) -> int
{
- int num_pages = this->GetNumPages();
double progress;
int box_count, result;
@@ -155,7 +160,6 @@ Windows::Foundation::IAsyncOperationWithProgress<int, double>^
}
}
reporter.report(100.0);
- /* Todo no matches found alert */
if (box_count == 0)
return TEXT_NOT_FOUND;
else
@@ -165,24 +169,47 @@ Windows::Foundation::IAsyncOperationWithProgress<int, double>^
/* Pack the page into a bmp stream */
Windows::Foundation::IAsyncOperation<InMemoryRandomAccessStream^>^
- mudocument::RenderPageAsync(int page_num, int width, int height, bool use_dlist)
+ mudocument::RenderPageAsync(int page_num, int bmp_width, int bmp_height,
+ bool use_dlist)
{
- return create_async([this, width, height, page_num, use_dlist](cancellation_token ct) -> InMemoryRandomAccessStream^
+ return create_async([this, bmp_width, bmp_height, page_num, use_dlist]
+ (cancellation_token ct) -> InMemoryRandomAccessStream^
{
/* Allocate space for bmp */
- Array<unsigned char>^ bmp_data = ref new Array<unsigned char>(height * 4 * width);
+ Array<unsigned char>^ bmp_data =
+ ref new Array<unsigned char>(bmp_height * 4 * bmp_width);
/* Set up the memory stream */
InMemoryRandomAccessStream ^ras = ref new InMemoryRandomAccessStream();
DataWriter ^dw = ref new DataWriter(ras->GetOutputStreamAt(0));
+ status_t code;
/* Go ahead and write our header data into the memory stream */
- Prepare_bmp(width, height, dw);
-
- std::lock_guard<std::mutex> lock(mutex_lock);
+ Prepare_bmp(bmp_width, bmp_height, dw);
- /* Get raster bitmap stream */
- status_t code = mu_object.RenderPage(page_num, width, height, &(bmp_data[0]),
- use_dlist);
+ if (use_dlist)
+ {
+ void *dlist;
+ int page_height;
+ int page_width;
+
+ mutex_lock.lock();
+ /* This lock will keep out issues in mupdf as well as race conditions
+ in the page cache */
+ dlist = (void*) mu_object.CreateDisplayList(page_num, &page_width,
+ &page_height);
+ /* Rendering of display list can occur with other threads so unlock */
+ mutex_lock.unlock();
+ code = mu_object.RenderPageMT(dlist, page_width, page_height,
+ &(bmp_data[0]), bmp_width, bmp_height);
+ }
+ else
+ {
+ /* Rendering in immediate mode. Keep lock in place */
+ mutex_lock.lock();
+ code = mu_object.RenderPage(page_num, &(bmp_data[0]), bmp_width,
+ bmp_height);
+ mutex_lock.unlock();
+ }
if (code != S_ISOK)
{
throw ref new FailureException("Page Rendering Failed");
@@ -200,11 +227,12 @@ Windows::Foundation::IAsyncOperation<InMemoryRandomAccessStream^>^
int mudocument::ComputeLinks(int page_num)
{
- std::lock_guard<std::mutex> lock(mutex_lock);
/* We get back a standard smart pointer from muctx interface and go to WinRT
type here */
sh_vector_link link_smart_ptr_vec(new std::vector<sh_link>());
+ mutex_lock.lock();
int num_items = mu_object.GetLinks(page_num, link_smart_ptr_vec);
+ mutex_lock.unlock();
if (num_items == 0)
return 0;
/* Pack into winRT type*/
@@ -237,13 +265,16 @@ Links^ mudocument::GetLink(int k)
int mudocument::ComputeTextSearch(String^ text, int page_num)
{
- std::lock_guard<std::mutex> lock(mutex_lock);
/* We get back a standard smart pointer from muctx interface and go to
* WinRT type here */
char* text_char = String_to_char(text);
sh_vector_text text_smart_ptr_vec(new std::vector<sh_text>());
+ int num_items;
+
+ mutex_lock.lock();
+ num_items = mu_object.GetTextSearch(page_num, text_char, text_smart_ptr_vec);
+ mutex_lock.unlock();
- int num_items = mu_object.GetTextSearch(page_num, text_char, text_smart_ptr_vec);
if (num_items == 0)
return 0;
/* Pack into winRT type*/
@@ -280,13 +311,14 @@ Links^ mudocument::GetTextSearch(int k)
int mudocument::ComputeContents()
{
- std::lock_guard<std::mutex> lock(mutex_lock);
/* We get back a standard smart pointer from muctx interface and go to
* WinRT type here */
-
sh_vector_content content_smart_ptr_vec(new std::vector<sh_content>());
+ int has_content;
- int has_content = mu_object.GetContents(content_smart_ptr_vec);
+ mutex_lock.lock();
+ has_content = mu_object.GetContents(content_smart_ptr_vec);
+ mutex_lock.unlock();
if (!has_content)
return 0;
@@ -315,6 +347,10 @@ ContentItem^ mudocument::GetContent(int k)
String^ mudocument::ComputeHTML(int page_num)
{
- std::lock_guard<std::mutex> lock(mutex_lock);
- return mu_object.GetHTML(page_num);
+ String^ html;
+
+ mutex_lock.lock();
+ html = mu_object.GetHTML(page_num);
+ mutex_lock.unlock();
+ return html;
}
diff --git a/platform/winrt/mupdfwinrt/mudocument.h b/platform/winrt/mupdfwinrt/mudocument.h
index bb4de722..eebe1fbe 100644
--- a/platform/winrt/mupdfwinrt/mudocument.h
+++ b/platform/winrt/mupdfwinrt/mudocument.h
@@ -35,7 +35,8 @@ namespace mupdfwinrt
Windows::Foundation::IAsyncOperation<InMemoryRandomAccessStream^>^
RenderPageAsync(int page_num, int width, int height, bool use_dlist);
Windows::Foundation::IAsyncOperationWithProgress<int, double>^
- SearchDocumentWithProgressAsync(String^ textToFind, int dir, int start_page);
+ SearchDocumentWithProgressAsync(String^ textToFind, int dir,
+ int start_page, int num_pages);
String^ ComputeHTML(int page_num);
int ComputeTextSearch(String^ text, int page_num);
Links^ GetTextSearch(int k);