ipe-7.2.13/0000755000175000017500000000000013561570220012234 5ustar otfriedotfriedipe-7.2.13/src/0000755000175000017500000000000013561570220013023 5ustar otfriedotfriedipe-7.2.13/src/ipeui/0000755000175000017500000000000013561570220014136 5ustar otfriedotfriedipe-7.2.13/src/ipeui/ipeui_cocoa.cpp0000644000175000017500000010731213561570220017125 0ustar otfriedotfried// -*- objc -*- // -------------------------------------------------------------------- // Lua bindings for Cocoa dialogs // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifdef IPESTRICT #include "../include/ipeosx.h" #endif #include "ipeui_common.h" #import #include "ipeuilayout_cocoa.h" #include #define COLORICONSIZE 12 inline const char *N2C(NSString *aStr) { return aStr.UTF8String; } inline NSString *C2N(const char *s) {return [NSString stringWithUTF8String:s];} inline NSString *S2N(const std::string &s) { return C2N(s.c_str()); } // -------------------------------------------------------------------- class PDialog; @interface IpeDialogDelegate : NSObject @property PDialog *dialog; - (void) ipeControl:(id) sender; @end // -------------------------------------------------------------------- void addToLayout(NSView *view, NSView *subview) { [view addSubview:subview]; [subview setTranslatesAutoresizingMaskIntoConstraints:NO]; } id layoutGuide(NSView *owner) { #if MAC_OS_X_VERSION_MAX_ALLOWED >= 101100 if ([owner respondsToSelector:@selector(addLayoutGuide:)]) { #pragma clang diagnostic push #pragma clang diagnostic ignored "-Wdeprecated-declarations" NSLayoutGuide *g = [[NSLayoutGuide alloc] init]; [owner addLayoutGuide:g]; #pragma clang diagnostic pop return g; } #endif NSView *g = [[NSView alloc] initWithFrame:NSZeroRect]; addToLayout(owner, g); return g; } static NSLayoutAttribute layoutAttribute(char ch) { switch (ch) { case 'l': return NSLayoutAttributeLeft; case 'r': return NSLayoutAttributeRight; case 't': return NSLayoutAttributeTop; case 'b': return NSLayoutAttributeBottom; case 'w': return NSLayoutAttributeWidth; case 'h': return NSLayoutAttributeHeight; case 'x': return NSLayoutAttributeCenterX; case 'y': return NSLayoutAttributeCenterY; default: return NSLayoutAttributeNotAnAttribute; } } static NSLayoutRelation layoutRelation(char ch) { switch (ch) { case '<': return NSLayoutRelationLessThanOrEqual; case '=': default: return NSLayoutRelationEqual; case '>': return NSLayoutRelationGreaterThanOrEqual; } } static NSView *owner(id a) { if ([a respondsToSelector:@selector(superview)]) return [a superview]; #if MAC_OS_X_VERSION_MAX_ALLOWED >= 101100 if ([a respondsToSelector:@selector(owningView)]) return [a owningView]; // is a layout guide #endif return nil; } void activateConstraint(NSLayoutConstraint *c, BOOL active) { #if MAC_OS_X_VERSION_MAX_ALLOWED >= 101000 if ([c respondsToSelector:@selector(setActive:)]) { #pragma clang diagnostic push #pragma clang diagnostic ignored "-Wdeprecated-declarations" c.active = active; #pragma clang diagnostic pop return; } #endif // need to figure out lowest common ancestor id a = c.firstItem; id b = c.secondItem; NSView *lca = nil; NSView *ao = owner(a); NSView *bo = owner(b); if (b == nil) lca = a; else if (ao == b) lca = b; else if (bo == a) lca = a; else { assert(ao == bo); lca = ao; } if (active) [lca addConstraint:c]; else [lca removeConstraint:c]; } NSLayoutConstraint *layout(id a, id b, const char *rel, double gap, double multiplier, BOOL activate) { assert(strlen(rel) == 3); NSLayoutAttribute a1 = layoutAttribute(rel[0]); NSLayoutAttribute b1 = layoutAttribute(rel[2]); NSLayoutConstraint *c = [NSLayoutConstraint constraintWithItem:a attribute:a1 relatedBy:layoutRelation(rel[1]) toItem:b attribute:b1 multiplier:multiplier constant:gap]; if (activate) activateConstraint(c, YES); return c; } // -------------------------------------------------------------------- // Exported from ipeui! NSString *ipeui_set_mnemonic(NSString *title, NSButton *button) { unichar mnemonic = 0; NSMutableString *result = [NSMutableString stringWithCapacity:[title length]]; size_t i = 0; while (i < [title length]) { unichar ch = [title characterAtIndex:i]; if (ch != '&') { [result appendFormat:@"%C", ch]; ++i; } else if (i + 1 < [title length]) { ch = [title characterAtIndex:i+1]; if (!mnemonic && ch != '&') mnemonic = ch; [result appendFormat:@"%C", ch]; i += 2; } else ++i; // discard trailing & } if (button) { [button setTitle:result]; if (mnemonic) { [button setKeyEquivalent:[NSString stringWithCharacters:&mnemonic length:1]]; [button setKeyEquivalentModifierMask:NSAlternateKeyMask|NSCommandKeyMask]; } } return result; } // -------------------------------------------------------------------- class PDialog : public Dialog { public: PDialog(lua_State *L0, WINID parent, const char *caption); virtual ~PDialog(); void itemAction(int idx); int numberOfRows(int idx); NSString *row(int idx, int row); virtual void setMapped(lua_State *L, int idx); virtual bool buildAndRun(int w, int h); virtual void retrieveValues(); virtual void enableItem(int idx, bool value); virtual void acceptDialog(lua_State *L); private: void fillComboBox(NSPopUpButton *cb, int idx); void setTextView(NSTextView *tv, const std::string &s); std::string getTextView(NSTextView *tv); void layoutControls(); private: NSPanel *iPanel; IpeDialogDelegate *iDelegate; NSMutableArray *iViews; }; // -------------------------------------------------------------------- @implementation IpeDialogDelegate - (void) ipeControl:(id) sender { self.dialog->itemAction([sender tag]); } - (BOOL) windowShouldClose:(id) sender { [NSApp stopModalWithCode:0]; return YES; } - (void) tableViewSelectionDidChange:(NSNotification *) notification { self.dialog->itemAction([[notification object] tag]); } - (NSInteger) numberOfRowsInTableView:(NSTableView *) tv { return self.dialog->numberOfRows([tv tag]); } - (id) tableView:(NSTableView *) tv objectValueForTableColumn:(NSTableColumn *) col row:(NSInteger)row { return self.dialog->row([tv tag], row); } - (NSView *) tableView:(NSTableView *) tv viewForTableColumn:(NSTableColumn *) col row:(NSInteger) row { NSTextField *result = [tv makeViewWithIdentifier:@"DialogList" owner:self]; if (result == nil) { result = [[NSTextField alloc] initWithFrame:NSMakeRect(0., 0., 200., 20.)]; result.identifier = @"DialogList"; result.editable = NO; result.bordered = NO; result.drawsBackground = NO; } [result setStringValue:self.dialog->row([tv tag], row)]; return result; } @end // -------------------------------------------------------------------- PDialog::PDialog(lua_State *L0, WINID parent, const char *caption) : Dialog(L0, parent, caption) { // } PDialog::~PDialog() { // } void PDialog::acceptDialog(lua_State *L) { int accept = lua_toboolean(L, 2); [NSApp stopModalWithCode:accept]; [iPanel close]; } void PDialog::itemAction(int idx) { SElement &m = iElements[idx]; if (m.flags & EAccept) { [NSApp stopModalWithCode:true]; [iPanel close]; } else if (m.flags & EReject) { [NSApp stopModalWithCode:false]; [iPanel close]; } else if (m.lua_method != LUA_NOREF) callLua(m.lua_method); } int PDialog::numberOfRows(int idx) { return iElements[idx].items.size(); } NSString *PDialog::row(int idx, int row) { return S2N(iElements[idx].items[row]); } void PDialog::setMapped(lua_State *L, int idx) { SElement &m = iElements[idx]; NSView *ctrl = iViews[idx]; switch (m.type) { case ELabel: case EInput: [((NSTextField *) ctrl) setStringValue:S2N(m.text)]; break; case ETextEdit: setTextView((NSTextView *) ctrl, m.text); break; case ECheckBox: [((NSButton *) ctrl) setState:m.value]; break; case EList: // listbox gets items directly from items array [((NSTableView *) ctrl) reloadData]; [((NSTableView *) ctrl) selectRowIndexes:[NSIndexSet indexSetWithIndex:m.value] byExtendingSelection:NO]; break; case ECombo: { NSPopUpButton *b = (NSPopUpButton *) ctrl; if (lua_istable(L, 3)) fillComboBox(b, idx); [b selectItemAtIndex:m.value]; } break; default: break; // EButton } } void PDialog::retrieveValues() { for (int i = 0; i < int(iElements.size()); ++i) { SElement &m = iElements[i]; NSView *ctrl = iViews[i]; switch (m.type) { case EInput: m.text = N2C([((NSTextField *) ctrl) stringValue]); break; case ETextEdit: m.text = getTextView((NSTextView *) ctrl); break; case EList: m.value = [((NSTableView *) ctrl) selectedRow]; break; case ECombo: m.value = [((NSPopUpButton *) ctrl) indexOfSelectedItem]; break; case ECheckBox: m.value = [((NSButton *) ctrl) intValue]; break; default: break; // label and button - nothing to do } } } void PDialog::enableItem(int idx, bool value) { if (iElements[idx].type != ETextEdit) [((NSControl *) iViews[idx]) setEnabled:value]; } void PDialog::fillComboBox(NSPopUpButton *cb, int idx) { SElement &m = iElements[idx]; [cb removeAllItems]; for (int k = 0; k < int(m.items.size()); ++k) [cb addItemWithTitle:S2N(m.items[k])]; } void PDialog::setTextView(NSTextView *tv, const std::string &s) { NSAttributedString *n = [[NSAttributedString alloc] initWithString:S2N(s)]; [[tv textStorage] setAttributedString:n]; tv.textColor = [NSColor textColor]; } std::string PDialog::getTextView(NSTextView *tv) { return std::string(N2C([[tv textStorage] string])); } // -------------------------------------------------------------------- void PDialog::layoutControls() { double gap = 12.0; int buttonGap = 12.0; NSView *content = [iPanel contentView]; // create row guides NSMutableArray *rows = [NSMutableArray arrayWithCapacity:iNoRows]; for (int i = 0; i < iNoRows; ++i) { id g = layoutGuide(content); layout(content, g, "l=l"); layout(g, content, "r=r"); if (i > 0) layout(g, rows[i-1], "t=b", gap); [rows addObject:g]; } layout(rows[0], content, "t=t", gap); // create column guides NSMutableArray *cols = [NSMutableArray arrayWithCapacity:iNoCols]; for (int i = 0; i < iNoCols; ++i) { id g = layoutGuide(content); layout(content, g, "t=t"); layout(g, rows[iNoRows-1], "b=b"); if (i > 0) layout(g, cols[i-1], "l=r", gap); [cols addObject:g]; } layout(cols[0], content, "l=l", gap); layout(content, cols[iNoCols-1], "r=r", gap); // layout buttons NSView *lastButton = nil; int bcount = 0; for (size_t i = 0; i < iElements.size(); ++i) { SElement &m = iElements[i]; if (m.row >= 0) continue; NSView *w = iViews[i]; ++bcount; layout(w, rows[iNoRows-1], "t=b", buttonGap); layout(content, w, "b=b", buttonGap); if (lastButton) { if (bcount == 3) layout(lastButton, w, "l>r", buttonGap); else layout(lastButton, w, "l=r", buttonGap); layout(w, lastButton, "w=w"); } else layout(content, w, "r=r", buttonGap); lastButton = w; } if (bcount > 2) layout(lastButton, content, "l=l", buttonGap); else if (bcount) layout(lastButton, content, "l>l", buttonGap); else // no button added using "addButton". Probably an old ipelet. layout(content, rows[iNoRows-1], "b=b", gap); while (int(iColStretch.size()) < iNoCols) iColStretch.push_back(0); while (int(iRowStretch.size()) < iNoRows) iRowStretch.push_back(0); // layout rows and columns for (size_t i = 0; i < iElements.size(); ++i) { SElement &m = iElements[i]; if (m.row < 0) continue; NSView *w = iViews[i]; if (m.type == EList || m.type == ETextEdit) w = [[w superview] superview]; layout(w, rows[m.row], "t=t"); if (m.type == ECombo || m.type == ECheckBox) layout(rows[m.row + m.rowspan - 1], w, "b>b"); else layout(rows[m.row + m.rowspan - 1], w, "b=b"); layout(w, cols[m.col], "l=l"); layout(w, cols[m.col + m.colspan - 1], "r=r"); if (m.type == EInput || m.type == ETextEdit) layout(w, nil, "w>0", 100); // does it have stretch? BOOL rowStretch = NO; for (int r = m.row; r < m.row + m.rowspan; ++r) if (iRowStretch[r] > 0) rowStretch = YES; BOOL colStretch = NO; for (int c = m.col; c < m.col + m.colspan; ++c) if (iColStretch[c] > 0) colStretch = YES; NSLayoutPriority rowpri = rowStretch ? 250.0 : 750.0; NSLayoutPriority colpri = colStretch ? 250.0 : 550.0; [w setContentHuggingPriority:rowpri forOrientation:NSLayoutConstraintOrientationVertical]; [w setContentHuggingPriority:colpri forOrientation:NSLayoutConstraintOrientationHorizontal]; } // make columns with stretch 1 equally wide NSView *g1 = nil; for (int i = 0; i < iNoCols; ++i) { if (iColStretch[i] == 1) { if (g1 == nil) g1 = cols[i]; else layout(g1, cols[i], "w=w"); } } } // -------------------------------------------------------------------- bool PDialog::buildAndRun(int w, int h) { NSUInteger style = NSTitledWindowMask|NSResizableWindowMask; if (!iIgnoreEscape) style |= NSClosableWindowMask; iPanel = [[NSPanel alloc] initWithContentRect:NSMakeRect(400.,800., w, h) styleMask:style backing:NSBackingStoreBuffered defer:YES]; [iPanel setTitle:S2N(iCaption)]; hDialog = iPanel; iDelegate = [[IpeDialogDelegate alloc] init]; [iDelegate setDialog:this]; [iPanel setDelegate:iDelegate]; iViews = [NSMutableArray arrayWithCapacity:iElements.size()]; NSView *content = [iPanel contentView]; NSView *focusCtrl = nil; for (int i = 0; i < int(iElements.size()); ++i) { SElement &m = iElements[i]; NSControl *ctrl = nil; NSView *view = nil; NSScrollView *scroll = nil; if (m.row < 0) { NSButton *b = [[NSButton alloc] initWithFrame:NSZeroRect]; [b setButtonType:NSMomentaryPushInButton]; ipeui_set_mnemonic(S2N(m.text), b); [b setImagePosition:NSNoImage]; [b setBezelStyle:NSRoundedBezelStyle]; ctrl = b; if (m.flags & EAccept) { [b setKeyEquivalent:@"\r"]; [b setKeyEquivalentModifierMask:NSCommandKeyMask]; } } else { switch (m.type) { case ELabel: { NSTextField *t = [[NSTextField alloc] initWithFrame:NSZeroRect]; t.stringValue= S2N(m.text); t.bordered= NO; t.drawsBackground = NO; t.editable = NO; ctrl = t; } break; case EButton: { NSButton *b = [[NSButton alloc] initWithFrame:NSZeroRect]; [b setButtonType:NSMomentaryPushInButton]; ipeui_set_mnemonic(S2N(m.text), b); [b setImagePosition:NSNoImage]; [b setBezelStyle:NSRoundedBezelStyle]; ctrl = b; } break; case ECheckBox: { NSButton *b = [[NSButton alloc] initWithFrame:NSZeroRect]; [b setButtonType:NSSwitchButton]; ipeui_set_mnemonic(S2N(m.text), b); [b setState:m.value ? NSOnState : NSOffState]; ctrl = b; } break; case EInput: { NSTextField *t = [[NSTextField alloc] initWithFrame:NSZeroRect]; [t setStringValue:S2N(m.text)]; if (m.flags & ESelectAll) [t selectText:content]; ctrl = t; } break; case ETextEdit: { scroll = [[NSScrollView alloc] initWithFrame:NSZeroRect]; NSTextView *tv = [[NSTextView alloc] initWithFrame:NSZeroRect]; tv.editable = !(m.flags & (EReadOnly|EDisabled)); tv.richText = NO; tv.allowsUndo = YES; tv.continuousSpellCheckingEnabled = !!(m.flags & ESpellCheck); tv.automaticSpellingCorrectionEnabled = NO; tv.automaticQuoteSubstitutionEnabled = NO; tv.automaticTextReplacementEnabled = NO; tv.automaticDataDetectionEnabled = NO; tv.automaticDashSubstitutionEnabled = NO; setTextView(tv, m.text); view = tv; } break; case ECombo: { NSPopUpButton *b = [[NSPopUpButton alloc] initWithFrame:NSZeroRect pullsDown:NO]; fillComboBox(b, i); [b selectItemAtIndex:m.value]; ctrl = b; } break; case EList: { scroll = [[NSScrollView alloc] initWithFrame:NSZeroRect]; NSTableView *tv = [[NSTableView alloc] initWithFrame:NSZeroRect]; NSTableColumn *column = [[NSTableColumn alloc] initWithIdentifier:@"col1"]; [tv addTableColumn:column]; [tv setTag:i]; // needed before adding data source [tv setDataSource:iDelegate]; [tv setHeaderView:nil]; [tv selectRowIndexes:[NSIndexSet indexSetWithIndex:m.value] byExtendingSelection:NO]; [tv setDelegate:iDelegate]; ctrl = tv; } break; default: break; } } if (ctrl) { ctrl.enabled = !(m.flags & EDisabled); ctrl.tag = i; if (m.type != EList) { ctrl.action = @selector(ipeControl:); ctrl.target = iDelegate; } view = ctrl; } if (m.flags & EFocused) focusCtrl = view; if (scroll) { [view setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable]; [scroll setDocumentView:view]; scroll.hasVerticalScroller = YES; layout(scroll, nil, "h>0", 100.0); layout(scroll, nil, "w>0", 160.0); } [view setContentCompressionResistancePriority:NSLayoutPriorityRequired forOrientation:NSLayoutConstraintOrientationVertical]; [iViews addObject:view]; addToLayout(content, scroll ? scroll : view); } layoutControls(); // set keyboard focus if (focusCtrl) [iPanel makeFirstResponder:focusCtrl]; // this is such a hack, but it seems to work for Ipe NSMenu *editMenu = [[[NSApp mainMenu] itemAtIndex:2] submenu]; NSMenuItem *undoItem = [editMenu itemAtIndex:0]; NSMenuItem *redoItem = [editMenu itemAtIndex:1]; undoItem.action = @selector(undo:); redoItem.action = @selector(redo:); int result = [NSApp runModalForWindow:iPanel]; retrieveValues(); // for future reference undoItem.action = @selector(ipeMenuAction:); redoItem.action = @selector(ipeMenuAction:); iPanel = nil; return result; } // -------------------------------------------------------------------- static int dialog_constructor(lua_State *L) { WINID parent = check_winid(L, 1); const char *s = luaL_checkstring(L, 2); Dialog **dlg = (Dialog **) lua_newuserdata(L, sizeof(Dialog *)); *dlg = nullptr; luaL_getmetatable(L, "Ipe.dialog"); lua_setmetatable(L, -2); *dlg = new PDialog(L, parent, s); return 1; } // -------------------------------------------------------------------- void editor_thread(const char *cmd) { int result = std::system(cmd); (void) result; [NSApp abortModal]; } static int ipeui_wait(lua_State *L) { const char *cmd = luaL_checkstring(L, 2); NSPanel *panel = [[NSPanel alloc] initWithContentRect:NSMakeRect(400.,800., 200, 100) styleMask:NSTitledWindowMask backing:NSBackingStoreBuffered defer:YES]; panel.title = @"Ipe: waiting"; NSTextField *l = [[NSTextField alloc] initWithFrame:NSMakeRect(0., 0., 200., 100.)]; l.stringValue = @"Waiting for external editor"; l.editable = NO; l.bordered = NO; l.drawsBackground = NO; panel.contentView = l; std::thread t(editor_thread, cmd); [NSApp runModalForWindow:panel]; [panel close]; t.join(); return 0; } // -------------------------------------------------------------------- class PMenu; @interface IpePopupMenuItem : NSMenuItem @property NSString *ipeName; // name of single item @property int ipeSubmenuIndex; // index of item in submenu @property NSString *ipeSubmenuName; // name of item in submenu @property PMenu *ipeMenu; - (void) ipePopupAction:(id) sender; @end class PMenu : public Menu { public: PMenu(); virtual int add(lua_State *L); virtual int execute(lua_State *L); void itemSelected(IpePopupMenuItem *item); private: NSMenu *iMenu; IpePopupMenuItem __unsafe_unretained *iSelected; }; // -------------------------------------------------------------------- @implementation IpePopupMenuItem - (void) ipePopupAction:(id) sender { IpePopupMenuItem *item = (IpePopupMenuItem *) sender; self.ipeMenu->itemSelected(item); } @end // -------------------------------------------------------------------- PMenu::PMenu() { iMenu = [[NSMenu alloc] init]; } void PMenu::itemSelected(IpePopupMenuItem *item) { iSelected = item; } int PMenu::execute(lua_State *L) { NSPoint p = { luaL_checknumber(L, 2), luaL_checknumber(L, 3) }; iSelected = nil; BOOL result = [iMenu popUpMenuPositioningItem:nil atLocation:p inView:nil]; if (result && iSelected) { lua_pushstring(L, N2C(iSelected.ipeName)); lua_pushinteger(L, iSelected.ipeSubmenuIndex); if (iSelected.ipeSubmenuName) lua_pushstring(L, N2C(iSelected.ipeSubmenuName)); else lua_pushliteral(L, ""); return 3; } else return 0; } NSImage *colorIcon(double red, double green, double blue, int pixels) { NSImage *icon = [NSImage imageWithSize:NSMakeSize(pixels, pixels) flipped:NO drawingHandler:^(NSRect rect) { CGContextRef myContext = [[NSGraphicsContext currentContext] CGContext]; CGContextSetRGBFillColor(myContext, red, green, blue, 1.0); CGContextFillRect(myContext, CGRectMake(0, 0, pixels, pixels)); return YES; }]; return icon; } int PMenu::add(lua_State *L) { const char *name = luaL_checkstring(L, 2); const char *title = luaL_checkstring(L, 3); if (lua_gettop(L) == 3) { IpePopupMenuItem *item = [[IpePopupMenuItem alloc] initWithTitle:ipeui_set_mnemonic(C2N(title),nil) action:@selector(ipePopupAction:) keyEquivalent:@""]; [item setIpeName:C2N(name)]; [item setIpeSubmenuIndex:0]; [item setTarget:item]; [item setIpeMenu:this]; [iMenu addItem:item]; } else { luaL_argcheck(L, lua_istable(L, 4), 4, "argument is not a table"); bool hasmap = !lua_isnoneornil(L, 5) && lua_isfunction(L, 5); bool hastable = !hasmap && !lua_isnoneornil(L, 5); bool hascolor = !lua_isnoneornil(L, 6) && lua_isfunction(L, 6); bool hascheck = !hascolor && !lua_isnoneornil(L, 6); if (hastable) luaL_argcheck(L, lua_istable(L, 5), 5, "argument is not a function or table"); const char *current = nullptr; if (hascheck) { luaL_argcheck(L, lua_isstring(L, 6), 6, "argument is not a function or string"); current = luaL_checkstring(L, 6); } NSMenu *sm = [[NSMenu alloc] initWithTitle:C2N(title)]; if (hascolor) [sm setShowsStateColumn:NO]; int no = lua_rawlen(L, 4); for (int i = 1; i <= no; ++i) { lua_rawgeti(L, 4, i); luaL_argcheck(L, lua_isstring(L, -1), 4, "items must be strings"); const char *label = lua_tostring(L, -1); if (hastable) { lua_rawgeti(L, 5, i); luaL_argcheck(L, lua_isstring(L, -1), 5, "labels must be strings"); } else if (hasmap) { lua_pushvalue(L, 5); // function lua_pushnumber(L, i); // index lua_pushvalue(L, -3); // name lua_call(L, 2, 1); // function returns label luaL_argcheck(L, lua_isstring(L, -1), 5, "function does not return string"); } else lua_pushvalue(L, -1); const char *text = lua_tostring(L, -1); IpePopupMenuItem *item = [[IpePopupMenuItem alloc] initWithTitle:ipeui_set_mnemonic(C2N(text),nil) action:@selector(ipePopupAction:) keyEquivalent:@""]; [item setIpeName:C2N(name)]; [item setIpeSubmenuIndex:i]; [item setIpeSubmenuName:C2N(label)]; [item setTarget:item]; [item setIpeMenu:this]; if (hascheck && !strcmp(label, current)) [item setState:NSOnState]; [sm addItem:item]; if (hascolor) { lua_pushvalue(L, 6); // function lua_pushnumber(L, i); // index lua_pushvalue(L, -4); // name lua_call(L, 2, 3); // function returns red, green, blue double red = luaL_checknumber(L, -3); double green = luaL_checknumber(L, -2); double blue = luaL_checknumber(L, -1); lua_pop(L, 3); // pop result NSImage *im = colorIcon(red, green, blue, COLORICONSIZE); [item setImage:im]; } lua_pop(L, 2); // item, text } NSMenuItem *mitem = [[NSMenuItem alloc] initWithTitle:ipeui_set_mnemonic(C2N(title),nil) action:nullptr keyEquivalent:@""]; [mitem setSubmenu:sm]; [iMenu addItem:mitem]; } return 0; } // -------------------------------------------------------------------- static int menu_constructor(lua_State *L) { // check_winid(L, 1); Menu **m = (Menu **) lua_newuserdata(L, sizeof(Menu *)); *m = nullptr; luaL_getmetatable(L, "Ipe.menu"); lua_setmetatable(L, -2); *m = new PMenu(); return 1; } // -------------------------------------------------------------------- class PTimer; @interface IpeTimerDelegate : NSObject @property PTimer *ptimer; - (void) fired:(NSTimer *) timer; @end class PTimer : public Timer { public: PTimer(lua_State *L0, int lua_object, const char *method); virtual int setInterval(lua_State *L); virtual int active(lua_State *L); virtual int start(lua_State *L); virtual int stop(lua_State *L); void fired(); private: int iInterval; NSTimer *iTimer; IpeTimerDelegate *iDelegate; }; // -------------------------------------------------------------------- @implementation IpeTimerDelegate - (void) fired:(NSTimer *) timer { self.ptimer->fired(); } @end PTimer::PTimer(lua_State *L0, int lua_object, const char *method) : Timer(L0, lua_object, method) { iTimer = nil; iInterval = 0; iDelegate = [[IpeTimerDelegate alloc] init]; iDelegate.ptimer = this; } void PTimer::fired() { callLua(); } int PTimer::setInterval(lua_State *L) { iInterval = int(luaL_checkinteger(L, 2)); return 0; } int PTimer::active(lua_State *L) { lua_pushboolean(L, iTimer && [iTimer isValid]); return 1; } int PTimer::start(lua_State *L) { if (iTimer) luaL_argerror(L, 1, "timer is already started"); iTimer = [NSTimer scheduledTimerWithTimeInterval:iInterval / 1000.0 target:iDelegate selector:@selector(fired:) userInfo:nil repeats:!iSingleShot]; return 0; } int PTimer::stop(lua_State *L) { if (iTimer) [iTimer invalidate]; iTimer = nil; return 0; } // -------------------------------------------------------------------- static int timer_constructor(lua_State *L) { luaL_argcheck(L, lua_istable(L, 1), 1, "argument is not a table"); const char *method = luaL_checkstring(L, 2); Timer **t = (Timer **) lua_newuserdata(L, sizeof(Timer *)); *t = nullptr; luaL_getmetatable(L, "Ipe.timer"); lua_setmetatable(L, -2); // create a table with weak reference to Lua object lua_createtable(L, 1, 1); lua_pushliteral(L, "v"); lua_setfield(L, -2, "__mode"); lua_pushvalue(L, -1); lua_setmetatable(L, -2); lua_pushvalue(L, 1); lua_rawseti(L, -2, 1); int lua_object = luaL_ref(L, LUA_REGISTRYINDEX); *t = new PTimer(L, lua_object, method); return 1; } // -------------------------------------------------------------------- static NSArray *make_filters(const char *s) { NSMutableArray *exts = [NSMutableArray arrayWithCapacity:10]; const char *p = s; while (*p) { p += 2; // skip *. const char *q = p; while (*q && *q != ';') ++q; NSString *ext = [[NSString alloc] initWithBytes:p length:q-p encoding:NSUTF8StringEncoding]; [exts addObject:ext]; if (*q == ';') ++q; p = q; } return exts; } @interface IpeFileDialogHelper : NSObject @property (weak) NSSavePanel *panel; @property NSPopUpButton *fileType; @property NSMutableArray *filters; - (instancetype) initFor:(NSSavePanel *) panel; - (void) setupWithLua:(lua_State *) L; - (void) changeFileType:(id) sender; @end @implementation IpeFileDialogHelper - (instancetype) initFor:(NSSavePanel *) panel { self = [super init]; if (self) { _panel = panel; } return self; } - (void) changeFileType:(id) sender { [self setFilter:[self.fileType indexOfSelectedItem]]; } - (void) setupWithLua:(lua_State *) L { self.panel.message = C2N(luaL_checkstring(L, 3)); if (!lua_isnoneornil(L, 5)) { const char *dir = luaL_checkstring(L, 5); self.panel.directoryURL = [NSURL fileURLWithPath:C2N(dir) isDirectory:YES]; } if (!lua_isnoneornil(L, 6)) { auto url = [NSURL fileURLWithPath:C2N(luaL_checkstring(L, 6))]; self.panel.nameFieldStringValue = [url lastPathComponent]; } self.panel.canCreateDirectories = YES; self.panel.showsTagField = NO; self.panel.canSelectHiddenExtension = YES; self.fileType = [[NSPopUpButton alloc] initWithFrame:NSMakeRect(0., 0., 200.0, 40.0) pullsDown:NO]; self.fileType.target = self; self.fileType.action = @selector(changeFileType:); self.panel.accessoryView = self.fileType; if (!lua_istable(L, 4)) luaL_argerror(L, 4, "table expected for filters"); int nFilters = lua_rawlen(L, 4); self.filters = [NSMutableArray arrayWithCapacity:nFilters/2]; for (int i = 1; i <= nFilters; ++i) { lua_rawgeti(L, 4, i); luaL_argcheck(L, lua_isstring(L, -1), 4, "filter entry is not a string"); const char *s = lua_tostring(L, -1); if (i % 2 == 1) [self.fileType addItemWithTitle:C2N(s)]; else [self.filters addObject:make_filters(s)]; lua_pop(L, 1); // element i } int selected = 0; if (!lua_isnoneornil(L, 7)) selected = luaL_checkinteger(L, 7) - 1; [self.fileType selectItemAtIndex:selected]; [self setFilter:selected]; } - (void) setFilter:(int) filterIndex { if ([self.filters[filterIndex][0] isEqualToString:@"*"]) self.panel.allowedFileTypes = nil; else self.panel.allowedFileTypes = self.filters[filterIndex]; } @end static int ipeui_fileDialog(lua_State *L) { static const char * const typenames[] = { "open", "save", nullptr }; // not needed: NSWindow *win = check_winid(L, 1); int type = luaL_checkoption(L, 2, nullptr, typenames); if (type == 0) { // open file NSOpenPanel *panel = [NSOpenPanel openPanel]; IpeFileDialogHelper *helper = [[IpeFileDialogHelper alloc] initFor:panel]; [helper setupWithLua:L]; if ([panel runModal] == NSFileHandlingPanelOKButton) { lua_pushstring(L, N2C([[panel URLs][0] path])); lua_pushinteger(L, [helper.fileType indexOfSelectedItem] + 1); return 2; } } else { // save file NSSavePanel *panel = [NSSavePanel savePanel]; IpeFileDialogHelper *helper = [[IpeFileDialogHelper alloc] initFor:panel]; [helper setupWithLua:L]; if ([panel runModal] == NSFileHandlingPanelOKButton) { lua_pushstring(L, N2C([[panel URL] path])); lua_pushinteger(L, [helper.fileType indexOfSelectedItem] + 1); return 2; } } return 0; } // -------------------------------------------------------------------- static int ipeui_getColor(lua_State *L) { NSWindow *win = check_winid(L, 1); NSColorPanel *panel = [NSColorPanel sharedColorPanel]; if ([panel isVisible]) { NSColor *rgb = [panel color]; lua_pushnumber(L, rgb.redComponent); lua_pushnumber(L, rgb.greenComponent); lua_pushnumber(L, rgb.blueComponent); return 3; } else { const char *title = luaL_checkstring(L, 2); double r = luaL_checknumber(L, 3); double g = luaL_checknumber(L, 4); double b = luaL_checknumber(L, 5); NSColor *rgb = [NSColor colorWithRed:r green:g blue:b alpha:1.0]; [panel setColor:rgb]; [panel setTitle:C2N(title)]; [panel orderFront:win]; return 0; } } // -------------------------------------------------------------------- static int ipeui_messageBox(lua_State *L) { static const char * const options[] = { "none", "warning", "information", "question", "critical", nullptr }; static const char * const buttontype[] = { "ok", "okcancel", "yesnocancel", "discardcancel", "savediscardcancel", nullptr }; NSWindow *win = check_winid(L, 1); int type = luaL_checkoption(L, 2, "none", options); const char *text = luaL_checkstring(L, 3); const char *details = nullptr; if (!lua_isnoneornil(L, 4)) details = luaL_checkstring(L, 4); int buttons = 0; if (lua_isnumber(L, 5)) buttons = (int)luaL_checkinteger(L, 5); else if (!lua_isnoneornil(L, 5)) buttons = luaL_checkoption(L, 5, nullptr, buttontype); (void) win; NSAlert *alert = [[NSAlert alloc] init]; [alert setMessageText:C2N(text)]; if (details) [alert setInformativeText:C2N(details)]; NSAlertStyle astyle = NSInformationalAlertStyle; switch (type) { case 0: default: break; case 1: astyle = NSWarningAlertStyle; break; case 2: break; case 3: // Question doesn't seem to exist on Cocoa break; case 4: astyle = NSCriticalAlertStyle; break; } [alert setAlertStyle:astyle]; switch (buttons) { case 0: default: break; case 1: [alert addButtonWithTitle:@"Ok"]; [alert addButtonWithTitle:@"Cancel"]; break; case 2: [alert addButtonWithTitle:@"Yes"]; [alert addButtonWithTitle:@"No"]; [alert addButtonWithTitle:@"Cancel"]; break; case 3: [alert addButtonWithTitle:@"Discard"]; [alert addButtonWithTitle:@"Cancel"]; break; case 4: [alert addButtonWithTitle:@"Save"]; [alert addButtonWithTitle:@"Discard"]; [alert addButtonWithTitle:@"Cancel"]; break; } switch ([alert runModal]) { case NSAlertFirstButtonReturn: lua_pushnumber(L, 1); break; case NSAlertSecondButtonReturn: if (buttons == 2 || buttons == 4) lua_pushnumber(L, 0); else lua_pushnumber(L, -1); break; case NSAlertThirdButtonReturn: default: lua_pushnumber(L, -1); break; } return 1; } // -------------------------------------------------------------------- static int ipeui_currentDateTime(lua_State *L) { NSDate *now = [NSDate date]; NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierGregorian]; unsigned unitFlags = NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay | NSCalendarUnitHour | NSCalendarUnitMinute | NSCalendarUnitSecond; NSDateComponents *st = [gregorian components:unitFlags fromDate:now]; char buf[16]; sprintf(buf, "%04ld%02ld%02ld%02ld%02ld%02ld", long(st.year), long(st.month), long(st.day), long(st.hour), long(st.minute), long(st.second)); lua_pushstring(L, buf); return 1; } static int ipeui_startBrowser(lua_State *L) { const char *url = luaL_checkstring(L, 1); int res = [[NSWorkspace sharedWorkspace] openURL:[NSURL URLWithString:C2N(url)]]; lua_pushboolean(L, res); return 1; } // -------------------------------------------------------------------- static const struct luaL_Reg ipeui_functions[] = { { "waitDialog", ipeui_wait }, { "Dialog", dialog_constructor }, { "Timer", timer_constructor }, { "Menu", menu_constructor }, { "fileDialog", ipeui_fileDialog }, { "getColor", ipeui_getColor }, { "messageBox", ipeui_messageBox }, { "currentDateTime", ipeui_currentDateTime }, { "startBrowser", ipeui_startBrowser }, { nullptr, nullptr } }; // -------------------------------------------------------------------- int luaopen_ipeui(lua_State *L) { luaL_newlib(L, ipeui_functions); lua_setglobal(L, "ipeui"); luaopen_ipeui_common(L); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipeui/ipeuilayout_cocoa.h0000644000175000017500000000320013561570220020017 0ustar otfriedotfried// -*- objc -*- // ipeuilayout_cocoa.h /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEUILAYOUT_H #define IPEUILAYOUT_H extern void addToLayout(NSView *view, NSView *subview); extern id layoutGuide(NSView *owner); extern void activateConstraint(NSLayoutConstraint *c, BOOL active); extern NSLayoutConstraint *layout(id a, id b, const char *rel, double gap = 0.0, double multiplier=1.0, BOOL activate=YES); extern NSString *ipeui_set_mnemonic(NSString *title, NSButton *button); // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipeui/ipeui_qt.cpp0000644000175000017500000005666013561570220016476 0ustar otfriedotfried// -------------------------------------------------------------------- // Lua bindings for Qt dialogs // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeui_qt.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include // -------------------------------------------------------------------- inline void push_string(lua_State *L, const QString &str) { lua_pushstring(L, str.toUtf8()); } inline QString toqstring(lua_State *L, int i) { return QString::fromUtf8(lua_tostring(L, i)); } inline QString checkqstring(lua_State *L, int i) { return QString::fromUtf8(luaL_checkstring(L, i)); } // -------------------------------------------------------------------- class XmlHighlighter : public QSyntaxHighlighter { public: XmlHighlighter(QTextEdit *textEdit); protected: void applyFormat(const QString &text, QRegExp &exp, const QTextCharFormat &format); virtual void highlightBlock(const QString &text); }; void XmlHighlighter::applyFormat(const QString &text, QRegExp &exp, const QTextCharFormat &format) { int index = text.indexOf(exp); while (index >= 0) { int length = exp.matchedLength(); setFormat(index, length, format); index = text.indexOf(exp, index + length); } } void XmlHighlighter::highlightBlock(const QString &text) { QTextCharFormat tagFormat, stringFormat, numberFormat; tagFormat.setFontWeight(QFont::Bold); tagFormat.setForeground(Qt::blue); stringFormat.setForeground(Qt::darkMagenta); numberFormat.setForeground(Qt::red); QRegExp tagExp( "<.*>" ); QRegExp stringExp( "\"[a-zA-Z]*\"" ); QRegExp numberExp( "[+|-]*[0-9]*.[0-9][0-9]*" ); applyFormat(text, tagExp, tagFormat); applyFormat(text, stringExp, stringFormat); applyFormat(text, numberExp, numberFormat); } XmlHighlighter::XmlHighlighter(QTextEdit *textEdit) : QSyntaxHighlighter(textEdit) { // nothing } // -------------------------------------------------------------------- class LatexHighlighter : public QSyntaxHighlighter { public: LatexHighlighter(QTextEdit *textEdit); protected: void applyFormat(const QString &text, QRegExp &exp, const QTextCharFormat &format); virtual void highlightBlock(const QString &text); }; void LatexHighlighter::applyFormat(const QString &text, QRegExp &exp, const QTextCharFormat &format) { int index = text.indexOf(exp); while (index >= 0) { int length = exp.matchedLength(); setFormat(index, length, format); index = text.indexOf(exp, index + length); } } void LatexHighlighter::highlightBlock(const QString &text) { QTextCharFormat mathFormat, tagFormat; mathFormat.setForeground(Qt::red); tagFormat.setFontWeight(QFont::Bold); tagFormat.setForeground(Qt::blue); QRegExp mathExp( "\\$[^$]+\\$" ); QRegExp tagExp( "\\\\[a-zA-Z]+" ); applyFormat(text, mathExp, mathFormat); applyFormat(text, tagExp, tagFormat); } LatexHighlighter::LatexHighlighter(QTextEdit *textEdit) : QSyntaxHighlighter(textEdit) { // nothing } // -------------------------------------------------------------------- PDialog::PDialog(lua_State *L0, WINID parent, const char *caption) : QDialog(parent), Dialog(L0, parent, caption) { setWindowTitle(caption); QVBoxLayout *vlo = new QVBoxLayout; setLayout(vlo); iGrid = new QGridLayout; vlo->addLayout(iGrid); iButtonArea = new QHBoxLayout; vlo->addLayout(iButtonArea); iButtonArea->addStretch(1); QShortcut *shortcut = new QShortcut(QKeySequence("Ctrl+Return"), this); connect(shortcut, &QShortcut::activated, this, &QDialog::accept); } PDialog::~PDialog() { // } void PDialog::keyPressEvent(QKeyEvent *e) { if (iIgnoreEscape && e->key() == Qt::Key_Escape) return; QDialog::keyPressEvent(e); } static void markupLog(QTextEdit *t, const QString &text) { QTextDocument *doc = new QTextDocument(t); doc->setPlainText(text); QTextCursor cursor(doc); int curPos = 0; int errNo = 0; for (;;) { int nextErr = text.indexOf(QLatin1String("\n!"), curPos); if (nextErr < 0) break; int lines = 0; while (curPos < nextErr + 1) { if (text[curPos++] == QLatin1Char('\n')) ++lines; } cursor.movePosition(QTextCursor::Down, QTextCursor::MoveAnchor, lines); int pos = cursor.position(); cursor.movePosition(QTextCursor::Down); cursor.setPosition(pos, QTextCursor::KeepAnchor); ++errNo; QString s; s.sprintf("err%d", errNo); QTextCharFormat format; format.setBackground(Qt::yellow); format.setAnchorName(s); format.setAnchor(true); cursor.setCharFormat(format); } t->setDocument(doc); t->scrollToAnchor(QLatin1String("err1")); } void PDialog::setMapped(lua_State *L, int idx) { SElement &m = iElements[idx]; QWidget *w = iWidgets[idx]; switch (m.type) { case ELabel: (qobject_cast(w))->setText(QString::fromUtf8(m.text.c_str())); break; case ECheckBox: (qobject_cast(w))->setChecked(m.value); break; case ETextEdit: (qobject_cast(w))->setText(QString::fromUtf8(m.text.c_str())); break; case EInput: (qobject_cast(w))->setText(QString::fromUtf8(m.text.c_str())); break; case EList: { QListWidget *l = qobject_cast(w); if (!lua_isnumber(L, 3)) { l->clear(); for (int k = 0; k < int(m.items.size()); ++k) l->addItem(QString::fromUtf8(m.items[k].c_str())); } l->setCurrentRow(m.value); } break; case ECombo: { QComboBox *b = qobject_cast(w); if (!lua_isnumber(L, 3)) { b->clear(); for (int k = 0; k < int(m.items.size()); ++k) b->addItem(QString::fromUtf8(m.items[k].c_str())); } b->setCurrentIndex(m.value); } break; default: break; // EButton } } bool PDialog::buildAndRun(int w, int h) { for (int i = 0; i < int(iElements.size()); ++i) { SElement &m = iElements[i]; if (m.row < 0) { QPushButton *b = new QPushButton(QString::fromUtf8(m.text.c_str()), this); iWidgets.push_back(b); if (m.flags & EAccept) { b->setDefault(true); connect(b, &QPushButton::clicked, this, &QDialog::accept); } else if (m.flags & EReject) connect(b, &QPushButton::clicked, this, &QDialog::reject); else if (m.lua_method != LUA_NOREF) connect(b, &QPushButton::clicked, [&,method=m.lua_method](){ callLua(method); }); iButtonArea->addWidget(b); } else { QWidget *w = nullptr; switch (m.type) { case ELabel: w = new QLabel(QString::fromUtf8(m.text.c_str()), this); w->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed); break; case EButton: { QPushButton *b = new QPushButton(QString::fromUtf8(m.text.c_str()), this); if (m.flags & EAccept) connect(b, &QPushButton::clicked, this, &QDialog::accept); else if (m.flags & EReject) connect(b, &QPushButton::clicked, this, &QDialog::reject); else if (m.lua_method != LUA_NOREF) connect(b, &QPushButton::clicked, [&,method=m.lua_method](){ callLua(method); }); w = b; } break; case ECheckBox: { QCheckBox *ch = new QCheckBox(QString::fromUtf8(m.text.c_str()), this); ch->setChecked(m.value); if (m.lua_method != LUA_NOREF) connect(ch, &QCheckBox::stateChanged, [&,method=m.lua_method](int){ callLua(method); }); w = ch; } break; case EInput: { QLineEdit *e = new QLineEdit(this); e->setText(QString::fromUtf8(m.text.c_str())); if (m.flags & ESelectAll) e->selectAll(); w = e; } break; case ETextEdit: { QTextEdit *t = new QTextEdit(this); t->setAcceptRichText(false); if (m.flags & EReadOnly) t->setReadOnly(true); if (m.flags & EXml) (void) new XmlHighlighter(t); else if (m.flags & ELatex) (void) new LatexHighlighter(t); QString text = QString::fromUtf8(m.text.c_str()); if (m.flags & ELogFile) { markupLog(t, text); } else t->setPlainText(text); if (m.flags & ESelectAll) t->selectAll(); w = t; } break; case ECombo: { QComboBox *b = new QComboBox(this); for (int k = 0; k < int(m.items.size()); ++k) b->addItem(QString::fromUtf8(m.items[k].c_str())); b->setCurrentIndex(m.value); if (m.lua_method != LUA_NOREF) { connect(b, &QComboBox::activated, [=](int index){ callLua(m.lua_method); }); } w = b; } break; case EList: { QListWidget *l = new QListWidget(this); for (int k = 0; k < int(m.items.size()); ++k) l->addItem(QString::fromUtf8(m.items[k].c_str())); if (m.lua_method != LUA_NOREF) { connect(l, &QListWidget::itemActivated, [=](QListWidgetItem *){ callLua(m.lua_method); }); } w = l; } break; default: break; } iWidgets.push_back(w); gridlayout()->addWidget(w, m.row, m.col, m.rowspan, m.colspan); if (m.flags & EFocused) w->setFocus(Qt::OtherFocusReason); if (m.flags & EDisabled) w->setEnabled(false); } } setMinimumSize(w, h); int result = exec(); retrieveValues(); // for future reference return (result == QDialog::Accepted); } void PDialog::retrieveValues() { for (int i = 0; i < int(iElements.size()); ++i) { SElement &m = iElements[i]; QWidget *w = iWidgets[i]; switch (m.type) { case EInput: m.text = std::string((qobject_cast(w))->text().toUtf8()); break; case ETextEdit: m.text = std::string((qobject_cast(w))-> toPlainText().toUtf8()); break; case EList: { int r = (qobject_cast(w))->currentRow(); m.value = (r >= 0) ? r : 0; } break; case ECombo: m.value = (qobject_cast(w))->currentIndex(); break; case ECheckBox: m.value = qobject_cast(w)->isChecked(); break; default: break; // label and button - nothing to do } } } void PDialog::enableItem(int idx, bool value) { iWidgets[idx]->setEnabled(value); } void PDialog::acceptDialog(lua_State *L) { int accept = lua_toboolean(L, 2); QDialog::done(accept); } // -------------------------------------------------------------------- static int dialog_constructor(lua_State *L) { QWidget *parent = check_winid(L, 1); const char *s = luaL_checkstring(L, 2); Dialog **dlg = (Dialog **) lua_newuserdata(L, sizeof(Dialog *)); *dlg = nullptr; luaL_getmetatable(L, "Ipe.dialog"); lua_setmetatable(L, -2); *dlg = new PDialog(L, parent, s); return 1; } // -------------------------------------------------------------------- MenuAction::MenuAction(const QString &name, int number, const QString &item, const QString &text, QWidget *parent) : QAction(text, parent) { iName = name; iItemName = item; iNumber = number; } // -------------------------------------------------------------------- PMenu::PMenu(WINID parent) { iMenu = new QMenu(); } PMenu::~PMenu() { delete iMenu; } int PMenu::execute(lua_State *L) { int vx = (int)luaL_checknumber(L, 2); int vy = (int)luaL_checknumber(L, 3); QAction *a = iMenu->exec(QPoint(vx, vy)); MenuAction *ma = qobject_cast(a); if (ma) { push_string(L, ma->name()); lua_pushnumber(L, ma->number()); push_string(L, ma->itemName()); return 3; } return 0; } #define SIZE 16 static QIcon colorIcon(double red, double green, double blue) { QPixmap pixmap(SIZE, SIZE); pixmap.fill(QColor(int(red * 255.0 + 0.5), int(green * 255.0 + 0.5), int(blue * 255.0 + 0.5))); return QIcon(pixmap); } int PMenu::add(lua_State *L) { QString name = checkqstring(L, 2); QString title = checkqstring(L, 3); if (lua_gettop(L) == 3) { iMenu->addAction(new MenuAction(name, 0, QString(), title, iMenu)); } else { luaL_argcheck(L, lua_istable(L, 4), 4, "argument is not a table"); bool hasmap = !lua_isnoneornil(L, 5) && lua_isfunction(L, 5); bool hastable = !hasmap && !lua_isnoneornil(L, 5); bool hascolor = !lua_isnoneornil(L, 6) && lua_isfunction(L, 6); bool hascheck = !hascolor && !lua_isnoneornil(L, 6); if (hastable) luaL_argcheck(L, lua_istable(L, 5), 5, "argument is not a function or table"); QString current; if (hascheck) { luaL_argcheck(L, lua_isstring(L, 6), 6, "argument is not a function or string"); current = checkqstring(L, 6); } int no = lua_rawlen(L, 4); QMenu *sm = new QMenu(title, iMenu); for (int i = 1; i <= no; ++i) { lua_rawgeti(L, 4, i); luaL_argcheck(L, lua_isstring(L, -1), 4, "items must be strings"); QString item = toqstring(L, -1); QString text = item; if (hastable) { lua_rawgeti(L, 5, i); luaL_argcheck(L, lua_isstring(L, -1), 5, "labels must be strings"); text = toqstring(L, -1); lua_pop(L, 1); } if (hasmap) { lua_pushvalue(L, 5); // function lua_pushnumber(L, i); // index lua_pushvalue(L, -3); // name lua_call(L, 2, 1); // function returns label luaL_argcheck(L, lua_isstring(L, -1), 5, "function does not return string"); text = toqstring(L, -1); lua_pop(L, 1); // pop result } MenuAction *ma = new MenuAction(name, i, item, text, sm); if (hascolor) { lua_pushvalue(L, 6); // function lua_pushnumber(L, i); // index lua_pushvalue(L, -3); // name lua_call(L, 2, 3); // function returns red, green, blue double red = luaL_checknumber(L, -3); double green = luaL_checknumber(L, -2); double blue = luaL_checknumber(L, -1); lua_pop(L, 3); // pop result QIcon icon = colorIcon(red, green, blue); ma->setIcon(icon); ma->setIconVisibleInMenu(true); } if (hascheck) { ma->setCheckable(true); ma->setChecked(item == current); } lua_pop(L, 1); // item sm->addAction(ma); } iMenu->addMenu(sm); } return 0; } static int menu_constructor(lua_State *L) { QWidget *parent = check_winid(L, 1); Menu **m = (Menu **) lua_newuserdata(L, sizeof(PMenu *)); *m = nullptr; luaL_getmetatable(L, "Ipe.menu"); lua_setmetatable(L, -2); *m = new PMenu(parent); return 1; } // -------------------------------------------------------------------- class EditorThread : public QThread { public: EditorThread(const QString &cmd); protected: virtual void run(); private: QString iCommand; }; EditorThread::EditorThread(const QString &cmd) : QThread() { iCommand = cmd; } void EditorThread::run() { int result = std::system(iCommand.toUtf8()); (void) result; } class EditorDialog : public QDialog { public: EditorDialog(QWidget *parent = nullptr); protected: void closeEvent(QCloseEvent *ev); }; EditorDialog::EditorDialog(QWidget *parent) : QDialog(parent) { QGridLayout *lo = new QGridLayout; setLayout(lo); setWindowTitle("Ipe: waiting"); QLabel *l = new QLabel("Waiting for external editor", this); lo->addWidget(l, 0, 0); } void EditorDialog::closeEvent(QCloseEvent *ev) { ev->ignore(); } static int ipeui_wait(lua_State *L) { QString cmd = checkqstring(L, 2); EditorDialog *dialog = new EditorDialog(); EditorThread *thread = new EditorThread(cmd); dialog->connect(thread, &QThread::finished, dialog, &QDialog::accept); thread->start(); dialog->exec(); delete dialog; delete thread; return 0; } // -------------------------------------------------------------------- PTimer::PTimer(lua_State *L0, int lua_object, const char *method) : Timer(L0, lua_object, method) { iTimer = new QTimer(); connect(iTimer, &QTimer::timeout, [&]() { if (iSingleShot) iTimer->stop(); callLua(); }); } PTimer::~PTimer() { delete iTimer; } int PTimer::setInterval(lua_State *L) { int t = (int)luaL_checkinteger(L, 2); iTimer->setInterval(t); return 0; } int PTimer::active(lua_State *L) { lua_pushboolean(L, iTimer->isActive()); return 1; } int PTimer::start(lua_State *L) { iTimer->start(); return 0; } int PTimer::stop(lua_State *L) { iTimer->stop(); return 0; } // -------------------------------------------------------------------- static int timer_constructor(lua_State *L) { luaL_argcheck(L, lua_istable(L, 1), 1, "argument is not a table"); const char *method = luaL_checkstring(L, 2); Timer **t = (Timer **) lua_newuserdata(L, sizeof(Timer *)); *t = nullptr; luaL_getmetatable(L, "Ipe.timer"); lua_setmetatable(L, -2); // create a table with weak reference to Lua object lua_createtable(L, 1, 1); lua_pushliteral(L, "v"); lua_setfield(L, -2, "__mode"); lua_pushvalue(L, -1); lua_setmetatable(L, -2); lua_pushvalue(L, 1); lua_rawseti(L, -2, 1); int lua_object = luaL_ref(L, LUA_REGISTRYINDEX); *t = new PTimer(L, lua_object, method); return 1; } // -------------------------------------------------------------------- static int ipeui_getColor(lua_State *L) { QWidget *parent = check_winid(L, 1); QString title = checkqstring(L, 2); QColor initial = QColor::fromRgbF(luaL_checknumber(L, 3), luaL_checknumber(L, 4), luaL_checknumber(L, 5)); #if QT_VERSION >= 0x040500 QColor changed = QColorDialog::getColor(initial, parent, title); #else QColor changed = QColorDialog::getColor(initial, parent); #endif if (changed.isValid()) { lua_pushnumber(L, changed.redF()); lua_pushnumber(L, changed.greenF()); lua_pushnumber(L, changed.blueF()); return 3; } else return 0; } // -------------------------------------------------------------------- static int ipeui_fileDialog(lua_State *L) { static const char * const typenames[] = { "open", "save", nullptr }; QWidget *parent = check_winid(L, 1); int type = luaL_checkoption(L, 2, nullptr, typenames); QString caption = checkqstring(L, 3); if (!lua_istable(L, 4)) luaL_argerror(L, 4, "table expected for filters"); QStringList filters; int nFilters = lua_rawlen(L, 4); for (int i = 1; i <= nFilters; i += 2) { // skip Windows versions lua_rawgeti(L, 4, i); luaL_argcheck(L, lua_isstring(L, -1), 4, "filter entry is not a string"); filters += checkqstring(L, -1); lua_pop(L, 1); // element i } QString dir; if (!lua_isnoneornil(L, 5)) dir = checkqstring(L, 5); QString name; if (!lua_isnoneornil(L, 6)) name = checkqstring(L, 6); int selected = 0; if (!lua_isnoneornil(L, 7)) selected = luaL_checkinteger(L, 7); QFileDialog dialog(parent); dialog.setWindowTitle(caption); dialog.setNameFilters(filters); dialog.setConfirmOverwrite(false); if (type == 0) { dialog.setFileMode(QFileDialog::ExistingFile); dialog.setAcceptMode(QFileDialog::AcceptOpen); } else { dialog.setFileMode(QFileDialog::AnyFile); dialog.setAcceptMode(QFileDialog::AcceptSave); } if (selected) dialog.selectNameFilter(filters[selected-1]); if (!dir.isNull()) dialog.setDirectory(dir); if (!name.isNull()) dialog.selectFile(name); if (dialog.exec() == QDialog::Accepted) { QStringList fns = dialog.selectedFiles(); if (!fns.isEmpty()) { push_string(L, fns[0]); QString f = dialog.selectedNameFilter(); int sf = 0; while (sf < filters.size() && filters[sf] != f) ++sf; lua_pushinteger(L, (sf < filters.size()) ? sf + 1 : 0); return 2; } } return 0; } // -------------------------------------------------------------------- static int ipeui_messageBox(lua_State *L) { static const char * const options[] = { "none", "warning", "information", "question", "critical", nullptr }; static const char * const buttontype[] = { "ok", "okcancel", "yesnocancel", "discardcancel", "savediscardcancel", nullptr }; QWidget *parent = check_winid(L, 1); int type = luaL_checkoption(L, 2, "none", options); QString text = checkqstring(L, 3); QString details; if (!lua_isnoneornil(L, 4)) details = checkqstring(L, 4); int buttons = 0; if (lua_isnumber(L, 5)) buttons = luaL_checkinteger(L, 5); else if (!lua_isnoneornil(L, 5)) buttons = luaL_checkoption(L, 5, nullptr, buttontype); QMessageBox msgBox(parent); msgBox.setText(text); msgBox.setInformativeText(details); switch (type) { case 0: default: msgBox.setIcon(QMessageBox::NoIcon); break; case 1: msgBox.setIcon(QMessageBox::Warning); break; case 2: msgBox.setIcon(QMessageBox::Information); break; case 3: msgBox.setIcon(QMessageBox::Question); break; case 4: msgBox.setIcon(QMessageBox::Critical); break; } switch (buttons) { case 0: default: msgBox.setStandardButtons(QMessageBox::Ok); break; case 1: msgBox.setStandardButtons(QMessageBox::Ok|QMessageBox::Cancel); break; case 2: msgBox.setStandardButtons(QMessageBox::Yes|QMessageBox::No| QMessageBox::Cancel); break; case 3: msgBox.setStandardButtons(QMessageBox::Discard|QMessageBox::Cancel); break; case 4: msgBox.setStandardButtons(QMessageBox::Save|QMessageBox::Discard| QMessageBox::Cancel); break; } int ret = msgBox.exec(); switch (ret) { case QMessageBox::Ok: case QMessageBox::Yes: case QMessageBox::Save: lua_pushnumber(L, 1); break; case QMessageBox::No: case QMessageBox::Discard: lua_pushnumber(L, 0); break; case QMessageBox::Cancel: default: lua_pushnumber(L, -1); break; } return 1; } // -------------------------------------------------------------------- static int ipeui_currentDateTime(lua_State *L) { QDateTime dt = QDateTime::currentDateTime(); QString mod; mod.sprintf("%04d%02d%02d%02d%02d%02d", dt.date().year(), dt.date().month(), dt.date().day(), dt.time().hour(), dt.time().minute(), dt.time().second()); push_string(L, mod); return 1; } // -------------------------------------------------------------------- static const struct luaL_Reg ipeui_functions[] = { { "Dialog", dialog_constructor }, { "Menu", menu_constructor }, { "Timer", timer_constructor }, { "getColor", ipeui_getColor }, { "fileDialog", ipeui_fileDialog }, { "messageBox", ipeui_messageBox }, { "waitDialog", ipeui_wait }, { "currentDateTime", ipeui_currentDateTime }, { nullptr, nullptr } }; // -------------------------------------------------------------------- int luaopen_ipeui(lua_State *L) { luaL_newlib(L, ipeui_functions); lua_setglobal(L, "ipeui"); luaopen_ipeui_common(L); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipeui/ipeui_qt.h0000644000175000017500000000624413561570220016134 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // A UI toolkit for Lua, QT version // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEUI_QT_H #define IPEUI_QT_H #include "ipeui_common.h" #include #include #include #include class QTimer; class QTextEdit; // -------------------------------------------------------------------- class MenuAction : public QAction { Q_OBJECT public: MenuAction(const QString &name, int number, const QString &item, const QString &text, QWidget *parent); QString name() const { return iName; } QString itemName() const { return iItemName; } int number() const { return iNumber; } private: QString iName; QString iItemName; int iNumber; }; class PMenu : public Menu { public: PMenu(WINID parent); virtual ~PMenu(); virtual int add(lua_State *L); virtual int execute(lua_State *L); private: QMenu *iMenu; }; // -------------------------------------------------------------------- class PTimer : public QObject, public Timer { Q_OBJECT public: PTimer(lua_State *L0, int lua_object, const char *method); virtual ~PTimer(); virtual int setInterval(lua_State *L); virtual int active(lua_State *L); virtual int start(lua_State *L); virtual int stop(lua_State *L); private: QTimer *iTimer; }; // -------------------------------------------------------------------- class PDialog : public QDialog, public Dialog { Q_OBJECT public: PDialog(lua_State *L0, WINID parent, const char *caption); ~PDialog(); QGridLayout *gridlayout() { return iGrid; } protected: virtual void setMapped(lua_State *L, int idx); virtual bool buildAndRun(int w, int h); virtual void retrieveValues(); virtual void enableItem(int idx, bool value); virtual void acceptDialog(lua_State *L); protected: virtual void keyPressEvent(QKeyEvent *e); private: std::vector iWidgets; QGridLayout *iGrid; QHBoxLayout *iButtonArea; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipeui/ipeui_common.h0000644000175000017500000001342513561570220016777 0ustar otfriedotfried// -------------------------------------------------------------------- // Classes common to several platforms // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEUI_COMMON_H #define IPEUI_COMMON_H extern "C" { #include #include #include } #include #include #include #include #ifdef IPEUI_GTK #include using WINID = GtkWidget *; #endif #ifdef IPEUI_WIN32 #include using WINID = HWND; #endif #ifdef IPEUI_QT #include using WINID = QWidget *; #endif #ifdef IPEUI_COCOA #include using WINID = NSWindow * __unsafe_unretained; #endif using ushort = unsigned short; using uchar = unsigned char; // -------------------------------------------------------------------- extern WINID check_winid(lua_State *L, int i); extern void push_winid(lua_State *L, WINID win); // -------------------------------------------------------------------- inline std::string checkstring(lua_State *L, int i) { return std::string(luaL_checklstring(L, i, nullptr)); } inline std::string tostring(lua_State *L, int i) { return std::string(lua_tolstring(L, i, nullptr)); } inline void luacall(lua_State *L, int nargs, int nresults) { lua_callk(L, nargs, nresults, 0, nullptr); } // -------------------------------------------------------------------- class Dialog { public: Dialog(lua_State *L0, WINID parent, const char *caption); virtual ~Dialog(); // Lua methods int add(lua_State *L); int addButton(lua_State *L); int set(lua_State *L); int get(lua_State *L); int setEnabled(lua_State *L); int setStretch(lua_State *L); bool execute(lua_State *L, int w, int h); virtual void acceptDialog(lua_State *L) = 0; WINID winId() const { return hDialog; } protected: enum TFlags { ELogFile = 0x001, EXml = 0x002, ELatex = 0x040, EAccept = 0x004, EReject = 0x008, EReadOnly = 0x010, EDisabled = 0x020, ESelectAll = 0x080, EFocused = 0x100, ESpellCheck = 0x200, }; enum TType { EButton = 0, ETextEdit, EList, ELabel, ECombo, ECheckBox, EInput }; struct SElement { std::string name; TType type; int row, col, rowspan, colspan; int minWidth, minHeight; // only used on Windows int lua_method; int flags; std::vector items; std::string text; int value; }; void callLua(int luaMethod); int findElement(lua_State *L, int index); void setUnmapped(lua_State *L, int idx); virtual void setMapped(lua_State *L, int idx) = 0; virtual bool buildAndRun(int w, int h) = 0; virtual void retrieveValues() = 0; virtual void enableItem(int idx, bool value) = 0; void addButtonItem(lua_State *L, SElement &m); void addTextEdit(lua_State *L, SElement &m); void addList(lua_State *L, SElement &m); void addLabel(lua_State *L, SElement &m); void addCombo(lua_State *L, SElement &m); void addCheckbox(lua_State *L, SElement &m); void addInput(lua_State *L, SElement &m); void setListItems(lua_State *L, int index, SElement &m); protected: lua_State *L; WINID iParent; WINID hDialog; std::string iCaption; std::vector iElements; int iLuaDialog; bool iIgnoreEscape; int iBaseX, iBaseY; int iNoRows, iNoCols; std::vector iRowStretch; std::vector iColStretch; }; // -------------------------------------------------------------------- inline Dialog **check_dialog(lua_State *L, int i) { return (Dialog **) luaL_checkudata(L, i, "Ipe.dialog"); } // -------------------------------------------------------------------- class Menu { public: virtual ~Menu(); virtual int add(lua_State *L) = 0; virtual int execute(lua_State *L) = 0; }; // -------------------------------------------------------------------- inline Menu **check_menu(lua_State *L, int i) { return (Menu **) luaL_checkudata(L, i, "Ipe.menu"); } // -------------------------------------------------------------------- class Timer { public: Timer(lua_State *L0, int lua_object, const char *method); virtual ~Timer(); int setSingleShot(lua_State *L); virtual int setInterval(lua_State *L) = 0; virtual int active(lua_State *L) = 0; virtual int start(lua_State *L) = 0; virtual int stop(lua_State *L) = 0; protected: void callLua(); protected: lua_State *L; int iLuaObject; std::string iMethod; bool iSingleShot; }; // -------------------------------------------------------------------- inline Timer **check_timer(lua_State *L, int i) { return (Timer **) luaL_checkudata(L, i, "Ipe.timer"); } // -------------------------------------------------------------------- extern int luaopen_ipeui_common(lua_State *L); // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipeui/Makefile0000644000175000017500000000225013561570220015575 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for ipeui # -------------------------------------------------------------------- OBJDIR = $(BUILDDIR)/obj/ipeui include ../common.mak TARGET = $(call dll_target,ipeui) MAKE_SYMLINKS = $(call dll_symlinks,ipeui) SONAME = $(call soname,ipeui) INSTALL_SYMLINKS = $(call install_symlinks,ipeui) CPPFLAGS += $(UI_CFLAGS) $(LUA_CFLAGS) LIBS += $(UI_LIBS) $(LUA_LIBS) CXXFLAGS += $(DLL_CFLAGS) all: $(TARGET) sources = ipeui_common.cpp cocoa_sources = ipeui_cocoa.cpp qt_sources = ipeui_qt.cpp moc_headers = ipeui_qt.h win_sources = ipeui_win.cpp gtk_sources = ipeui_gtk.cpp ifdef IPEUI_COCOA CXXFLAGS += $(IPEOBJCPP) endif $(TARGET): $(objects) $(MAKE_LIBDIR) $(CXX) $(LDFLAGS) $(DLL_LDFLAGS) $(SONAME) -o $@ $^ $(LIBS) $(MAKE_SYMLINKS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_SYMLINKS) # -------------------------------------------------------------------- ipe-7.2.13/src/ipeui/ipeui_common.cpp0000644000175000017500000004427613561570220017342 0ustar otfriedotfried// -------------------------------------------------------------------- // Lua bindings for UI, platform-neutral common part // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeui_common.h" #include // -------------------------------------------------------------------- WINID check_winid(lua_State *L, int i) { if (lua_isnil(L, i)) return nullptr; WINID *w = (WINID *) luaL_checkudata(L, i, "Ipe.winid"); return *w; } void push_winid(lua_State *L, WINID win) { WINID *w = (WINID *) lua_newuserdata(L, sizeof(WINID)); *w = win; luaL_getmetatable(L, "Ipe.winid"); lua_setmetatable(L, -2); } static int winid_tostring(lua_State *L) { check_winid(L, 1); lua_pushfstring(L, "GtkWidget@%p", lua_topointer(L, 1)); return 1; } static const struct luaL_Reg winid_methods[] = { { "__tostring", winid_tostring }, { nullptr, nullptr } }; // -------------------------------------------------------------------- Dialog::Dialog(lua_State *L0, WINID parent, const char *caption) : iCaption(caption) { L = L0; iParent = parent; iLuaDialog = LUA_NOREF; hDialog = nullptr; iIgnoreEscape = false; iNoRows = 1; iNoCols = 1; } // Careful: On Qt, the dialog is owned by the parent window. // It's important that Lua deletes the dialog before Qt tries to, otherwise // we have a double deletion. // Make sure not to create a cyclic reference to the dialog by capturing it inside // the Lua method for an action, as this would stop it from being garbage collected. Dialog::~Dialog() { // dereference lua methods for (int i = 0; i < int(iElements.size()); ++i) luaL_unref(L, LUA_REGISTRYINDEX, iElements[i].lua_method); luaL_unref(L, LUA_REGISTRYINDEX, iLuaDialog); } void Dialog::callLua(int luaMethod) { // only call back to Lua during execute() if (iLuaDialog == LUA_NOREF) return; lua_rawgeti(L, LUA_REGISTRYINDEX, luaMethod); lua_rawgeti(L, LUA_REGISTRYINDEX, iLuaDialog); luacall(L, 1, 0); } // name, label, action int Dialog::addButton(lua_State *L) { SElement m; m.name = std::string(luaL_checklstring(L, 2, nullptr)); m.type = EButton; m.lua_method = LUA_NOREF; m.flags = 0; m.row = -1; m.col = -1; m.rowspan = 1; m.colspan = 1; m.text = std::string(luaL_checklstring(L, 3, nullptr)); if (lua_isstring(L, 4)) { const char *s = lua_tolstring(L, 4, nullptr); if (!strcmp(s, "accept")) m.flags |= EAccept; else if (!strcmp(s, "reject")) m.flags |= EReject; else luaL_argerror(L, 4, "unknown action"); } else { luaL_argcheck(L, lua_isfunction(L, 4), 4, "unknown action"); lua_pushvalue(L, 4); m.lua_method = luaL_ref(L, LUA_REGISTRYINDEX); } m.minHeight = 16; m.minWidth = 4 * m.text.length() + 8; if (m.minWidth < 64) m.minWidth = 64; iElements.push_back(m); return 0; } int Dialog::add(lua_State *L) { static const char * const typenames[] = { "button", "text", "list", "label", "combo", "checkbox", "input", nullptr }; SElement m; m.name = checkstring(L, 2); m.type = TType(luaL_checkoption(L, 3, nullptr, typenames)); luaL_checktype(L, 4, LUA_TTABLE); m.lua_method = LUA_NOREF; m.flags = 0; m.row = luaL_checkinteger(L, 5) - 1; if (m.row < 0) m.row = iNoRows + 1 + m.row; m.col = luaL_checkinteger(L, 6) - 1; m.rowspan = 1; m.colspan = 1; if (!lua_isnoneornil(L, 7)) m.rowspan = luaL_checkinteger(L, 7); if (!lua_isnoneornil(L, 8)) m.colspan = luaL_checkinteger(L, 8); if (m.row + m.rowspan > iNoRows) iNoRows = m.row + m.rowspan; if (m.col + m.colspan > iNoCols) iNoCols = m.col + m.colspan; switch (m.type) { case EButton: addButtonItem(L, m); break; case ETextEdit: addTextEdit(L, m); break; case EList: addList(L, m); break; case ELabel: addLabel(L, m); break; case ECombo: addCombo(L, m); break; case ECheckBox: addCheckbox(L, m); break; case EInput: addInput(L, m); break; default: break; } iElements.push_back(m); return 0; } void Dialog::addLabel(lua_State *L, SElement &m) { lua_getfield(L, 4, "label"); luaL_argcheck(L, lua_isstring(L, -1), 4, "no label"); m.text = std::string(lua_tolstring(L, -1, nullptr)); lua_pop(L, 1); // label m.minHeight = 16; const char *p = m.text.c_str(); int maxlen = 0; int curlen = 0; while (*p) { if (*p++ == '\n') { m.minHeight += 8; if (curlen > maxlen) maxlen = curlen; curlen = 0; } ++curlen; } if (curlen > maxlen) maxlen = curlen; m.minWidth = 4 * maxlen; } void Dialog::addButtonItem(lua_State *L, SElement &m) { lua_getfield(L, 4, "label"); luaL_argcheck(L, lua_isstring(L, -1), 4, "no button label"); m.text = tostring(L, -1); lua_getfield(L, 4, "action"); if (lua_isstring(L, -1)) { auto s = tostring(L, -1); if (s == "accept") m.flags |= EAccept; else if (s == "reject") m.flags |= EReject; else luaL_argerror(L, 4, "unknown action"); } else if (lua_isfunction(L, -1)) { lua_pushvalue(L, -1); m.lua_method = luaL_ref(L, LUA_REGISTRYINDEX); } else if (!lua_isnil(L, -1)) luaL_argerror(L, 4, "unknown action type"); lua_pop(L, 2); // action, label m.minHeight = 16; m.minWidth = 4 * m.text.length() + 8; if (m.minWidth < 64) m.minWidth = 64; } void Dialog::addCheckbox(lua_State *L, SElement &m) { lua_getfield(L, 4, "label"); luaL_argcheck(L, lua_isstring(L, -1), 4, "no label"); m.text = tostring(L, -1); lua_getfield(L, 4, "action"); if (!lua_isnil(L, -1)) { luaL_argcheck(L, lua_isfunction(L, -1), 4, "unknown action type"); lua_pushvalue(L, -1); m.lua_method = luaL_ref(L, LUA_REGISTRYINDEX); } lua_pop(L, 2); // action, label m.value = 0; m.minHeight = 16; m.minWidth = 4 * m.text.length() + 32; } void Dialog::addInput(lua_State *L, SElement &m) { m.minHeight = 12; m.minWidth = 100; lua_getfield(L, 4, "select_all"); if (lua_toboolean(L, -1)) m.flags |= ESelectAll; lua_getfield(L, 4, "focus"); if (lua_toboolean(L, -1)) m.flags |= EFocused; lua_pop(L, 2); } void Dialog::addTextEdit(lua_State *L, SElement &m) { lua_getfield(L, 4, "read_only"); if (lua_toboolean(L, -1)) m.flags |= EReadOnly; lua_getfield(L, 4, "select_all"); if (lua_toboolean(L, -1)) m.flags |= ESelectAll; lua_getfield(L, 4, "focus"); if (lua_toboolean(L, -1)) m.flags |= EFocused; lua_getfield(L, 4, "syntax"); if (!lua_isnil(L, -1)) { auto s = tostring(L, -1); if (s == "logfile") { m.flags |= ELogFile; } else if (s == "xml") { m.flags |= EXml; } else if (s == "latex") { m.flags |= ELatex; } else luaL_argerror(L, 4, "unknown syntax"); } lua_getfield(L, 4, "spell_check"); if (lua_toboolean(L, -1)) m.flags |= ESpellCheck; lua_pop(L, 5); // spell_check, syntax, focus, select_all, read_only m.minHeight = 48; m.minWidth = 100; } void Dialog::setListItems(lua_State *L, int index, SElement &m) { int no = lua_rawlen(L, index); m.minWidth = 48; for (int i = 1; i <= no; ++i) { lua_rawgeti(L, index, i); luaL_argcheck(L, lua_isstring(L, -1), index, "items must be strings"); auto item = tostring(L, -1); int w = 4 * item.size() + 16; if (w > m.minWidth) m.minWidth = w; m.items.emplace_back(item); lua_pop(L, 1); // item } lua_getfield(L, index, "action"); if (!lua_isnil(L, -1)) { luaL_argcheck(L, lua_isfunction(L, -1), index, "unknown action type"); lua_pushvalue(L, -1); m.lua_method = luaL_ref(L, LUA_REGISTRYINDEX); } lua_pop(L, 1); // action } void Dialog::addList(lua_State *L, SElement &m) { setListItems(L, 4, m); m.value = 0; m.minHeight = 48; } void Dialog::addCombo(lua_State *L, SElement &m) { setListItems(L, 4, m); m.value = 0; m.minHeight = 16; } int Dialog::findElement(lua_State *L, int index) { auto name = checkstring(L, index); for (int i = 0; i < int(iElements.size()); ++i) { if (name == iElements[i].name) return i; } return luaL_argerror(L, index, "no such element in dialog"); } int Dialog::set(lua_State *L) { auto s = checkstring(L, 2); if (s == "ignore-escape") { iIgnoreEscape = lua_toboolean(L, 3); return 0; } int idx = findElement(L, 2); // set internal representation setUnmapped(L, idx); // if dialog is on screen, also set there if (iLuaDialog != LUA_NOREF) setMapped(L, idx); return 0; } void Dialog::setUnmapped(lua_State *L, int idx) { SElement &m = iElements[idx]; switch (m.type) { case ELabel: case ETextEdit: case EInput: m.text = checkstring(L, 3); break; case EList: case ECombo: if (lua_isnumber(L, 3)) { int n = luaL_checkinteger(L, 3); luaL_argcheck(L, 1 <= n && n <= int(m.items.size()), 3, "list index out of bounds"); m.value = n - 1; } else if (lua_isstring(L, 3)) { auto s = tostring(L, 3); auto it = std::find_if(m.items.cbegin(), m.items.cend(), [&s](const std::string &el) { return s == el; }); luaL_argcheck(L, it != m.items.end(), 3, "item not in list"); m.value = (it - m.items.begin()); } else { luaL_checktype(L, 3, LUA_TTABLE); m.items.clear(); setListItems(L, 3, m); m.value = 0; } break; case ECheckBox: m.value = lua_toboolean(L, 3); break; default: luaL_argerror(L, 2, "no suitable element"); } } int Dialog::get(lua_State *L) { if (iLuaDialog != LUA_NOREF) retrieveValues(); int idx = findElement(L, 2); SElement &m = iElements[idx]; switch (m.type) { case ETextEdit: case EInput: lua_pushstring(L, m.text.c_str()); return 1; case EList: case ECombo: lua_pushinteger(L, m.value + 1); return 1; case ECheckBox: lua_pushboolean(L, m.value); return 1; default: return luaL_argerror(L, 2, "no suitable element"); } } bool Dialog::execute(lua_State *L, int w, int h) { // remember Lua object for dialog for callbacks lua_pushvalue(L, 1); iLuaDialog = luaL_ref(L, LUA_REGISTRYINDEX); bool result = buildAndRun(w, h); // execute dialog // discard reference to dialog object // (otherwise the circular reference will stop Lua gc) luaL_unref(L, LUA_REGISTRYINDEX, iLuaDialog); iLuaDialog = LUA_NOREF; return result; } int Dialog::setEnabled(lua_State *L) { int idx = findElement(L, 2); bool value = lua_toboolean(L, 3); if (iLuaDialog != LUA_NOREF) // mapped enableItem(idx, value); else if (value) iElements[idx].flags &= ~EDisabled; else iElements[idx].flags |= EDisabled; return 0; } int Dialog::setStretch(lua_State *L) { static const char * const typenames[] = { "row", "column", nullptr }; while (int(iColStretch.size()) < iNoCols) iColStretch.push_back(0); while (int(iRowStretch.size()) < iNoRows) iRowStretch.push_back(0); int type = luaL_checkoption(L, 2, nullptr, typenames); int rowcol = (int)luaL_checkinteger(L, 3) - 1; int stretch = (int)luaL_checkinteger(L, 4); if (type == 0) { luaL_argcheck(L, 0 <= rowcol && rowcol < iNoRows, 3, "Row index out of range"); iRowStretch[rowcol] = stretch; } else { luaL_argcheck(L, 0 <= rowcol && rowcol < iNoCols, 3, "Column index out of range"); iColStretch[rowcol] = stretch; } return 0; } // -------------------------------------------------------------------- static int dialog_tostring(lua_State *L) { check_dialog(L, 1); lua_pushfstring(L, "Dialog@%p", lua_topointer(L, 1)); return 1; } static int dialog_destructor(lua_State *L) { //fprintf(stderr, "Dialog::~Dialog()\n"); Dialog **dlg = check_dialog(L, 1); // on Qt, hope we destruct before the parent window does delete (*dlg); *dlg = nullptr; return 0; } static int dialog_execute(lua_State *L) { Dialog **dlg = check_dialog(L, 1); int w = 0; int h = 0; if (!lua_isnoneornil(L, 2)) { luaL_argcheck(L, lua_istable(L, 2), 2, "argument is not a table"); lua_rawgeti(L, 2, 1); luaL_argcheck(L, lua_isnumber(L, -1), 2, "width is not a number"); lua_rawgeti(L, 2, 2); luaL_argcheck(L, lua_isnumber(L, -1), 2, "height is not a number"); w = lua_tointegerx(L, -2, nullptr); h = lua_tointegerx(L, -1, nullptr); lua_pop(L, 2); // w & h } lua_pushboolean(L, (*dlg)->execute(L, w, h)); return 1; } static int dialog_setStretch(lua_State *L) { Dialog **dlg = check_dialog(L, 1); return (*dlg)->setStretch(L); } static int dialog_add(lua_State *L) { Dialog **dlg = check_dialog(L, 1); return (*dlg)->add(L); } static int dialog_addButton(lua_State *L) { Dialog **dlg = check_dialog(L, 1); return (*dlg)->addButton(L); } static int dialog_set(lua_State *L) { Dialog **dlg = check_dialog(L, 1); return (*dlg)->set(L); } static int dialog_get(lua_State *L) { Dialog **dlg = check_dialog(L, 1); return (*dlg)->get(L); } static int dialog_setEnabled(lua_State *L) { Dialog **dlg = check_dialog(L, 1); return (*dlg)->setEnabled(L); } static int dialog_accept(lua_State *L) { Dialog **dlg = check_dialog(L, 1); (*dlg)->acceptDialog(L); return 0; } // -------------------------------------------------------------------- static const struct luaL_Reg dialog_methods[] = { { "__tostring", dialog_tostring }, { "__gc", dialog_destructor }, { "execute", dialog_execute }, { "setStretch", dialog_setStretch }, { "add", dialog_add }, { "addButton", dialog_addButton }, { "set", dialog_set }, { "get", dialog_get }, { "setEnabled", dialog_setEnabled }, { "accept", dialog_accept }, { nullptr, nullptr } }; // -------------------------------------------------------------------- Menu::~Menu() { // empty } // -------------------------------------------------------------------- static int menu_tostring(lua_State *L) { check_menu(L, 1); lua_pushfstring(L, "Menu@%p", lua_topointer(L, 1)); return 1; } static int menu_destructor(lua_State *L) { //fprintf(stderr, "Menu::~Menu()\n"); Menu **m = check_menu(L, 1); delete *m; *m = nullptr; return 0; } static int menu_execute(lua_State *L) { Menu **m = check_menu(L, 1); return (*m)->execute(L); } static int menu_add(lua_State *L) { Menu **m = check_menu(L, 1); return (*m)->add(L); } // -------------------------------------------------------------------- static const struct luaL_Reg menu_methods[] = { { "__tostring", menu_tostring }, { "__gc", menu_destructor }, { "execute", menu_execute }, { "add", menu_add }, { nullptr, nullptr } }; // -------------------------------------------------------------------- Timer::Timer(lua_State *L0, int lua_object, const char *method) : iMethod(method) { L = L0; iLuaObject = lua_object; iSingleShot = false; } Timer::~Timer() { luaL_unref(L, LUA_REGISTRYINDEX, iLuaObject); } void Timer::callLua() { lua_rawgeti(L, LUA_REGISTRYINDEX, iLuaObject); lua_rawgeti(L, -1, 1); // get Lua object if (lua_isnil(L, -1)) { lua_pop(L, 2); // pop weak table, nil return; } lua_getfield(L, -1, iMethod.c_str()); if (lua_isnil(L, -1)) { lua_pop(L, 3); // pop weak table, table, nil return; } lua_remove(L, -3); // remove weak table lua_insert(L, -2); // stack is now: method, table luacall(L, 1, 0); // call method } int Timer::setSingleShot(lua_State *L) { iSingleShot = lua_toboolean(L, 2); return 0; } // -------------------------------------------------------------------- static int timer_tostring(lua_State *L) { check_timer(L, 1); lua_pushfstring(L, "Timer@%p", lua_topointer(L, 1)); return 1; } static int timer_destructor(lua_State *L) { Timer **t = check_timer(L, 1); //fprintf(stderr, "Timer::~Timer()\n"); delete *t; *t = nullptr; return 0; } // -------------------------------------------------------------------- static int timer_start(lua_State *L) { Timer **t = check_timer(L, 1); return (*t)->start(L); } static int timer_stop(lua_State *L) { Timer **t = check_timer(L, 1); return (*t)->stop(L); } static int timer_active(lua_State *L) { Timer **t = check_timer(L, 1); return (*t)->active(L); } static int timer_setinterval(lua_State *L) { Timer **t = check_timer(L, 1); return (*t)->setInterval(L); } static int timer_setsingleshot(lua_State *L) { Timer **t = check_timer(L, 1); return (*t)->setSingleShot(L); } // -------------------------------------------------------------------- static const struct luaL_Reg timer_methods[] = { { "__tostring", timer_tostring }, { "__gc", timer_destructor }, { "start", timer_start }, { "stop", timer_stop }, { "active", timer_active }, { "setInterval", timer_setinterval }, { "setSingleShot", timer_setsingleshot }, { nullptr, nullptr } }; // -------------------------------------------------------------------- static void make_metatable(lua_State *L, const char *name, const struct luaL_Reg *methods) { luaL_newmetatable(L, name); lua_pushstring(L, "__index"); lua_pushvalue(L, -2); /* pushes the metatable */ lua_settable(L, -3); /* metatable.__index = metatable */ luaL_setfuncs(L, methods, 0); lua_pop(L, 1); } int luaopen_ipeui_common(lua_State *L) { make_metatable(L, "Ipe.winid", winid_methods); make_metatable(L, "Ipe.dialog", dialog_methods); make_metatable(L, "Ipe.menu", menu_methods); make_metatable(L, "Ipe.timer", timer_methods); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipeui/ipeui_win.cpp0000644000175000017500000007777713561570220016663 0ustar otfriedotfried// -------------------------------------------------------------------- // Lua bindings for Win32 dialogs // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeui_common.h" #include "ipeui_wstring.h" #include // -------------------------------------------------------------------- #define IDBASE 9000 #define PAD 3 #define BORDER 6 #define BUTTONHEIGHT 14 // -------------------------------------------------------------------- void WString::init(const char *s, int len) { int rw = MultiByteToWideChar(CP_UTF8, 0, s, len, nullptr, 0); resize(rw + 1, wchar_t(0)); MultiByteToWideChar(CP_UTF8, 0, s, len, data(), rw); } BOOL setWindowText(HWND h, const char *s) { WString ws(s); wchar_t *p = ws.data(); std::vector w; w.reserve(ws.size()); while (*p) { wchar_t ch = *p++; if (ch != '\r') { if (ch == '\n') w.push_back('\r'); w.push_back(ch); } } w.push_back(0); return SetWindowTextW(h, &w[0]); } void sendMessage(HWND h, UINT code, const char *t, WPARAM wParam) { WString w(t); SendMessageW(h, code, wParam, (LPARAM) w.data()); } static std::string wideToUtf8(const wchar_t *wbuf) { int rm = WideCharToMultiByte(CP_UTF8, 0, wbuf, -1, nullptr, 0, nullptr, nullptr); std::vector multi(rm); WideCharToMultiByte(CP_UTF8, 0, wbuf, -1, &multi[0], rm, nullptr, nullptr); return std::string(&multi[0]); } static void buildFlags(std::vector &t, DWORD flags) { union { DWORD dw; short s[2]; } a; a.dw = flags; t.push_back(a.s[0]); t.push_back(a.s[1]); t.push_back(0); t.push_back(0); } static void buildString(std::vector &t, const char *s) { WString w(s); const wchar_t *p = w.data(); while (*p) t.push_back(*p++); t.push_back(0); } static void buildControl(std::vector &t, short what, const char *s = nullptr) { t.push_back(0xffff); t.push_back(what); if (s) buildString(t, s); else t.push_back(0); // text t.push_back(0); // creation data } // -------------------------------------------------------------------- class PDialog : public Dialog { public: PDialog(lua_State *L0, WINID parent, const char *caption); virtual ~PDialog(); protected: virtual void setMapped(lua_State *L, int idx); virtual bool buildAndRun(int w, int h); void buildElements(std::vector &t); virtual void retrieveValues(); virtual void enableItem(int idx, bool value); void computeDimensions(int &w, int &h); void buildDimensions(std::vector &t, SElement &m, int id); virtual void acceptDialog(lua_State *L); BOOL initDialog(); BOOL dlgCommand(WPARAM wParam, LPARAM lParam); static BOOL CALLBACK dialogProc(HWND hwndDlg, UINT message, WPARAM wParam, LPARAM lParam); private: int iBaseX, iBaseY; int iButtonX; std::vector iRowHeight; std::vector iColWidth; }; PDialog::PDialog(lua_State *L0, WINID parent, const char *caption) : Dialog(L0, parent, caption) { LONG base = GetDialogBaseUnits(); iBaseX = LOWORD(base); iBaseY = HIWORD(base); } PDialog::~PDialog() { // nothing yet } void PDialog::setMapped(lua_State *L, int idx) { SElement &m = iElements[idx]; HWND h = GetDlgItem(hDialog, idx+IDBASE); switch (m.type) { case ETextEdit: case EInput: case ELabel: setWindowText(h, m.text.c_str()); break; case EList: if (!lua_isnumber(L, 3)) { ListBox_ResetContent(h); for (int j = 0; j < int(m.items.size()); ++j) sendMessage(h, LB_ADDSTRING, m.items[j].c_str()); } ListBox_SetCurSel(h, m.value); break; case ECombo: if (!lua_isnumber(L, 3)) { ComboBox_ResetContent(h); for (int j = 0; j < int(m.items.size()); ++j) sendMessage(h, CB_ADDSTRING, m.items[j].c_str()); } ComboBox_SetCurSel(h, m.value); break; case ECheckBox: CheckDlgButton(hDialog, idx+IDBASE, (m.value ? BST_CHECKED : BST_UNCHECKED)); break; default: break; // already handled in setUnmapped } } static void markupLog(HWND h, const std::string &text) { const char *p = text.c_str(); if (*p) ++p; int pos = 1; while (*p) { if (p[-1] == '\n' && p[0] == '!') { // found it const char *b = p; while (*p && *p != '\n') ++p; SendMessage(h, EM_SETSEL, (WPARAM) pos, (LPARAM) pos + (p - b)); int line = SendMessage(h, EM_LINEFROMCHAR, (WPARAM) pos, 0); SendMessage(h, EM_LINESCROLL, 0, (LPARAM) line - 1); return; } // take into account conversion done by setText if (*p == '\n') pos += 2; else if (*p != '\r') ++pos; ++p; } // not found, nothing to be done } BOOL PDialog::initDialog() { BOOL result = TRUE; for (int i = 0; i < int(iElements.size()); ++i) { SElement &m = iElements[i]; HWND h = GetDlgItem(hDialog, i+IDBASE); if (m.flags & EDisabled) EnableWindow(h, FALSE); switch (m.type) { case EInput: case ETextEdit: setWindowText(h, m.text.c_str()); if (m.flags & EFocused) { SetFocus(h); result = FALSE; // we set the focus ourselves } if (m.flags & ELogFile) markupLog(h, m.text); break; case EList: for (int j = 0; j < int(m.items.size()); ++j) sendMessage(h, LB_ADDSTRING, m.items[j].c_str()); ListBox_SetCurSel(h, m.value); break; case ECombo: for (int j = 0; j < int(m.items.size()); ++j) sendMessage(h, CB_ADDSTRING, m.items[j].c_str()); ComboBox_SetCurSel(h, m.value); break; case ECheckBox: CheckDlgButton(hDialog, i+IDBASE, (m.value ? BST_CHECKED : BST_UNCHECKED)); break; default: break; } } return result; } static std::string getEditText(HWND h) { int n = GetWindowTextLengthW(h); if (n == 0) return std::string(""); WCHAR wbuf[n+1]; GetWindowTextW(h, wbuf, n+1); std::vector w; wchar_t *p = wbuf; while (*p) { wchar_t ch = *p++; if (ch != '\r') w.push_back(ch); } w.push_back(0); return wideToUtf8(&w[0]); } void PDialog::retrieveValues() { for (int i = 0; i < int(iElements.size()); ++i) { SElement &m = iElements[i]; HWND h = GetDlgItem(hDialog, i+IDBASE); switch (m.type) { case ETextEdit: case EInput: m.text = getEditText(h); break; case EList: m.value = ListBox_GetCurSel(h); if (m.value == LB_ERR) m.value = 0; break; case ECombo: m.value = ComboBox_GetCurSel(h); if (m.value == CB_ERR) m.value = 0; break; case ECheckBox: m.value = (IsDlgButtonChecked(hDialog, i+IDBASE) == BST_CHECKED); break; case ELabel: default: break; // nothing to do } } } void PDialog::buildDimensions(std::vector &t, SElement &m, int id) { int x = BORDER; int y = BORDER; int w = 0; int h = 0; if (m.row < 0) { y = BORDER; for (int i = 0; i < iNoRows; ++i) y += iRowHeight[i] + PAD; w = m.minWidth; h = BUTTONHEIGHT; x = iButtonX; iButtonX += w + PAD; } else { for (int i = 0; i < m.col; ++i) x += iColWidth[i] + PAD; for (int i = 0; i < m.row; ++i) y += iRowHeight[i] + PAD; w = iColWidth[m.col]; for (int i = m.col + 1; i < m.col + m.colspan; ++i) w += iColWidth[i] + PAD; h = iRowHeight[m.row]; for (int i = m.row + 1; i < m.row + m.rowspan; ++i) h += iRowHeight[i] + PAD; } t.push_back(x); t.push_back(y); t.push_back(w); t.push_back(h); t.push_back(id); // control id } BOOL PDialog::dlgCommand(WPARAM wParam, LPARAM lParam) { int id = LOWORD(wParam); if (id == IDOK) { retrieveValues(); EndDialog(hDialog, TRUE); return TRUE; } if (id == IDCANCEL && !iIgnoreEscape) { retrieveValues(); EndDialog(hDialog, FALSE); return TRUE; } if (id < IDBASE || id >= IDBASE + int(iElements.size())) return FALSE; SElement &m = iElements[id - IDBASE]; if (m.flags & EAccept) { retrieveValues(); EndDialog(hDialog, TRUE); return TRUE; } else if (m.flags & EReject) { retrieveValues(); EndDialog(hDialog, FALSE); return TRUE; } else if (m.lua_method != LUA_NOREF) callLua(m.lua_method); return FALSE; } void PDialog::acceptDialog(lua_State *L) { int accept = lua_toboolean(L, 2); retrieveValues(); EndDialog(hDialog, accept); } static WNDPROC wpOrigProc; static LRESULT subclassProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { if (message == WM_KEYDOWN) { if (wParam == VK_RETURN && (GetKeyState(VK_CONTROL) & 0x8000)) { SendMessage(GetParent(hwnd), WM_COMMAND, IDOK, 0); return 0; } } return CallWindowProc(wpOrigProc, hwnd, message, wParam, lParam); } BOOL CALLBACK PDialog::dialogProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { PDialog *d = (PDialog *) GetWindowLongPtr(hwnd, GWLP_USERDATA); switch (message) { case WM_INITDIALOG: d = (PDialog *) lParam; SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR) d); d->hDialog = hwnd; // subclass all Edit controls // TODO: Use modern SetSubclass method for (int i = 0; i < int(d->iElements.size()); ++i) { if (d->iElements[i].type == ETextEdit) wpOrigProc = (WNDPROC) SetWindowLongPtr(GetDlgItem(hwnd, i + IDBASE), GWLP_WNDPROC, (LONG_PTR) &subclassProc); } return d->initDialog(); case WM_COMMAND: if (d) return d->dlgCommand(wParam, lParam); else return FALSE; case WM_DESTROY: // Remove the subclasses from text edits for (int i = 0; i < int(d->iElements.size()); ++i) { if (d->iElements[i].type == ETextEdit) SetWindowLongPtr(GetDlgItem(hwnd, i + IDBASE), GWLP_WNDPROC, (LONG_PTR) wpOrigProc); } return FALSE; default: return FALSE; } } void PDialog::buildElements(std::vector &t) { for (int i = 0; i < int(iElements.size()); ++i) { if (t.size() % 2 != 0) t.push_back(0); SElement &m = iElements[i]; int id = i + IDBASE; DWORD flags = WS_CHILD|WS_VISIBLE; switch (m.type) { case EButton: flags |= BS_TEXT|WS_TABSTOP|BS_FLAT; if (m.flags & EAccept) flags |= BS_DEFPUSHBUTTON; else flags |= BS_PUSHBUTTON; buildFlags(t, flags); buildDimensions(t, m, id); buildControl(t, 0x0080, m.text.c_str()); // button break; case ECheckBox: buildFlags(t, flags|BS_AUTOCHECKBOX|BS_TEXT|WS_TABSTOP); buildDimensions(t, m, id); buildControl(t, 0x0080, m.text.c_str()); // button break; case ELabel: buildFlags(t, flags|SS_LEFT); buildDimensions(t, m, id); buildControl(t, 0x0082, m.text.c_str()); // static text break; case EInput: buildFlags(t, flags|ES_LEFT|WS_TABSTOP|WS_BORDER|ES_AUTOHSCROLL); buildDimensions(t, m, id); buildControl(t, 0x0081); // edit break; case ETextEdit: flags |= ES_LEFT|WS_TABSTOP|WS_BORDER; flags |= ES_MULTILINE|ES_WANTRETURN|WS_VSCROLL; if (m.flags & EReadOnly) flags |= ES_READONLY; buildFlags(t, flags); buildDimensions(t, m, id); buildControl(t, 0x0081); // edit break; case EList: buildFlags(t, flags|WS_TABSTOP|WS_VSCROLL|WS_BORDER); buildDimensions(t, m, id); buildControl(t, 0x0083); // list box break; case ECombo: buildFlags(t, flags|CBS_DROPDOWNLIST|WS_TABSTOP); buildDimensions(t, m, id); buildControl(t, 0x0085); // combo box break; default: break; } } } bool PDialog::buildAndRun(int w, int h) { computeDimensions(w, h); RECT rect; GetWindowRect(iParent, &rect); int pw = (rect.right - rect.left) * 4 / iBaseX; int ph = (rect.bottom - rect.top) * 8 / iBaseY; std::vector t; // Dialog flags buildFlags(t, WS_POPUP | WS_BORDER | DS_SHELLFONT | WS_SYSMENU | DS_MODALFRAME | WS_CAPTION); t.push_back(iElements.size()); t.push_back((pw - w)/2); // offset of popup-window from parent window t.push_back((ph - h)/2); t.push_back(w); t.push_back(h); // menu t.push_back(0); // class t.push_back(0); // title buildString(t, iCaption.c_str()); // for DS_SHELLFONT t.push_back(10); buildString(t,"MS Shell Dlg"); buildElements(t); int res = DialogBoxIndirectParamW((HINSTANCE) GetWindowLongPtr(iParent, GWLP_HINSTANCE), (LPCDLGTEMPLATE) &t[0], iParent, (DLGPROC) dialogProc, (LPARAM) this); // retrieveValues() has been called before EndDialog! hDialog = nullptr; // already destroyed by Windows return (res > 0); } void PDialog::computeDimensions(int &w, int &h) { int minWidth[iNoCols]; int minHeight[iNoRows]; for (int i = 0; i < iNoCols; ++i) minWidth[i] = 0; for (int i = 0; i < iNoRows; ++i) minHeight[i] = 0; int buttonWidth = -PAD; for (int i = 0; i < int(iElements.size()); ++i) { SElement &m = iElements[i]; if (m.row < 0) { // button row buttonWidth += m.minWidth + PAD; } else { int wd = m.minWidth / m.colspan; for (int j = m.col; j < m.col + m.colspan; ++j) { if (wd > minWidth[j]) minWidth[j] = wd; } int ht = m.minHeight / m.rowspan; for (int j = m.row; j < m.row + m.rowspan; ++j) { if (ht > minHeight[j]) minHeight[j] = ht; } } } // Convert w and h to dialog units: w = w * 4 / iBaseX; h = h * 8 / iBaseY; while (int(iColStretch.size()) < iNoCols) iColStretch.push_back(0); while (int(iRowStretch.size()) < iNoRows) iRowStretch.push_back(0); int totalW = BORDER + BORDER - PAD; int totalWStretch = 0; for (int i = 0; i < iNoCols; ++i) { totalW += minWidth[i] + PAD; totalWStretch += iColStretch[i]; } int totalH = BORDER + BORDER + BUTTONHEIGHT; int totalHStretch = 0; for (int i = 0; i < iNoRows; ++i) { totalH += minHeight[i] + PAD; totalHStretch += iRowStretch[i]; } if (totalW > w) w = totalW; if (totalH > h) h = totalH; if (buttonWidth + BORDER + BORDER > w) w = buttonWidth + BORDER + BORDER; iButtonX = (w - buttonWidth) / 2; int spareW = w - totalW; int spareH = h - totalH; iColWidth.resize(iNoCols); iRowHeight.resize(iNoRows); if (totalWStretch == 0) { // spread spareW equally int extra = spareW / iNoCols; for (int i = 0; i < iNoCols; ++i) iColWidth[i] = minWidth[i] + extra; } else { for (int i = 0; i < iNoCols; ++i) { int extra = spareW * iColStretch[i] / totalWStretch; iColWidth[i] = minWidth[i] + extra; } } if (totalHStretch == 0) { // spread spareH equally int extra = spareH / iNoRows; for (int i = 0; i < iNoRows; ++i) iRowHeight[i] = minHeight[i] + extra; } else { for (int i = 0; i < iNoRows; ++i) { int extra = spareH * iRowStretch[i] / totalHStretch; iRowHeight[i] = minHeight[i] + extra; } } /* fprintf(stderr, "iColWidth\n"); for (int i = 0; i < iNoCols; ++i) fprintf(stderr, "%d ", iColWidth[i]); fprintf(stderr, "\n"); fflush(stderr); */ } void PDialog::enableItem(int idx, bool value) { EnableWindow(GetDlgItem(hDialog, idx+IDBASE), value); } // -------------------------------------------------------------------- static int dialog_constructor(lua_State *L) { HWND parent = check_winid(L, 1); const char *s = luaL_checklstring(L, 2, nullptr); Dialog **dlg = (Dialog **) lua_newuserdata(L, sizeof(Dialog *)); *dlg = nullptr; luaL_getmetatable(L, "Ipe.dialog"); lua_setmetatable(L, -2); *dlg = new PDialog(L, parent, s); return 1; } // -------------------------------------------------------------------- class PMenu : public Menu { public: PMenu(HWND parent); virtual ~PMenu(); virtual int add(lua_State *L); virtual int execute(lua_State *L); private: struct Item { std::string name; std::string itemName; int itemIndex; }; std::vector items; int currentId; HMENU hMenu; HWND hwnd; std::vector bitmaps; }; PMenu::PMenu(HWND parent) { hMenu = CreatePopupMenu(); hwnd = parent; } PMenu::~PMenu() { if (hMenu) DestroyMenu(hMenu); hMenu = nullptr; for (int i = 0; i < int(bitmaps.size()); ++i) DeleteObject(bitmaps[i]); } int PMenu::execute(lua_State *L) { int vx = (int)luaL_checkinteger(L, 2); int vy = (int)luaL_checkinteger(L, 3); int result = TrackPopupMenu(hMenu, TPM_NONOTIFY | TPM_RETURNCMD | TPM_RIGHTBUTTON, vx, vy, 0, hwnd, nullptr); if (1 <= result && result <= int(items.size())) { result -= 1; lua_pushstring(L, items[result].name.c_str()); lua_pushinteger(L, items[result].itemIndex); if (items[result].itemName.c_str()) lua_pushstring(L, items[result].itemName.c_str()); else lua_pushstring(L, ""); return 3; } return 0; } static HBITMAP colorIcon(double red, double green, double blue) { int r = int(red * 255.0); int g = int(green * 255.0); int b = int(blue * 255.0); COLORREF rgb = RGB(r, g, b); int cx = GetSystemMetrics(SM_CXMENUCHECK); int cy = GetSystemMetrics(SM_CYMENUCHECK); HDC hdc = GetDC(nullptr); HDC memDC = CreateCompatibleDC(hdc); HBITMAP bm = CreateCompatibleBitmap(hdc, cx, cy); SelectObject(memDC, bm); for (int y = 0; y < cy; ++y) { for (int x = 0; x < cx; ++x) { SetPixel(memDC, x, y, rgb); } } DeleteDC(memDC); ReleaseDC(nullptr, hdc); return bm; } int PMenu::add(lua_State *L) { const char *name = luaL_checklstring(L, 2, nullptr); WString title(luaL_checklstring(L, 3, nullptr)); if (lua_gettop(L) == 3) { AppendMenuW(hMenu, MF_STRING, items.size() + 1, title.data()); Item item; item.name = name; item.itemIndex = 0; items.push_back(item); } else { luaL_argcheck(L, lua_istable(L, 4), 4, "argument is not a table"); bool hasmap = !lua_isnoneornil(L, 5) && lua_isfunction(L, 5); bool hastable = !hasmap && !lua_isnoneornil(L, 5); bool hascolor = !lua_isnoneornil(L, 6) && lua_isfunction(L, 6); bool hascheck = !hascolor && !lua_isnoneornil(L, 6); if (hastable) luaL_argcheck(L, lua_istable(L, 5), 5, "argument is not a function or table"); const char *current = nullptr; if (hascheck) { luaL_argcheck(L, lua_isstring(L, 6), 6, "argument is not a function or string"); current = luaL_checklstring(L, 6, nullptr); } int no = lua_rawlen(L, 4); HMENU sm = CreatePopupMenu(); for (int i = 1; i <= no; ++i) { lua_rawgeti(L, 4, i); luaL_argcheck(L, lua_isstring(L, -1), 4, "items must be strings"); int id = items.size() + 1; const char *item = lua_tolstring(L, -1, nullptr); if (hastable) { lua_rawgeti(L, 5, i); luaL_argcheck(L, lua_isstring(L, -1), 5, "labels must be strings"); } else if (hasmap) { lua_pushvalue(L, 5); // function lua_pushnumber(L, i); // index lua_pushvalue(L, -3); // name luacall(L, 2, 1); // function returns label luaL_argcheck(L, lua_isstring(L, -1), 5, "function does not return string"); } else lua_pushvalue(L, -1); WString text(tostring(L, -1)); AppendMenuW(sm, MF_STRING, id, text.data()); Item mitem; mitem.name = name; mitem.itemName = item; mitem.itemIndex = i; items.push_back(mitem); if (hascheck && !strcmp(item, current)) CheckMenuItem(sm, id, MF_CHECKED); if (hascolor) { lua_pushvalue(L, 6); // function lua_pushnumber(L, i); // index lua_pushvalue(L, -4); // name luacall(L, 2, 3); // function returns red, green, blue double red = luaL_checknumber(L, -3); double green = luaL_checknumber(L, -2); double blue = luaL_checknumber(L, -1); lua_pop(L, 3); // pop result HBITMAP bits = colorIcon(red, green, blue); bitmaps.push_back(bits); SetMenuItemBitmaps(sm, id, MF_BYCOMMAND, bits, bits); } lua_pop(L, 2); // item, text } AppendMenuW(hMenu, MF_STRING | MF_POPUP, (UINT_PTR) sm, title.data()); } return 0; } // -------------------------------------------------------------------- static int menu_constructor(lua_State *L) { HWND hwnd = check_winid(L, 1); Menu **m = (Menu **) lua_newuserdata(L, sizeof(Menu *)); *m = nullptr; luaL_getmetatable(L, "Ipe.menu"); lua_setmetatable(L, -2); *m = new PMenu(hwnd); return 1; } // -------------------------------------------------------------------- class PTimer : public Timer { public: PTimer(lua_State *L0, int lua_object, const char *method); virtual ~PTimer(); virtual int setInterval(lua_State *L); virtual int active(lua_State *L); virtual int start(lua_State *L); virtual int stop(lua_State *L); protected: void elapsed(); static void CALLBACK TimerProc(HWND hwnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime); static std::vector all_timers; protected: UINT_PTR iTimer; UINT iInterval; }; std::vector PTimer::all_timers; void CALLBACK PTimer::TimerProc(HWND, UINT, UINT_PTR id, DWORD) { for (int i = 0; i < int(all_timers.size()); ++i) { if (id == all_timers[i]->iTimer) { all_timers[i]->elapsed(); return; } } } PTimer::PTimer(lua_State *L0, int lua_object, const char *method) : Timer(L0, lua_object, method) { iTimer = 0; iInterval = 0; all_timers.push_back(this); } PTimer::~PTimer() { if (iTimer) KillTimer(nullptr, iTimer); // remove it from all_timers for (int i = 0; i < int(all_timers.size()); ++i) { if (all_timers[i] == this) { all_timers.erase(all_timers.begin() + i); return; } } } void PTimer::elapsed() { callLua(); if (iSingleShot) { KillTimer(nullptr, iTimer); iTimer = 0; } } int PTimer::setInterval(lua_State *L) { int t = (int)luaL_checkinteger(L, 2); iInterval = t; if (iTimer) SetTimer(nullptr, iTimer, iInterval, TimerProc); return 0; } int PTimer::active(lua_State *L) { lua_pushboolean(L, (iTimer != 0)); return 1; } int PTimer::start(lua_State *L) { if (iTimer == 0) iTimer = SetTimer(nullptr, 0, iInterval, TimerProc); return 0; } int PTimer::stop(lua_State *L) { if (iTimer) { KillTimer(nullptr, iTimer); iTimer = 0; } return 0; } // -------------------------------------------------------------------- static int timer_constructor(lua_State *L) { luaL_argcheck(L, lua_istable(L, 1), 1, "argument is not a table"); const char *method = luaL_checklstring(L, 2, nullptr); Timer **t = (Timer **) lua_newuserdata(L, sizeof(Timer *)); *t = nullptr; luaL_getmetatable(L, "Ipe.timer"); lua_setmetatable(L, -2); // create a table with weak reference to Lua object lua_createtable(L, 1, 1); lua_pushliteral(L, "v"); lua_setfield(L, -2, "__mode"); lua_pushvalue(L, -1); lua_setmetatable(L, -2); lua_pushvalue(L, 1); lua_rawseti(L, -2, 1); int lua_object = luaL_ref(L, LUA_REGISTRYINDEX); *t = new PTimer(L, lua_object, method); return 1; } // -------------------------------------------------------------------- static COLORREF custom[16] = { 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff }; static int ipeui_getColor(lua_State *L) { HWND hwnd = check_winid(L, 1); // const char *title = luaL_checkstring(L, 2); double r = luaL_checknumber(L, 3); double g = luaL_checknumber(L, 4); double b = luaL_checknumber(L, 5); CHOOSECOLOR cc; ZeroMemory(&cc, sizeof(cc)); cc.lStructSize = sizeof(cc); cc.hwndOwner = hwnd; cc.Flags = CC_FULLOPEN | CC_RGBINIT; cc.rgbResult = RGB(int(r * 255), int(g * 255), int(b * 255)); cc.lpCustColors = custom; if (ChooseColor(&cc)) { lua_pushnumber(L, GetRValue(cc.rgbResult) / 255.0); lua_pushnumber(L, GetGValue(cc.rgbResult) / 255.0); lua_pushnumber(L, GetBValue(cc.rgbResult) / 255.0); return 3; } else return 0; } // -------------------------------------------------------------------- static int ipeui_fileDialog(lua_State *L) { static const char * const typenames[] = { "open", "save", nullptr }; HWND hwnd = check_winid(L, 1); int type = luaL_checkoption(L, 2, nullptr, typenames); WString caption(luaL_checklstring(L, 3, nullptr)); if (!lua_istable(L, 4)) luaL_argerror(L, 4, "table expected for filters"); std::wstring filters; int nFilters = lua_rawlen(L, 4); for (int i = 1; i <= nFilters; ++i) { lua_rawgeti(L, 4, i); luaL_argcheck(L, lua_isstring(L, -1), 4, "filter entry is not a string"); WString el(tostring(L, -1)); filters += el; lua_pop(L, 1); // element i } filters.push_back(0); // terminate list const char *dir = nullptr; if (!lua_isnoneornil(L, 5)) dir = luaL_checklstring(L, 5, nullptr); const char *name = nullptr; if (!lua_isnoneornil(L, 6)) name = luaL_checklstring(L, 6, nullptr); int selected = 0; if (!lua_isnoneornil(L, 7)) selected = luaL_checkinteger(L, 7); OPENFILENAMEW ofn; wchar_t szFileName[MAX_PATH] = L""; ZeroMemory(&ofn, sizeof(ofn)); ofn.lStructSize = sizeof(ofn); ofn.hwndOwner = hwnd; ofn.lpstrFilter = &filters[0]; ofn.nFilterIndex = selected; ofn.lpstrFile = szFileName; ofn.nMaxFile = MAX_PATH; ofn.lpstrDefExt = L"ipe"; if (name) { WString wname(name); wcsncpy(szFileName, wname.data(), MAX_PATH); } if (dir) { WString wdir(dir); ofn.lpstrInitialDir = wdir.data(); } ofn.lpstrTitle = caption.data(); BOOL result; if (type == 0) { ofn.Flags = OFN_EXPLORER | OFN_FILEMUSTEXIST | OFN_HIDEREADONLY; result = GetOpenFileNameW(&ofn); } else { ofn.Flags = OFN_EXPLORER | OFN_PATHMUSTEXIST | OFN_HIDEREADONLY; result = GetSaveFileNameW(&ofn); } if (!result) return 0; std::string s = wideToUtf8(ofn.lpstrFile); lua_pushstring(L, s.c_str()); lua_pushinteger(L, ofn.nFilterIndex); return 2; } // -------------------------------------------------------------------- static int ipeui_messageBox(lua_State *L) { static const char * const options[] = { "none", "warning", "information", "question", "critical", nullptr }; static const char * const buttontype[] = { "ok", "okcancel", "yesnocancel", "discardcancel", "savediscardcancel", nullptr }; HWND hwnd = check_winid(L, 1); int type = luaL_checkoption(L, 2, "none", options); const char *text = luaL_checklstring(L, 3, nullptr); const char *details = nullptr; if (!lua_isnoneornil(L, 4)) details = luaL_checklstring(L, 4, nullptr); int buttons = 0; if (lua_isnumber(L, 5)) buttons = (int)luaL_checkinteger(L, 5); else if (!lua_isnoneornil(L, 5)) buttons = luaL_checkoption(L, 5, nullptr, buttontype); UINT uType = MB_APPLMODAL; switch (type) { case 0: default: break; case 1: uType |= MB_ICONWARNING; break; case 2: uType |= MB_ICONINFORMATION; break; case 3: uType |= MB_ICONQUESTION; break; case 4: uType |= MB_ICONERROR; break; } switch (buttons) { case 0: default: uType |= MB_OK; break; case 1: uType |= MB_OKCANCEL; break; case 2: uType |= MB_YESNOCANCEL; break; case 3: // should be Discard Cancel uType |= MB_OKCANCEL; break; case 4: // should be Save Discard Cancel uType |= MB_YESNOCANCEL; break; } int ret = -1; if (details) { char buf[strlen(text) + strlen(details) + 8]; sprintf(buf, "%s\n\n%s", text, details); WString wbuf(buf); ret = MessageBoxW(hwnd, wbuf.data(), L"Ipe", uType); } else ret = MessageBoxW(hwnd, WString(text).data(), L"Ipe", uType); switch (ret) { case IDOK: case IDYES: lua_pushnumber(L, 1); break; case IDNO: case IDIGNORE: lua_pushnumber(L, 0); break; case IDCANCEL: default: lua_pushnumber(L, -1); break; } return 1; } // -------------------------------------------------------------------- BOOL CALLBACK waitDialogProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { switch (message) { case WM_INITDIALOG: { HWND *p = (HWND *) lParam; *p = hwnd; return TRUE; } default: return FALSE; } } VOID CALLBACK waitCallback(PVOID lpParameter, BOOLEAN timerOrWaitFired) { HWND *hDialog = (HWND *) lpParameter; if (*hDialog) EndDialog(*hDialog, 1); } static int ipeui_wait(lua_State *L) { Dialog **dlg = check_dialog(L, 1); HWND parent = (*dlg)->winId(); std::vector t; // Dialog flags buildFlags(t, WS_POPUP | WS_BORDER | DS_SHELLFONT | WS_SYSMENU | DS_MODALFRAME | WS_CAPTION); t.push_back(1); t.push_back(0); // offset of popup-window from parent window t.push_back(0); t.push_back(240); t.push_back(60); // menu t.push_back(0); // class t.push_back(0); // title buildString(t, "Ipe: waiting"); // for DS_SHELLFONT t.push_back(10); buildString(t,"MS Shell Dlg"); if (t.size() % 2 != 0) t.push_back(0); buildFlags(t, WS_CHILD|WS_VISIBLE|SS_LEFT); t.push_back(40); t.push_back(20); t.push_back(120); t.push_back(20); t.push_back(IDBASE); buildControl(t, 0x0082, "Waiting for external editor"); // Declare and initialize process blocks PROCESS_INFORMATION processInformation; STARTUPINFOW startupInfo; memset(&processInformation, 0, sizeof(processInformation)); memset(&startupInfo, 0, sizeof(startupInfo)); startupInfo.cb = sizeof(startupInfo); // Call the executable program const char *cmd = luaL_checklstring(L, 2, nullptr); WString wcmd(cmd); int result = CreateProcessW(nullptr, wcmd.data(), nullptr, nullptr, FALSE, NORMAL_PRIORITY_CLASS|CREATE_NO_WINDOW, nullptr, nullptr, &startupInfo, &processInformation); if (result == 0) return 0; HWND dialogHandle = nullptr; HANDLE waitHandle; RegisterWaitForSingleObject(&waitHandle, processInformation.hProcess, waitCallback, &dialogHandle, INFINITE, WT_EXECUTEINWAITTHREAD|WT_EXECUTEONLYONCE); DialogBoxIndirectParamW((HINSTANCE) GetWindowLongPtr(parent, GWLP_HINSTANCE), (LPCDLGTEMPLATE) &t[0], parent, (DLGPROC) waitDialogProc, (LPARAM) &dialogHandle); UnregisterWait(waitHandle); CloseHandle(processInformation.hProcess); CloseHandle(processInformation.hThread); return 0; } // -------------------------------------------------------------------- static int ipeui_currentDateTime(lua_State *L) { SYSTEMTIME st; GetLocalTime(&st); char buf[32]; sprintf(buf, "%04d%02d%02d%02d%02d%02d", st.wYear, st.wMonth, st.wDay, st.wHour, st.wMinute, st.wSecond); lua_pushstring(L, buf); return 1; } static int ipeui_startBrowser(lua_State *L) { const char *url = luaL_checklstring(L, 1, nullptr); long long int res = (long long int) ShellExecuteA(nullptr, "open", url, nullptr, nullptr, SW_SHOWNORMAL); lua_pushboolean(L, (res >= 32)); return 1; } // -------------------------------------------------------------------- static const struct luaL_Reg ipeui_functions[] = { { "Dialog", dialog_constructor }, { "Menu", menu_constructor }, { "Timer", timer_constructor }, { "getColor", ipeui_getColor }, { "fileDialog", ipeui_fileDialog }, { "messageBox", ipeui_messageBox }, { "waitDialog", ipeui_wait }, { "currentDateTime", ipeui_currentDateTime }, { "startBrowser", ipeui_startBrowser }, { nullptr, nullptr } }; // -------------------------------------------------------------------- int luaopen_ipeui(lua_State *L) { luaL_newlib(L, ipeui_functions); lua_setglobal(L, "ipeui"); luaopen_ipeui_common(L); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipeui/ipeui_wstring.h0000644000175000017500000000352713561570220017206 0ustar otfriedotfried// -------------------------------------------------------------------- // Helper class for Win32 Unicode interface // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEUI_WSTRING_H #define IPEUI_WSTRING_H class WString : public std::wstring { public: #ifdef IPEBASE_H WString(const ipe::String &s) : std::wstring( std::move(s.w()) ) { /* nothing */ } #endif WString(const std::string &s) { init(s.data(), s.size()); } WString(const char *s) { init(s, -1); } private: void init(const char *s, int len); }; extern BOOL setWindowText(HWND h, const char *s); extern void sendMessage(HWND h, UINT code, const char *t, WPARAM wParam = 0); // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipeui/ipeui_gtk.cpp0000644000175000017500000006413013561570220016626 0ustar otfriedotfried// -------------------------------------------------------------------- // Lua bindings for GTK dialogs // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeui_common.h" // -------------------------------------------------------------------- class PDialog : public Dialog { public: PDialog(lua_State *L0, WINID parent, const char *caption); virtual ~PDialog(); virtual void setMapped(lua_State *L, int idx); virtual bool buildAndRun(int w, int h); virtual void retrieveValues(); virtual void enableItem(int idx, bool value); virtual void acceptDialog(lua_State *L); private: static void setListBoxRow(GtkTreeView *w, int row); static GtkWidget *createListBox(const SElement &m); static void fillListStore(GtkListStore *store, const SElement &m); static void itemResponse(GtkWidget *item, PDialog *dlg); private: std::vector iWidgets; }; PDialog::PDialog(lua_State *L0, WINID parent, const char *caption) : Dialog(L0, parent, caption) { // } PDialog::~PDialog() { // } void PDialog::acceptDialog(lua_State *L) { int accept = lua_toboolean(L, 2); (void) accept; // TODO // QDialog::done(accept); } void PDialog::itemResponse(GtkWidget *item, PDialog *dlg) { for (int i = 0; i < int(dlg->iWidgets.size()); ++i) { if (dlg->iWidgets[i] == item) { dlg->callLua(dlg->iElements[i].lua_method); return; } } } void PDialog::setMapped(lua_State *L, int idx) { SElement &m = iElements[idx]; GtkWidget *w = iWidgets[idx]; switch (m.type) { case ELabel: gtk_label_set_text(GTK_LABEL(w), m.text.z()); break; case ECheckBox: gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(w), m.value); break; case ETextEdit: gtk_text_buffer_set_text(gtk_text_view_get_buffer(GTK_TEXT_VIEW(w)), m.text.z(), -1); break; case EInput: gtk_entry_set_text(GTK_ENTRY(w), m.text.z()); break; case EList: if (lua_istable(L, 3)) { GtkTreeModel *mod = gtk_tree_view_get_model(GTK_TREE_VIEW(w)); fillListStore(GTK_LIST_STORE(mod), m); } setListBoxRow(GTK_TREE_VIEW(w), m.value); break; case ECombo: if (lua_istable(L, 3)) { GtkTreeModel *mod = gtk_combo_box_get_model(GTK_COMBO_BOX(w)); fillListStore(GTK_LIST_STORE(mod), m); } gtk_combo_box_set_active(GTK_COMBO_BOX(w), m.value); break; default: break; // EButton } } static String getTextEdit(GtkWidget *w) { GtkTextBuffer *buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(w)); GtkTextIter start; GtkTextIter end; gtk_text_buffer_get_iter_at_offset(buffer, &start, 0); gtk_text_buffer_get_iter_at_offset(buffer, &end, -1); gchar *s = gtk_text_buffer_get_text(buffer, &start, &end, TRUE); return String(s); } void PDialog::retrieveValues() { for (int i = 0; i < int(iElements.size()); ++i) { SElement &m = iElements[i]; GtkWidget *w = iWidgets[i]; switch (m.type) { case EInput: m.text = String(gtk_entry_get_text(GTK_ENTRY(w))); break; case ETextEdit: m.text = getTextEdit(w); break; case EList: { GtkTreeSelection *s = gtk_tree_view_get_selection(GTK_TREE_VIEW(w)); GtkTreeModel *model; GtkTreeIter iter; if (gtk_tree_selection_get_selected(s, &model, &iter)) { gint *path = gtk_tree_path_get_indices(gtk_tree_model_get_path(model, &iter)); m.value = path[0]; } else m.value = 0; } break; case ECombo: m.value = gtk_combo_box_get_active(GTK_COMBO_BOX(w)); break; case ECheckBox: m.value = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(w)); break; default: break; // label and button - nothing to do } } } void PDialog::enableItem(int idx, bool value) { gtk_widget_set_sensitive(iWidgets[idx], value); } void PDialog::setListBoxRow(GtkTreeView *w, int row) { GtkTreeSelection *s = gtk_tree_view_get_selection(w); GtkTreePath *path = gtk_tree_path_new_from_indices(row, -1); gtk_tree_selection_select_path(s, path); gtk_tree_path_free(path); } void PDialog::fillListStore(GtkListStore *store, const SElement &m) { GtkTreeIter iter; gtk_list_store_clear(store); for (int k = 0; k < int(m.items.size()); ++k) { gtk_list_store_append(store, &iter); gtk_list_store_set(store, &iter, 0, m.items[k].z(), -1); } } GtkWidget *PDialog::createListBox(const SElement &m) { GtkListStore *store = gtk_list_store_new(1, G_TYPE_STRING); fillListStore(store, m); GtkWidget *w = gtk_tree_view_new_with_model(GTK_TREE_MODEL(store)); g_object_unref(G_OBJECT(store)); GtkCellRenderer *renderer = gtk_cell_renderer_text_new (); // g_object_set(G_OBJECT(renderer), "foreground", "red", NULL); GtkTreeViewColumn *column = gtk_tree_view_column_new_with_attributes("Title", renderer, "text", 0, NULL); gtk_tree_view_append_column(GTK_TREE_VIEW(w), column); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(w), false); GtkTreeSelection *s = gtk_tree_view_get_selection(GTK_TREE_VIEW(w)); gtk_tree_selection_set_mode(s, GTK_SELECTION_SINGLE); setListBoxRow(GTK_TREE_VIEW(w), m.value); return w; } static GtkWidget *addScrollBar(GtkWidget *w) { GtkWidget *ww = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(ww), GTK_SHADOW_ETCHED_IN); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(ww), GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC); gtk_container_add(GTK_CONTAINER(ww), w); return ww; } static void ctrlEnterResponse(GtkWidget *, GtkDialog *dlg) { gtk_dialog_response(dlg, GTK_RESPONSE_ACCEPT); } static void escapeResponse(GtkWidget *, GtkDialog *dlg) { // catching escape, doing nothing } bool PDialog::buildAndRun(int w, int h) { hDialog = gtk_dialog_new(); gtk_window_set_title(GTK_WINDOW(hDialog), iCaption.z()); GtkAccelGroup *accel_group = gtk_accel_group_new(); gtk_window_add_accel_group(GTK_WINDOW(hDialog), accel_group); guint accel_key; GdkModifierType accel_mods; gtk_accelerator_parse("Return", &accel_key, &accel_mods); gtk_accel_group_connect(accel_group, accel_key, accel_mods, GtkAccelFlags(0), g_cclosure_new(G_CALLBACK(ctrlEnterResponse), hDialog, NULL)); if (iIgnoreEscape) { gtk_accelerator_parse("Escape", &accel_key, &accel_mods); gtk_accel_group_connect(accel_group, accel_key, accel_mods, GtkAccelFlags(0), g_cclosure_new(G_CALLBACK(escapeResponse), hDialog, NULL)); } if (w > 0 && h > 0) gtk_window_set_default_size(GTK_WINDOW(hDialog), w, h); GtkWidget *ca = gtk_dialog_get_content_area(GTK_DIALOG(hDialog)); GtkWidget *grid = gtk_table_new(iNoRows, iNoCols, FALSE); gtk_table_set_row_spacings(GTK_TABLE(grid), 8); gtk_table_set_col_spacings(GTK_TABLE(grid), 8); gtk_table_set_homogeneous(GTK_TABLE(grid), FALSE); gtk_container_set_border_width(GTK_CONTAINER(grid), 12); gtk_box_pack_start(GTK_BOX(ca), grid, TRUE, TRUE, 0); gtk_widget_show(grid); GtkWidget *aa = gtk_dialog_get_action_area(GTK_DIALOG(hDialog)); for (int i = 0; i < int(iElements.size()); ++i) { SElement &m = iElements[i]; GtkWidget *w = 0; GtkWidget *ww = 0; // for alignment int xOptions = 0; // GTK_EXPAND|GTK_SHRINK|GTK_FILL int yOptions = 0; // GTK_EXPAND|GTK_SHRINK|GTK_FILL if (m.row < 0) { if (m.flags & EAccept) { w = gtk_dialog_add_button(GTK_DIALOG(hDialog), m.text.z(), GTK_RESPONSE_ACCEPT); gtk_widget_set_can_default(w, TRUE); gtk_widget_grab_default(w); } else if (m.flags & EReject) w = gtk_dialog_add_button(GTK_DIALOG(hDialog), m.text.z(), GTK_RESPONSE_ACCEPT); else { w = gtk_button_new_with_label(m.text.z()); gtk_box_pack_start(GTK_BOX(aa), w, FALSE, FALSE, 0); gtk_widget_show(w); if (m.lua_method) g_signal_connect(w, "clicked", G_CALLBACK(itemResponse), this); } } else { switch (m.type) { case ELabel: ww = gtk_alignment_new(0.0, 0.5, 0.0, 1.0); w = gtk_label_new(m.text.z()); gtk_container_add(GTK_CONTAINER(ww), w); xOptions |= GTK_FILL; // left align in cell break; case EButton: w = gtk_button_new_with_label(m.text.z()); break; case ECheckBox: w = gtk_check_button_new_with_label(m.text.z()); if (m.lua_method) g_signal_connect(w, "toggled", G_CALLBACK(itemResponse), this); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(w), m.value); break; case EInput: w = gtk_entry_new(); gtk_entry_set_activates_default(GTK_ENTRY(w), TRUE); xOptions |= GTK_FILL; break; case ETextEdit: w = gtk_text_view_new(); gtk_text_view_set_editable(GTK_TEXT_VIEW(w), !(m.flags & EReadOnly)); gtk_text_buffer_set_text(gtk_text_view_get_buffer(GTK_TEXT_VIEW(w)), m.text.z(), -1); gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(w), GTK_WRAP_WORD); ww = addScrollBar(w); xOptions |= GTK_FILL; yOptions |= GTK_FILL; break; case ECombo: { ww = gtk_alignment_new(0.5, 0.0, 1.0, 0.0); GtkListStore *store = gtk_list_store_new(1, G_TYPE_STRING); fillListStore(store, m); w = gtk_combo_box_new_with_model(GTK_TREE_MODEL(store)); GtkCellRenderer *renderer = gtk_cell_renderer_text_new(); gtk_cell_layout_pack_start(GTK_CELL_LAYOUT(w), renderer, TRUE); gtk_cell_layout_add_attribute(GTK_CELL_LAYOUT(w), renderer, "text", 0); gtk_container_add(GTK_CONTAINER(ww), w); gtk_combo_box_set_active(GTK_COMBO_BOX(w), m.value); xOptions |= GTK_FILL; yOptions |= GTK_FILL; // align at top } break; case EList: w = createListBox(m); ww = addScrollBar(w); xOptions |= GTK_FILL; yOptions |= GTK_FILL; break; default: break; } for (int r = m.row; r < m.row + m.rowspan; ++r) if (iRowStretch[r] > 0) yOptions |= GTK_EXPAND; for (int c = m.col; c < m.col + m.colspan; ++c) if (iColStretch[c] > 0) xOptions |= GTK_EXPAND; if (ww == 0) ww = w; if (ww != 0) { gtk_table_attach(GTK_TABLE(grid), ww, m.col, m.col+m.colspan, m.row, m.row+m.rowspan, GtkAttachOptions(xOptions), GtkAttachOptions(yOptions), 0, 0); gtk_widget_show(ww); gtk_widget_show(w); } } if (m.flags & EDisabled) gtk_widget_set_sensitive(w, false); iWidgets.push_back(w); } gint result = gtk_dialog_run(GTK_DIALOG(hDialog)); retrieveValues(); // for future reference gtk_widget_destroy(hDialog); hDialog = NULL; return (result == GTK_RESPONSE_ACCEPT); } // -------------------------------------------------------------------- static int dialog_constructor(lua_State *L) { WINID parent = check_winid(L, 1); const char *s = luaL_checkstring(L, 2); Dialog **dlg = (Dialog **) lua_newuserdata(L, sizeof(Dialog *)); *dlg = 0; luaL_getmetatable(L, "Ipe.dialog"); lua_setmetatable(L, -2); *dlg = new PDialog(L, parent, s); return 1; } // -------------------------------------------------------------------- class PMenu : public Menu { public: PMenu(WINID parent); virtual ~PMenu(); virtual int add(lua_State *L); virtual int execute(lua_State *L); private: static void itemResponse(GtkWidget *item, PMenu *menu); static void deactivateResponse(GtkMenuShell *, PMenu *); static void positionResponse(GtkMenu *, gint *x, gint *y, gboolean *push_in, PMenu *menu); private: GtkWidget *iMenu; struct Item { gchar *name; gchar *itemName; int itemIndex; GtkWidget *widget; }; std::vector items; int iSelectedItem; int iPopupX; int iPopupY; }; void PMenu::itemResponse(GtkWidget *item, PMenu *menu) { for (int i = 0; i < int(menu->items.size()); ++i) { if (menu->items[i].widget == item) { menu->iSelectedItem = i; return; } } } void PMenu::deactivateResponse(GtkMenuShell *, PMenu *) { gtk_main_quit(); // drop out of nested loop } // NOT USED: Better to just let GTK use the cursor position void PMenu::positionResponse(GtkMenu *, gint *x, gint *y, gboolean *push_in, PMenu *menu) { *x = menu->iPopupX; *y = menu->iPopupY; *push_in = TRUE; } PMenu::PMenu(WINID parent) { iMenu = gtk_menu_new(); g_object_ref_sink(iMenu); g_signal_connect(iMenu, "deactivate", G_CALLBACK(deactivateResponse), this); } PMenu::~PMenu() { for (int i = 0; i < int(items.size()); ++i) { g_free(items[i].name); g_free(items[i].itemName); } g_object_unref(iMenu); } int PMenu::execute(lua_State *L) { iPopupX = (int)luaL_checkinteger(L, 2); iPopupY = (int)luaL_checkinteger(L, 3); iSelectedItem = -1; gtk_menu_popup(GTK_MENU(iMenu), NULL, NULL, // GtkMenuPositionFunc(positionResponse), this, NULL, NULL, 0, // initiated by button release gtk_get_current_event_time()); // nested main loop gtk_main(); if (0 <= iSelectedItem && iSelectedItem < int(items.size())) { lua_pushstring(L, items[iSelectedItem].name); lua_pushinteger(L, items[iSelectedItem].itemIndex); if (items[iSelectedItem].itemName) lua_pushstring(L, items[iSelectedItem].itemName); else lua_pushstring(L, ""); return 3; } else return 0; } static GtkWidget *colorIcon(double red, double green, double blue) { GtkWidget *w = gtk_drawing_area_new(); gtk_widget_set_size_request(w, 13, 13); GdkColor color; color.red = int(red * 65535.0); color.green = int(green * 65535.0); color.blue = int(blue * 65535.0); gtk_widget_modify_bg(w, GTK_STATE_NORMAL, &color); g_object_ref_sink(w); return w; } int PMenu::add(lua_State *L) { const char *name = luaL_checkstring(L, 2); const char *title = luaL_checkstring(L, 3); if (lua_gettop(L) == 3) { GtkWidget *w = gtk_menu_item_new_with_label(title); gtk_menu_shell_append(GTK_MENU_SHELL(iMenu), w); g_signal_connect(w, "activate", G_CALLBACK(itemResponse), this); gtk_widget_show(w); Item item; item.name = g_strdup(name); item.itemName = 0; item.itemIndex = 0; item.widget = w; items.push_back(item); } else { luaL_argcheck(L, lua_istable(L, 4), 4, "argument is not a table"); bool hasmap = !lua_isnoneornil(L, 5) && lua_isfunction(L, 5); bool hastable = !hasmap && !lua_isnoneornil(L, 5); bool hascolor = !lua_isnoneornil(L, 6) && lua_isfunction(L, 6); bool hascheck = !hascolor && !lua_isnoneornil(L, 6); if (hastable) luaL_argcheck(L, lua_istable(L, 5), 5, "argument is not a function or table"); const char *current = 0; if (hascheck) { luaL_argcheck(L, lua_isstring(L, 6), 6, "argument is not a function or string"); current = luaL_checkstring(L, 6); } GtkWidget *sm = gtk_menu_new(); int no = lua_rawlen(L, 4); for (int i = 1; i <= no; ++i) { lua_rawgeti(L, 4, i); luaL_argcheck(L, lua_isstring(L, -1), 4, "items must be strings"); const char *item = lua_tostring(L, -1); if (hastable) { lua_rawgeti(L, 5, i); luaL_argcheck(L, lua_isstring(L, -1), 5, "labels must be strings"); } else if (hasmap) { lua_pushvalue(L, 5); // function lua_pushnumber(L, i); // index lua_pushvalue(L, -3); // name lua_call(L, 2, 1); // function returns label luaL_argcheck(L, lua_isstring(L, -1), 5, "function does not return string"); } else lua_pushvalue(L, -1); const char *text = lua_tostring(L, -1); GtkWidget *w = 0; if (hascheck) w = gtk_check_menu_item_new_with_label(text); else if (hascolor) w = gtk_image_menu_item_new_with_label(text); else w = gtk_menu_item_new_with_label(text); if (hascheck && !g_strcmp0(item, current)) gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(w), true); gtk_menu_shell_append(GTK_MENU_SHELL(sm), w); g_signal_connect(w, "activate", G_CALLBACK(itemResponse), this); gtk_widget_show(w); Item mitem; mitem.name = g_strdup(name); mitem.itemName = g_strdup(item); mitem.itemIndex = i; mitem.widget = w; items.push_back(mitem); if (hascolor) { gtk_image_menu_item_set_always_show_image(GTK_IMAGE_MENU_ITEM(w), true); lua_pushvalue(L, 6); // function lua_pushnumber(L, i); // index lua_pushvalue(L, -4); // name lua_call(L, 2, 3); // function returns red, green, blue double red = luaL_checknumber(L, -3); double green = luaL_checknumber(L, -2); double blue = luaL_checknumber(L, -1); lua_pop(L, 3); // pop result GtkWidget *im = colorIcon(red, green, blue); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(w), im); g_object_unref(im); } lua_pop(L, 2); // item, text } GtkWidget *sme = gtk_menu_item_new_with_label(title); gtk_widget_show(sme); gtk_menu_item_set_submenu(GTK_MENU_ITEM(sme), sm); gtk_menu_shell_append(GTK_MENU_SHELL(iMenu), sme); gtk_widget_show(sme); } return 0; } // -------------------------------------------------------------------- static int menu_constructor(lua_State *L) { GtkWidget *parent = check_winid(L, 1); Menu **m = (Menu **) lua_newuserdata(L, sizeof(Menu *)); *m = 0; luaL_getmetatable(L, "Ipe.menu"); lua_setmetatable(L, -2); *m = new PMenu(parent); return 1; } // -------------------------------------------------------------------- static int ipeui_getColor(lua_State *L) { check_winid(L, 1); const char *title = luaL_checkstring(L, 2); double r = luaL_checknumber(L, 3); double g = luaL_checknumber(L, 4); double b = luaL_checknumber(L, 5); GdkColor color; color.red = int(r * 65535); color.green = int(g * 65535); color.blue = int(b * 65535); GtkWidget *dlg = gtk_color_selection_dialog_new(title); GtkColorSelection *sel = GTK_COLOR_SELECTION(gtk_color_selection_dialog_get_color_selection (GTK_COLOR_SELECTION_DIALOG(dlg))); gtk_color_selection_set_current_color(sel, &color); int result = gtk_dialog_run(GTK_DIALOG(dlg)); if (result == GTK_RESPONSE_OK) { gtk_color_selection_get_current_color(GTK_COLOR_SELECTION(sel), &color); gtk_widget_destroy(dlg); lua_pushnumber(L, color.red / 65535.0); lua_pushnumber(L, color.green / 65535.0); lua_pushnumber(L, color.blue / 65535.0); return 3; } gtk_widget_destroy(dlg); return 0; } // -------------------------------------------------------------------- static int ipeui_fileDialog(lua_State *L) { static const char * const typenames[] = { "open", "save", 0 }; GtkWindow *parent = GTK_WINDOW(check_winid(L, 1)); int type = luaL_checkoption(L, 2, 0, typenames); const char *caption = luaL_checkstring(L, 3); // GTK dialog uses no filters: args 4 and 7 are not used const char *dir = 0; if (!lua_isnoneornil(L, 5)) dir = luaL_checkstring(L, 5); const char *name = 0; if (!lua_isnoneornil(L, 6)) name = luaL_checkstring(L, 6); GtkWidget *dlg = gtk_file_chooser_dialog_new(caption, parent, (type ? GTK_FILE_CHOOSER_ACTION_SAVE : GTK_FILE_CHOOSER_ACTION_OPEN), GTK_STOCK_CANCEL, GTK_RESPONSE_REJECT, GTK_STOCK_OK, GTK_RESPONSE_ACCEPT, NULL); if (dir) gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(dlg), dir); if (name) gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(dlg), name); int result = gtk_dialog_run(GTK_DIALOG(dlg)); if (result == GTK_RESPONSE_ACCEPT) { char *fn = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(dlg)); lua_pushstring(L, fn); lua_pushinteger(L, 1); // name filters not used g_free(fn); gtk_widget_destroy(dlg); return 2; } gtk_widget_destroy(dlg); return 0; } // -------------------------------------------------------------------- static int ipeui_messageBox(lua_State *L) { static const char * const options[] = { "none", "warning", "information", "question", "critical", 0 }; static const char * const buttontype[] = { "ok", "okcancel", "yesnocancel", "discardcancel", "savediscardcancel", 0 }; GtkWidget *parent = check_winid(L, 1); int type = luaL_checkoption(L, 2, "none", options); const char *text = luaL_checkstring(L, 3); const char *details = 0; if (!lua_isnoneornil(L, 4)) details = luaL_checkstring(L, 4); int buttons = 0; if (lua_isnumber(L, 5)) buttons = (int)luaL_checkinteger(L, 5); else if (!lua_isnoneornil(L, 5)) buttons = luaL_checkoption(L, 5, 0, buttontype); GtkMessageType t = GTK_MESSAGE_OTHER; switch (type) { case 0: t = GTK_MESSAGE_OTHER; break; case 1: t = GTK_MESSAGE_WARNING; break; case 2: t = GTK_MESSAGE_INFO; break; case 3: t = GTK_MESSAGE_QUESTION; break; case 4: t = GTK_MESSAGE_ERROR; break; default: break; } GtkWidget *dlg = gtk_message_dialog_new(GTK_WINDOW(parent), GTK_DIALOG_MODAL, t, GTK_BUTTONS_NONE, "%s", text); if (details) gtk_message_dialog_format_secondary_text(GTK_MESSAGE_DIALOG(dlg), "%s", details); switch (buttons) { case 0: // "ok" gtk_dialog_add_buttons(GTK_DIALOG(dlg), GTK_STOCK_OK, GTK_RESPONSE_OK, NULL); break; case 1: // "okcancel" gtk_dialog_add_buttons(GTK_DIALOG(dlg), GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_OK, GTK_RESPONSE_OK, NULL); break; case 2: // "yesnocancel" gtk_dialog_add_buttons(GTK_DIALOG(dlg), GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_NO, GTK_RESPONSE_NO, GTK_STOCK_YES, GTK_RESPONSE_YES, NULL); break; case 3: // "discardcancel" gtk_dialog_add_buttons(GTK_DIALOG(dlg), GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_DISCARD, GTK_RESPONSE_NO, NULL); break; case 4: // "savediscardcancel" gtk_dialog_add_buttons(GTK_DIALOG(dlg), GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_DISCARD, GTK_RESPONSE_NO, GTK_STOCK_SAVE, GTK_RESPONSE_YES, NULL); default: break; } int result = gtk_dialog_run(GTK_DIALOG(dlg)); switch (result) { case GTK_RESPONSE_YES: case GTK_RESPONSE_OK: lua_pushnumber(L, 1); break; case GTK_RESPONSE_NO: lua_pushnumber(L, 0); break; case GTK_RESPONSE_CANCEL: default: lua_pushnumber(L, -1); break; } gtk_widget_destroy(dlg); return 1; } // -------------------------------------------------------------------- class PTimer : public Timer { public: PTimer(lua_State *L0, int lua_object, const char *method); virtual ~PTimer(); virtual int setInterval(lua_State *L); virtual int active(lua_State *L); virtual int start(lua_State *L); virtual int stop(lua_State *L); private: gboolean elapsed(); static gboolean timerCallback(gpointer data); private: guint iTimer; guint iInterval; }; gboolean PTimer::timerCallback(gpointer data) { PTimer *t = (PTimer *) data; return t->elapsed(); } PTimer::PTimer(lua_State *L0, int lua_object, const char *method) : Timer(L0, lua_object, method) { iTimer = 0; iInterval = 0; } PTimer::~PTimer() { if (iTimer != 0) g_source_remove(iTimer); } gboolean PTimer::elapsed() { callLua(); if (iSingleShot) { iTimer = 0; return FALSE; } else return TRUE; } // does not update interval on running timer int PTimer::setInterval(lua_State *L) { int t = (int)luaL_checkinteger(L, 2); iInterval = t; return 0; } int PTimer::active(lua_State *L) { lua_pushboolean(L, (iTimer != 0)); return 1; } int PTimer::start(lua_State *L) { if (iTimer == 0) { if (iInterval > 3000) iTimer = g_timeout_add_seconds(iInterval / 1000, GSourceFunc(timerCallback), this); else iTimer = g_timeout_add(iInterval, GSourceFunc(timerCallback), this); } return 0; } int PTimer::stop(lua_State *L) { if (iTimer != 0) { g_source_remove(iTimer); iTimer = 0; } return 0; } // -------------------------------------------------------------------- static int timer_constructor(lua_State *L) { luaL_argcheck(L, lua_istable(L, 1), 1, "argument is not a table"); const char *method = luaL_checkstring(L, 2); Timer **t = (Timer **) lua_newuserdata(L, sizeof(Timer *)); *t = 0; luaL_getmetatable(L, "Ipe.timer"); lua_setmetatable(L, -2); // create a table with weak reference to Lua object lua_createtable(L, 1, 1); lua_pushliteral(L, "v"); lua_setfield(L, -2, "__mode"); lua_pushvalue(L, -1); lua_setmetatable(L, -2); lua_pushvalue(L, 1); lua_rawseti(L, -2, 1); int lua_object = luaL_ref(L, LUA_REGISTRYINDEX); *t = new PTimer(L, lua_object, method); return 1; } // -------------------------------------------------------------------- static int ipeui_wait(lua_State *L) { luaL_error(L, "'waitDialog' is not yet implemented."); return 0; } // -------------------------------------------------------------------- static int ipeui_currentDateTime(lua_State *L) { time_t t = time(NULL); struct tm *tmp = localtime(&t); if (tmp == NULL) return 0; char buf[16]; sprintf(buf, "%04d%02d%02d%02d%02d%02d", 1900 + tmp->tm_year, 1 + tmp->tm_mon, tmp->tm_mday, tmp->tm_hour, tmp->tm_min, tmp->tm_sec); lua_pushstring(L, buf); return 1; } // -------------------------------------------------------------------- static const struct luaL_Reg ipeui_functions[] = { { "Dialog", dialog_constructor }, { "Menu", menu_constructor }, { "Timer", timer_constructor }, { "getColor", ipeui_getColor }, { "fileDialog", ipeui_fileDialog }, { "messageBox", ipeui_messageBox }, { "waitDialog", ipeui_wait }, { "currentDateTime", ipeui_currentDateTime }, { 0, 0}, }; // -------------------------------------------------------------------- int luaopen_ipeui(lua_State *L) { luaL_newlib(L, ipeui_functions); lua_setglobal(L, "ipeui"); luaopen_ipeui_common(L); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/config.mak0000644000175000017500000001005013561570220014756 0ustar otfriedotfried# -*- makefile -*- # -------------------------------------------------------------------- # # Ipe configuration for Unix # # *** This File is NOT USED on MAC OS X *** # # -------------------------------------------------------------------- # Optional component # -------------------------------------------------------------------- # # Compile support for online Latex translation? #IPECURL = 1 # # -------------------------------------------------------------------- # Include and linking options for libraries # -------------------------------------------------------------------- # # We just query "pkg-config" for the correct flags. If this doesn't # work on your system, enter the correct linker flags and directories # directly. # # The name of the Lua package (it could be "lua", "lua53", or "lua5.3") # LUA_PACKAGE ?= lua5.3 # ZLIB_CFLAGS ?= ZLIB_LIBS ?= -lz JPEG_CFLAGS ?= JPEG_LIBS ?= -ljpeg PNG_CFLAGS ?= $(shell pkg-config --cflags libpng) PNG_LIBS ?= $(shell pkg-config --libs libpng) FREETYPE_CFLAGS ?= $(shell pkg-config --cflags freetype2) FREETYPE_LIBS ?= $(shell pkg-config --libs freetype2) CAIRO_CFLAGS ?= $(shell pkg-config --cflags cairo) CAIRO_LIBS ?= $(shell pkg-config --libs cairo) LUA_CFLAGS ?= $(shell pkg-config --cflags $(LUA_PACKAGE)) LUA_LIBS ?= $(shell pkg-config --libs $(LUA_PACKAGE)) QT_CFLAGS ?= $(shell pkg-config --cflags Qt5Gui Qt5Widgets Qt5Core) QT_LIBS ?= $(shell pkg-config --libs Qt5Gui Qt5Widgets Qt5Core) ifdef IPECURL CURL_CFLAGS ?= $(shell pkg-config --cflags libcurl) CURL_LIBS ?= $(shell pkg-config --libs libcurl) endif # # Library needed to use dlopen/dlsym/dlclose calls # DL_LIBS ?= -ldl # # MOC is the Qt meta-object compiler. # Make sure it's the right one for Qt5. MOC ?= moc # # -------------------------------------------------------------------- # # The C++ compiler # I'm testing with g++ and clang++. # CXX = g++ # # Special compilation flags for compiling shared libraries # 64-bit Linux requires shared libraries to be compiled as # position independent code, that is -fpic or -fPIC # Qt5 seems to require -fPIC DLL_CFLAGS = -fPIC # # -------------------------------------------------------------------- # # Installing Ipe: # IPEVERS = 7.2.13 # # IPEPREFIX is the global prefix for the Ipe directory structure, which # you can override individually for any of the specific directories. # You could choose "/usr/local" or "/opt/ipe7", or # even "/usr", or "$(HOME)/ipe7" if you have to install in your home # directory. # # If you are installing Ipe in a networked environment, keep in mind # that executables, ipelets, and Ipe library are machine-dependent, # while the documentation and fonts can be shared. # #IPEPREFIX := /usr/local #IPEPREFIX := /usr #IPEPREFIX := /opt/ipe7 # ifeq "$(IPEPREFIX)" "" $(error You need to specify IPEPREFIX!) endif # # Where Ipe executables will be installed ('ipe', 'ipetoipe' etc) IPEBINDIR ?= $(IPEPREFIX)/bin # # Where the Ipe libraries will be installed ('libipe.so' etc.) IPELIBDIR ?= $(IPEPREFIX)/lib # # Where the header files for Ipelib will be installed: IPEHEADERDIR ?= $(IPEPREFIX)/include # # Where Ipelets will be installed: IPELETDIR ?= $(IPEPREFIX)/lib/ipe/$(IPEVERS)/ipelets # # Where Lua code will be installed # (This is the part of the Ipe program written in the Lua language) IPELUADIR ?= $(IPEPREFIX)/share/ipe/$(IPEVERS)/lua # # Directory where Ipe will look for scripts # (standard scripts will also be installed here) IPESCRIPTDIR ?= $(IPEPREFIX)/share/ipe/$(IPEVERS)/scripts # # Directory where Ipe will look for style files # (standard Ipe styles will also be installed here) IPESTYLEDIR ?= $(IPEPREFIX)/share/ipe/$(IPEVERS)/styles # # IPEICONDIR contains the icons used in the Ipe user interface # IPEICONDIR ?= $(IPEPREFIX)/share/ipe/$(IPEVERS)/icons # # IPEDOCDIR contains the Ipe documentation (mostly html files) # IPEDOCDIR ?= $(IPEPREFIX)/share/ipe/$(IPEVERS)/doc # # The Ipe manual pages are installed into IPEMANDIR # IPEMANDIR ?= $(IPEPREFIX)/share/man/man1 # # -------------------------------------------------------------------- ipe-7.2.13/src/ipelua/0000755000175000017500000000000013561570220014302 5ustar otfriedotfriedipe-7.2.13/src/ipelua/ipelib.cpp0000644000175000017500000004717013561570220016263 0ustar otfriedotfried// -------------------------------------------------------------------- // ipelib.cpp // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipelua.h" #include "ipedoc.h" #include "ipebitmap.h" #include #include using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- static const char * const format_name[] = { "xml", "pdf", "eps", "ipe5", "unknown" }; void ipelua::make_metatable(lua_State *L, const char *name, const struct luaL_Reg *methods) { luaL_newmetatable(L, name); lua_pushstring(L, "__index"); lua_pushvalue(L, -2); /* pushes the metatable */ lua_settable(L, -3); /* metatable.__index = metatable */ luaL_setfuncs(L, methods, 0); lua_pop(L, 1); } bool ipelua::is_type(lua_State *L, int ud, const char *tname) { if (lua_isuserdata(L, ud) && lua_getmetatable(L, ud)) { lua_getfield(L, LUA_REGISTRYINDEX, tname); if (lua_rawequal(L, -1, -2)) { lua_pop(L, 2); return true; } } return false; } String ipelua::check_filename(lua_State *L, int index) { return String(luaL_checklstring(L, index, nullptr)); } // -------------------------------------------------------------------- // Document // -------------------------------------------------------------------- static int document_constructor(lua_State *L) { bool has_fname = (lua_gettop(L) > 0); Document **d = (Document **) lua_newuserdata(L, sizeof(Document *)); *d = nullptr; luaL_getmetatable(L, "Ipe.document"); lua_setmetatable(L, -2); // should we load a document? if (has_fname) { String fname = check_filename(L, 1); int reason; *d = Document::load(fname.z(), reason); if (*d) return 1; lua_pop(L, 1); // pop empty document udata lua_pushnil(L); // return nil and ... switch (reason) { case Document::EVersionTooOld: lua_pushliteral(L, "The Ipe version of this document is too old"); break; case Document::EVersionTooRecent: lua_pushliteral(L, "The document was created by a newer version of Ipe"); break; case Document::EFileOpenError: lua_pushfstring(L, "Error opening file: %s", strerror(errno)); break; case Document::ENotAnIpeFile: lua_pushliteral(L, "The document was not created by Ipe"); break; default: lua_pushfstring(L, "Parsing error at position %d", reason); break; } lua_pushnumber(L, reason); return 3; } else { // create new empty document *d = new Document(); // create the first page (*d)->insert(0, Page::basic()); return 1; } } static int document_destruct(lua_State *L) { Document **d = check_document(L, 1); delete (*d); *d = nullptr; return 0; } static int document_tostring(lua_State *L) { check_document(L, 1); lua_pushfstring(L, "Document@%p", lua_topointer(L, 1)); return 1; } // -------------------------------------------------------------------- static int check_pageno(lua_State *L, int i, Document *d, int extra = 0) { int n = (int)luaL_checkinteger(L, i); luaL_argcheck(L, 1 <= n && n <= d->countPages() + extra, i, "invalid page number"); return n - 1; } static int document_index(lua_State *L) { Document **d = check_document(L, 1); if (lua_type(L, 2) == LUA_TNUMBER) { int n = check_pageno(L, 2, *d); push_page(L, (*d)->page(n), false); } else { const char *key = luaL_checklstring(L, 2, nullptr); if (!luaL_getmetafield(L, 1, key)) lua_pushnil(L); } return 1; } // Document --> int static int document_len(lua_State *L) { Document **d = check_document(L, 1); lua_pushinteger(L, (*d)->countPages()); return 1; } // arguments: document, counter static int document_page_iterator(lua_State *L) { Document **d = check_document(L, 1); int i = luaL_checkinteger(L, 2); i = i + 1; if (i <= (*d)->countPages()) { lua_pushinteger(L, i); // new counter push_page(L, (*d)->page(i-1), false); // page return 2; } else return 0; } // returns page iterator for use in for loop // returns iterator function, invariant state, control variable static int document_pages(lua_State *L) { (void) check_document(L, 1); lua_pushcfunction(L, document_page_iterator); // iterator function lua_pushvalue(L, 1); // document lua_pushinteger(L, 0); // counter return 3; } // "export", "nozip", "markedview" static uint32_t check_flags(lua_State *L, int index) { if (lua_isnoneornil(L, index)) return 0; luaL_argcheck(L, lua_istable(L, index), index, "argument is not a table"); uint32_t flags = 0; lua_getfield(L, index, "export"); if (lua_toboolean(L, -1)) flags |= SaveFlag::Export; lua_pop(L, 1); lua_getfield(L, index, "nozip"); if (lua_toboolean(L, -1)) flags |= SaveFlag::NoZip; lua_pop(L, 1); lua_getfield(L, index, "keepnotes"); if (lua_toboolean(L, -1)) flags |= SaveFlag::KeepNotes; lua_pop(L, 1); lua_getfield(L, index, "markedview"); if (lua_toboolean(L, -1)) flags |= SaveFlag::MarkedView; lua_pop(L, 1); return flags; } static int document_save(lua_State *L) { Document **d = check_document(L, 1); String fname = check_filename(L, 2); FileFormat format; if (lua_isnoneornil(L, 3)) format = Document::formatFromFilename(fname); else format = FileFormat(luaL_checkoption(L, 3, nullptr, format_name)); uint32_t flags = check_flags(L, 4); bool result = (*d)->save(fname.z(), format, flags); lua_pushboolean(L, result); return 1; } static int document_exportPages(lua_State *L) { Document **d = check_document(L, 1); String fname = check_filename(L, 2); uint32_t flags = check_flags(L, 3); int fromPage = check_pageno(L, 4, *d); int toPage = check_pageno(L, 5, *d); bool result = (*d)->exportPages(fname.z(), flags, fromPage, toPage); lua_pushboolean(L, result); return 1; } static int document_exportView(lua_State *L) { Document **d = check_document(L, 1); String fname = check_filename(L, 2); FileFormat format; if (lua_isnoneornil(L, 3)) format = Document::formatFromFilename(fname); else format = FileFormat(luaL_checkoption(L, 3, nullptr, format_name)); uint32_t flags = check_flags(L, 4); int pno = check_pageno(L, 5, *d); int vno = check_viewno(L, 6, (*d)->page(pno)); bool result = (*d)->exportView(fname.z(), format, flags, pno, vno); lua_pushboolean(L, result); return 1; } // Document --> int static int document_countTotalViews(lua_State *L) { Document **d = check_document(L, 1); lua_pushinteger(L, (*d)->countTotalViews()); return 1; } static int document_sheets(lua_State *L) { Document **d = check_document(L, 1); push_cascade(L, (*d)->cascade(), false); return 1; } static int document_replaceSheets(lua_State *L) { Document **d = check_document(L, 1); SCascade *p = check_cascade(L, 2); Cascade *sheets = p->cascade; if (!p->owned) sheets = new Cascade(*p->cascade); Cascade *old = (*d)->replaceCascade(sheets); p->owned = false; // now owned by document push_cascade(L, old); return 1; } static int document_runLatex(lua_State *L) { Document **d = check_document(L, 1); String docname; if (!lua_isnoneornil(L, 2)) docname = luaL_checklstring(L, 2, nullptr); String log; int result = (*d)->runLatex(docname, log); if (result == Document::ErrNone) { lua_pushboolean(L, true); lua_pushnil(L); lua_pushnil(L); } else if (result == Document::ErrNoText) { lua_pushboolean(L, true); lua_pushnil(L); lua_pushliteral(L, "notext"); } else { lua_pushboolean(L, false); switch (result) { case Document::ErrNoDir: lua_pushliteral(L, "Directory does not exist and cannot be created"); lua_pushliteral(L, "nodir"); break; case Document::ErrWritingSource: lua_pushliteral(L, "Error writing Latex source"); lua_pushliteral(L, "writingsource"); break; case Document::ErrOldPdfLatex: lua_pushliteral(L, "Your installed version of Pdflatex is too old"); lua_pushliteral(L, "oldpdflatex"); break; case Document::ErrRunLatex: lua_pushliteral(L, "There was an error trying to run Pdflatex"); lua_pushliteral(L, "runlatex"); break; case Document::ErrLatex: lua_pushliteral(L, "There were Latex errors"); lua_pushliteral(L, "latex"); break; case Document::ErrLatexOutput: lua_pushliteral(L, "There was an error reading the Pdflatex output"); lua_pushliteral(L, "latexoutput"); break; } } push_string(L, log); return 4; } static int document_checkStyle(lua_State *L) { Document **d = check_document(L, 1); AttributeSeq seq; (*d)->checkStyle(seq); lua_createtable(L, 0, seq.size()); for (int i = 0; i < size(seq); ++i) { push_attribute(L, seq[i]); lua_rawseti(L, -2, i+1); } return 1; } static int document_set(lua_State *L) { Document **d = check_document(L, 1); int no = check_pageno(L, 2, *d); Page *p = check_page(L, 3)->page; Page *old = (*d)->set(no, new Page(*p)); push_page(L, old); return 1; } static int document_insert(lua_State *L) { Document **d = check_document(L, 1); int no = check_pageno(L, 2, *d, 1); SPage *p = check_page(L, 3); (*d)->insert(no, new Page(*p->page)); return 0; } static int document_append(lua_State *L) { Document **d = check_document(L, 1); SPage *p = check_page(L, 2); (*d)->push_back(new Page(*p->page)); return 0; } static int document_remove(lua_State *L) { Document **d = check_document(L, 1); int no = check_pageno(L, 2, *d); Page *old = (*d)->remove(no); push_page(L, old); return 1; } static const char * const tex_engine_names[] = { "default", "pdftex", "xetex", "luatex" }; static int document_properties(lua_State *L) { Document **d = check_document(L, 1); Document::SProperties prop = (*d)->properties(); lua_createtable(L, 11, 0); push_string(L, prop.iTitle); lua_setfield(L, -2, "title"); push_string(L, prop.iAuthor); lua_setfield(L, -2, "author"); push_string(L, prop.iSubject); lua_setfield(L, -2, "subject"); push_string(L, prop.iKeywords); lua_setfield(L, -2, "keywords"); push_string(L, prop.iPreamble); lua_setfield(L, -2, "preamble"); push_string(L, prop.iCreated); lua_setfield(L, -2, "created"); push_string(L, prop.iModified); lua_setfield(L, -2, "modified"); push_string(L, prop.iCreator); lua_setfield(L, -2, "creator"); lua_pushboolean(L, prop.iFullScreen); lua_setfield(L, -2, "fullscreen"); lua_pushboolean(L, prop.iNumberPages); lua_setfield(L, -2, "numberpages"); lua_pushstring(L, tex_engine_names[int(prop.iTexEngine)]); lua_setfield(L, -2, "tex"); return 1; } static void propFlag(lua_State *L, const char *name, bool &flag) { lua_getfield(L, 2, name); if (!lua_isnil(L, -1)) flag = lua_toboolean(L, -1); lua_pop(L, 1); } static void propString(lua_State *L, const char *name, String &str) { lua_getfield(L, 2, name); if (lua_isstring(L, -1)) str = lua_tolstring(L, -1, nullptr); lua_pop(L, 1); } static int document_setProperties(lua_State *L) { Document **d = check_document(L, 1); luaL_checktype(L, 2, LUA_TTABLE); Document::SProperties prop = (*d)->properties(); // take from table propFlag(L, "numberpages", prop.iNumberPages); propFlag(L, "fullscreen", prop.iFullScreen); propString(L, "title", prop.iTitle); propString(L, "author", prop.iAuthor); propString(L, "subject", prop.iSubject); propString(L, "keywords", prop.iKeywords); propString(L, "preamble", prop.iPreamble); propString(L, "created", prop.iCreated); propString(L, "modified", prop.iModified); propString(L, "creator", prop.iCreator); String tex; propString(L, "tex", tex); for (int i = 0; i < 4; ++i) { if (!strcmp(tex.z(), tex_engine_names[i])) prop.iTexEngine = LatexType(i); } (*d)->setProperties(prop); return 0; } // -------------------------------------------------------------------- static const struct luaL_Reg document_methods[] = { { "__gc", document_destruct }, { "__tostring", document_tostring }, { "__len", document_len }, { "__index", document_index }, { "pages", document_pages }, { "save", document_save }, { "exportPages", document_exportPages }, { "exportView", document_exportView }, { "set", document_set }, { "insert", document_insert }, { "append", document_append }, { "remove", document_remove }, { "countTotalViews", document_countTotalViews }, { "sheets", document_sheets }, { "replaceSheets", document_replaceSheets }, { "runLatex", document_runLatex }, { "checkStyle", document_checkStyle }, { "properties", document_properties }, { "setProperties", document_setProperties }, { nullptr, nullptr }, }; // -------------------------------------------------------------------- static int file_format(lua_State *L) { String fname = check_filename(L, 1); FILE *fd = Platform::fopen(fname.z(), "rb"); if (!fd) luaL_error(L, "fopen error: %s", strerror(errno)); FileSource source(fd); FileFormat format = Document::fileFormat(source); fclose(fd); lua_pushstring(L, format_name[int(format)]); return 1; } static int ipe_normalizeangle(lua_State *L) { Angle alpha(luaL_checknumber(L, 1)); double low = luaL_checknumber(L, 2); lua_pushnumber(L, double(alpha.normalize(low))); return 1; } static int ipe_splinetobeziers(lua_State *L) { luaL_argcheck(L, lua_istable(L, 1), 1, "argument is not a table"); std::vector v; int no = lua_rawlen(L, 1); for (int i = 1; i <= no; ++i) { lua_rawgeti(L, 1, i); luaL_argcheck(L, is_type(L, -1, "Ipe.vector"), 1, "element is not a vector"); Vector *u = check_vector(L, -1); v.push_back(*u); lua_pop(L, 1); } bool closed = lua_toboolean(L, 2); bool oldStyle = lua_toboolean(L, 3); std::vector result; if (closed) Bezier::closedSpline(v.size(), &v[0], result); else if (oldStyle) Bezier::oldSpline(v.size(), &v[0], result); else Bezier::spline(v.size(), &v[0], result); lua_createtable(L, result.size(), 0); for (int i = 0; i < size(result); ++i) { lua_createtable(L, 4, 1); lua_pushliteral(L, "spline"); lua_setfield(L, -2, "type"); for (int k = 0; k < 4; ++k) { if (k == 0 && i > 0) push_vector(L, result[i-1].iV[3]); else push_vector(L, result[i].iV[k]); lua_rawseti(L, -2, k+1); } lua_rawseti(L, -2, i+1); } return 1; } static int ipe_fileExists(lua_State *L) { String s = check_filename(L, 1); lua_pushboolean(L, Platform::fileExists(s)); return 1; } static int ipe_realpath(lua_State *L) { String s = check_filename(L, 1); push_string(L, Platform::realPath(s)); return 1; } static int ipe_directory(lua_State *L) { const char *path = luaL_checklstring(L, 1, nullptr); std::vector files; if (!Platform::listDirectory(path, files)) luaL_error(L, "cannot list directory '%s'", path); lua_createtable(L, 0, files.size()); for (int i = 0; i < size(files); ++i) { push_string(L, files[i]); lua_rawseti(L, -2, i+1); } return 1; } #define l_checkmode(mode) \ (*mode != '\0' && strchr("rwa", *(mode++)) != nullptr && \ (*mode != '+' || ++mode) && /* skip if char is '+' */ \ (*mode != 'b' || ++mode) && /* skip if char is 'b' */ \ (*mode == '\0')) static int ipe_fclose (lua_State *L) { luaL_Stream *p = (luaL_Stream *) luaL_checkudata(L, 1, LUA_FILEHANDLE); int res = fclose(p->f); return luaL_fileresult(L, (res == 0), nullptr); } // open a file for reading or writing from Lua, // correctly handling UTF-8 filenames on Windows static int ipe_openFile(lua_State *L) { const char *filename = luaL_checklstring(L, 1, nullptr); const char *mode = luaL_optlstring(L, 2, "r", nullptr); luaL_Stream *p = (luaL_Stream *)lua_newuserdata(L, sizeof(luaL_Stream)); p->closef = nullptr; /* mark file handle as 'closed' */ luaL_setmetatable(L, LUA_FILEHANDLE); p->f = nullptr; p->closef = &ipe_fclose; const char *md = mode; /* to traverse/check mode */ luaL_argcheck(L, l_checkmode(md), 2, "invalid mode"); p->f = Platform::fopen(filename, mode); return (p->f == nullptr) ? luaL_fileresult(L, 0, filename) : 1; } static const char * const image_format_names[] = { "png", "jpeg" }; static int ipe_readImage(lua_State *L) { String s = check_filename(L, 1); int fmt = luaL_checkoption(L, 2, nullptr, image_format_names); Vector dotsPerInch; const char *errmsg = nullptr; Bitmap bmp = fmt ? Bitmap::readJpeg(s.z(), dotsPerInch, errmsg) : Bitmap::readPNG(s.z(), dotsPerInch, errmsg); if (bmp.isNull()) { lua_pushnil(L); lua_pushstring(L, errmsg); return 2; } Rect r(Vector::ZERO, Vector(bmp.width(), bmp.height())); Image *img = new Image(r, bmp); push_object(L, img); push_vector(L, dotsPerInch); return 2; } static int image_constructor(lua_State *L) { Rect *r = check_rect(L, 1); Object *s = check_object(L, 2)->obj; luaL_argcheck(L, s->type() == Object::EImage, 2, "not an image object"); Bitmap bm = s->asImage()->bitmap(); Image *img = new Image(*r, bm); push_object(L, img); return 1; } // -------------------------------------------------------------------- static const struct luaL_Reg ipelib_functions[] = { { "Document", document_constructor }, { "Page", page_constructor }, { "Vector", vector_constructor }, { "Direction", direction_constructor }, { "Matrix", matrix_constructor }, { "Translation", translation_constructor }, { "Rotation", rotation_constructor }, { "Rect", rect_constructor }, { "Line", line_constructor }, { "LineThrough", line_through }, { "Bisector", line_bisector }, { "Segment", segment_constructor }, { "Bezier", bezier_constructor }, { "Quad", quad_constructor }, { "Arc", arc_constructor }, { "Reference", reference_constructor }, { "Text", text_constructor }, { "Path", path_constructor }, { "Group", group_constructor }, { "Object", xml_constructor }, { "Sheet", sheet_constructor }, { "Sheets", cascade_constructor }, { "fileFormat", file_format }, { "Ipelet", ipelet_constructor }, { "normalizeAngle", ipe_normalizeangle }, { "splineToBeziers", ipe_splinetobeziers }, { "fileExists", ipe_fileExists }, { "realPath", ipe_realpath }, { "directory", ipe_directory }, { "openFile", ipe_openFile }, { "readImage", ipe_readImage }, { "Image", image_constructor }, { nullptr, nullptr } }; extern "C" int luaopen_ipe(lua_State *L) { Platform::initLib(IPELIB_VERSION); open_ipegeo(L); open_ipeobj(L); open_ipestyle(L); open_ipepage(L); open_ipelets(L); luaL_newmetatable(L, "Ipe.document"); luaL_setfuncs(L, document_methods, 0); lua_pop(L, 1); luaL_newlib(L, ipelib_functions); lua_setglobal(L, "ipe"); return 1; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelua/ipeluastyle.cpp0000644000175000017500000003443213561570220017354 0ustar otfriedotfried// -------------------------------------------------------------------- // ipeluastyle.cpp // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipelua.h" #include "ipestyle.h" #include "ipeiml.h" #include #include using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- static const char * const set_names[] = { "preamble", "linecap", "linejoin", "fillrule", "symbol", "layout", "gradient", nullptr }; int ipelua::test_option(lua_State *L, int i, const char * const *names) { const char *s = lua_tolstring(L, i, nullptr); const char * const *p = names; int what = 0; while (*p) { if (!strcmp(s, *p)) return what; ++what; ++p; } return -1; } // -------------------------------------------------------------------- void ipelua::push_sheet(lua_State *L, StyleSheet *s0, bool owned) { SSheet *s = (SSheet *) lua_newuserdata(L, sizeof(SSheet)); s->owned = owned; s->sheet = s0; luaL_getmetatable(L, "Ipe.sheet"); lua_setmetatable(L, -2); } int ipelua::sheet_constructor(lua_State *L) { if (lua_type(L, 1) == LUA_TSTRING) { String fname = check_filename(L, 1); FILE *fd = Platform::fopen(fname.z(), "rb"); if (!fd) { lua_pushnil(L); lua_pushfstring(L, "fopen error: %s", strerror(errno)); return 2; } FileSource source(fd); ImlParser parser(source); StyleSheet *sheet = parser.parseStyleSheet(); fclose(fd); if (!sheet) { lua_pushnil(L); lua_pushfstring(L, "Parsing error at %d", parser.parsePosition()); return 2; } push_sheet(L, sheet); } else if (lua_type(L, 2)== LUA_TSTRING) { size_t len;; const char *s = lua_tolstring(L, 2, &len); Buffer buf(s, len); BufferSource source(buf); ImlParser parser(source); StyleSheet *sheet = parser.parseStyleSheet(); if (!sheet) { lua_pushnil(L); lua_pushfstring(L, "Parsing error at %d", parser.parsePosition()); return 2; } push_sheet(L, sheet); } else push_sheet(L, new StyleSheet()); return 1; } static int sheet_clone(lua_State *L) { SSheet *p = check_sheet(L, 1); push_sheet(L, new StyleSheet(*p->sheet)); return 1; } static int sheet_destructor(lua_State *L) { SSheet *s = check_sheet(L, 1); if (s->owned) delete s->sheet; s->sheet = nullptr; return 0; } static int sheet_tostring(lua_State *L) { check_sheet(L, 1); lua_pushfstring(L, "Sheet@%p", lua_topointer(L, 1)); return 1; } // -------------------------------------------------------------------- // i must be positive static Attribute check_absolute_attribute(Kind kind, lua_State *L, int i) { switch (kind) { case EPen: case ESymbolSize: case EArrowSize: case ETextSize: case ETextStretch: case EOpacity: case EGridSize: case EAngleSize: { double v = luaL_checknumber(L, i); return Attribute(Fixed::fromInternal(int(v * 1000 + 0.5))); } case EColor: { Color color = check_color(L, i); return Attribute(color); } case EDashStyle: { const char *s = luaL_checklstring(L, i, nullptr); Attribute ds = Attribute::makeDashStyle(s); luaL_argcheck(L, !ds.isSymbolic(), i, "dashstyle is not absolute"); return ds; } case ETextStyle: case ELabelStyle: case EEffect: case ETiling: case EGradient: case ESymbol: luaL_argerror(L, i, "cannot set absolute value of this kind"); break; } return Attribute::NORMAL(); // placate compiler } static int sheet_add(lua_State *L) { StyleSheet *s = check_sheet(L, 1)->sheet; const char *what = luaL_checklstring(L, 2, nullptr); if (!strcmp(what, "symbol")) { const char *name = luaL_checklstring(L, 3, nullptr); SObject *obj = check_object(L, 4); Symbol symbol; symbol.iObject = obj->obj->clone(); symbol.iTransformations = ETransformationsAffine; s->addSymbol(Attribute(true, name), symbol); } else { Kind kind = Kind(luaL_checkoption(L, 2, nullptr, kind_names)); const char *name = luaL_checklstring(L, 3, nullptr); Attribute sym(true, String(name)); Attribute value = check_absolute_attribute(kind, L, 4); s->add(kind, sym, value); } return 0; } static int sheet_addfrom(lua_State *L) { StyleSheet *s = check_sheet(L, 1)->sheet; StyleSheet *t = check_sheet(L, 2)->sheet; Kind kind = Kind(luaL_checkoption(L, 3, nullptr, kind_names)); const char *name = luaL_checklstring(L, 4, nullptr); Attribute sym(true, name); switch (kind) { case EGradient: { const Gradient *g = t->findGradient(sym); if (!g) luaL_argerror(L, 4, "no such gradient"); s->addGradient(sym, *g); break; } case EEffect: { const Effect *e = t->findEffect(sym); if (!e) luaL_argerror(L, 4, "no such effect"); s->addEffect(sym, *e); break; } case ETiling: { const Tiling *g = t->findTiling(sym); if (!g) luaL_argerror(L, 4, "no such tiling"); s->addTiling(sym, *g); break; } default: luaL_argerror(L, 3, "cannot handle this kind"); break; } return 0; } static int sheet_remove(lua_State *L) { StyleSheet *s = check_sheet(L, 1)->sheet; Kind kind = Kind(luaL_checkoption(L, 2, nullptr, kind_names)); const char *name = luaL_checklstring(L, 3, nullptr); Attribute sym(true, name); s->remove(kind, sym); return 0; } static int sheet_isStandard(lua_State *L) { SSheet *p = check_sheet(L, 1); lua_pushboolean(L, p->sheet->isStandard()); return 1; } static int sheet_name(lua_State *L) { SSheet *p = check_sheet(L, 1); String n = p->sheet->name(); if (n.empty()) lua_pushnil(L); else push_string(L, n); return 1; } static int sheet_xml(lua_State *L) { SSheet *p = check_sheet(L, 1); bool with_bitmaps = lua_toboolean(L, 2); String data; StringStream stream(data); p->sheet->saveAsXml(stream, with_bitmaps); push_string(L, data); return 1; } static int sheet_setName(lua_State *L) { SSheet *p = check_sheet(L, 1); const char *name = luaL_checklstring(L, 2, nullptr); p->sheet->setName(name); return 0; } static int sheet_set(lua_State *L) { StyleSheet *s = check_sheet(L, 1)->sheet; int what = luaL_checkoption(L, 2, nullptr, set_names); switch (what) { case 0: // preamble s->setPreamble(luaL_checklstring(L, 3, nullptr)); break; case 1: // linecap s->setLineCap(check_property(EPropLineCap, L, 3).lineCap()); break; case 2: // linejoin s->setLineJoin(check_property(EPropLineJoin, L, 3).lineJoin()); break; case 3: // fillrule s->setFillRule(check_property(EPropFillRule, L, 3).fillRule()); break; default: luaL_argerror(L, 2, "invalid kind for 'set'"); break; } return 0; } // -------------------------------------------------------------------- static const struct luaL_Reg sheet_methods[] = { { "__gc", sheet_destructor }, { "__tostring", sheet_tostring }, { "clone", sheet_clone }, { "xml", sheet_xml }, { "add", sheet_add }, { "addFrom", sheet_addfrom }, { "remove", sheet_remove }, { "set", sheet_set }, { "isStandard", sheet_isStandard }, { "name", sheet_name }, { "setName", sheet_setName }, { nullptr, nullptr } }; // -------------------------------------------------------------------- void ipelua::push_cascade(lua_State *L, Cascade *s0, bool owned) { SCascade *s = (SCascade *) lua_newuserdata(L, sizeof(SCascade)); s->owned = owned; s->cascade = s0; luaL_getmetatable(L, "Ipe.cascade"); lua_setmetatable(L, -2); } int ipelua::cascade_constructor(lua_State *L) { push_cascade(L, new Cascade()); return 1; } static int cascade_clone(lua_State *L) { SCascade *s = check_cascade(L, 1); push_cascade(L, new Cascade(*s->cascade)); return 1; } static int cascade_destructor(lua_State *L) { SCascade *s = check_cascade(L, 1); if (s->owned) delete s->cascade; s->cascade = nullptr; return 0; } static int cascade_tostring(lua_State *L) { check_cascade(L, 1); lua_pushfstring(L, "Cascade@%p", lua_topointer(L, 1)); return 1; } // -------------------------------------------------------------------- // also works for symbol, gradient, tiling static int cascade_allNames(lua_State *L) { SCascade *p = check_cascade(L, 1); Kind kind = Kind(luaL_checkoption (L, 2, nullptr, kind_names)); AttributeSeq seq; p->cascade->allNames(kind, seq); lua_createtable(L, seq.size(), 0); for (int i = 0; i < size(seq); ++i) { push_string(L, seq[i].string()); lua_rawseti(L, -2, i + 1); } return 1; } static int push_layout(lua_State *L, const Layout &l) { lua_createtable(L, 0, 7); push_vector(L, l.iPaperSize); lua_setfield(L, -2, "papersize"); push_vector(L, l.iOrigin); lua_setfield(L, -2, "origin"); push_vector(L, l.iFrameSize); lua_setfield(L, -2, "framesize"); lua_pushnumber(L, l.iParagraphSkip); lua_setfield(L, -2, "paragraph_skip"); lua_pushboolean(L, l.iCrop); lua_setfield(L, -2, "crop"); return 1; } static int push_gradient(lua_State *L, const Gradient &g) { lua_createtable(L, 0, 6); lua_pushstring(L, (g.iType == Gradient::EAxial) ? "axial" : "radial"); lua_setfield(L, -2, "type"); lua_createtable(L, 2, 0); push_vector(L, g.iV[0]); lua_rawseti(L, -2, 1); push_vector(L, g.iV[1]); lua_rawseti(L, -2, 2); lua_setfield(L, -2, "v"); lua_pushboolean(L, g.iExtend); lua_setfield(L, -2, "extend"); push_matrix(L, g.iMatrix); lua_setfield(L, -2, "matrix"); if (g.iType == Gradient::ERadial) { lua_createtable(L, 2, 0); lua_pushnumber(L, g.iRadius[0]); lua_rawseti(L, -2, 1); lua_pushnumber(L, g.iRadius[1]); lua_rawseti(L, -2, 2); lua_setfield(L, -2, "radius"); } lua_createtable(L, g.iStops.size(), 0); for (int i = 0; i < int(g.iStops.size()); ++i) { lua_createtable(L, 0, 2); lua_pushnumber(L, g.iStops[i].offset); lua_setfield(L, -2, "offset"); push_color(L, g.iStops[i].color); lua_setfield(L, -2, "color"); lua_rawseti(L, -2, i+1); } lua_setfield(L, -2, "stops"); return 1; } // find will also work for the values that are "set" static int cascade_find(lua_State *L) { Cascade *s = check_cascade(L, 1)->cascade; luaL_checktype(L, 2, LUA_TSTRING); int what = test_option(L, 2, set_names); switch (what) { case 0: // preamble push_string(L, s->findPreamble()); break; case 1: // linecap push_attribute(L, Attribute(s->lineCap())); break; case 2: // linejoin push_attribute(L, Attribute(s->lineJoin())); break; case 3: // fillrule push_attribute(L, Attribute(s->fillRule())); break; case 4: { // symbol const char *name = luaL_checklstring(L, 3, nullptr); const Symbol *symbol = s->findSymbol(Attribute(true, name)); if (symbol) push_object(L, symbol->iObject->clone()); else lua_pushnil(L); break; } case 5: // layout push_layout(L, *s->findLayout()); break; case 6: { // gradient const char *name = luaL_checklstring(L, 3, nullptr); push_gradient(L, *s->findGradient(Attribute(true, name))); break; } default: { Kind kind = Kind(luaL_checkoption(L, 2, nullptr, kind_names)); const char *name = luaL_checklstring(L, 3, nullptr); push_attribute(L, s->find(kind, Attribute(true, String(name)))); break; } } return 1; } static int cascade_has(lua_State *L) { Cascade *p = check_cascade(L, 1)->cascade; Kind kind = Kind(luaL_checkoption(L, 2, nullptr, kind_names)); const char *name = luaL_checklstring(L, 3, nullptr); Attribute sym(true, String(name)); lua_pushboolean(L, p->has(kind, sym)); return 1; } static int cascade_count(lua_State *L) { Cascade *p = check_cascade(L, 1)->cascade; lua_pushnumber(L, p->count()); return 1; } static int cascade_sheet(lua_State *L) { Cascade *p = check_cascade(L, 1)->cascade; int index = (int)luaL_checkinteger(L, 2); luaL_argcheck(L, 1 <= index && index <= p->count(), 2, "index out of bounds"); push_sheet(L, p->sheet(index - 1), false); return 1; } static int cascade_insert(lua_State *L) { Cascade *p = check_cascade(L, 1)->cascade; int index = (int)luaL_checkinteger(L, 2); luaL_argcheck(L, 1 <= index && index <= p->count() + 1, 2, "index out of bounds"); SSheet *s = check_sheet(L, 3); StyleSheet *sheet = s->sheet; if (!s->owned) sheet = new StyleSheet(*s->sheet); p->insert(index - 1, sheet); s->owned = false; // now owned by cascade return 0; } static int cascade_remove(lua_State *L) { Cascade *p = check_cascade(L, 1)->cascade; int index = (int)luaL_checkinteger(L, 2); luaL_argcheck(L, 1 <= index && index <= p->count(), 2, "index out of bounds"); p->remove(index - 1); return 0; } // -------------------------------------------------------------------- static const struct luaL_Reg cascade_methods[] = { { "__gc", cascade_destructor }, { "__tostring", cascade_tostring }, { "clone", cascade_clone }, { "allNames", cascade_allNames }, { "find", cascade_find }, { "has", cascade_has }, { "count", cascade_count }, { "sheet", cascade_sheet }, { "insert", cascade_insert }, { "remove", cascade_remove }, { nullptr, nullptr } }; // -------------------------------------------------------------------- int ipelua::open_ipestyle(lua_State *L) { make_metatable(L, "Ipe.sheet", sheet_methods); make_metatable(L, "Ipe.cascade", cascade_methods); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelua/ipeluaipelet.cpp0000644000175000017500000002106213561570220017471 0ustar otfriedotfried// -------------------------------------------------------------------- // ipeluaipelets.cpp // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipelua.h" #ifdef WIN32 #include #else #include #include #endif using namespace ipe; using namespace ipelua; typedef Ipelet *(*PNewIpeletFn)(); // -------------------------------------------------------------------- static void snapFlag(lua_State *L, int &flags, const char *mode, uint32_t bits) { lua_getfield(L, -1, mode); if (!lua_isnil(L, -1)) flags = lua_toboolean(L, -1) ? (flags | bits) : (flags & ~bits); lua_pop(L, 1); } void ipelua::get_snap(lua_State *L, int i, ipe::Snap &snap) { luaL_checktype(L, i, LUA_TTABLE); snapFlag(L, snap.iSnap, "snapvtx", Snap::ESnapVtx); snapFlag(L, snap.iSnap, "snapctl", Snap::ESnapCtl); snapFlag(L, snap.iSnap, "snapbd", Snap::ESnapBd); snapFlag(L, snap.iSnap, "snapint", Snap::ESnapInt); snapFlag(L, snap.iSnap, "snapgrid", Snap::ESnapGrid); snapFlag(L, snap.iSnap, "snapangle", Snap::ESnapAngle); snapFlag(L, snap.iSnap, "snapauto", Snap::ESnapAuto); lua_getfield(L, i, "grid_visible"); if (!lua_isnil(L, -1)) snap.iGridVisible = lua_toboolean(L, -1); lua_pop(L, 1); lua_getfield(L, i, "gridsize"); if (!lua_isnil(L, -1)) snap.iGridSize = (int) luaL_checkinteger(L, -1); lua_pop(L, 1); lua_getfield(L, i, "anglesize"); if (!lua_isnil(L, -1)) snap.iAngleSize = IpePi * luaL_checknumber(L, -1) / 180.0; lua_pop(L, 1); lua_getfield(L, i, "snap_distance"); if (!lua_isnil(L, -1)) snap.iSnapDistance = (int) luaL_checkinteger(L, -1); lua_pop(L, 1); lua_getfield(L, i, "with_axes"); if (!lua_isnil(L, -1)) snap.iWithAxes = lua_toboolean(L, -1); lua_pop(L, 1); lua_getfield(L, i, "origin"); if (is_type(L, -1, "Ipe.vector")) snap.iOrigin = *check_vector(L, -1); lua_pop(L, 1); lua_getfield(L, i, "orientation"); if (!lua_isnil(L, -1)) snap.iDir = luaL_checknumber(L, -1); lua_pop(L, 1); } // -------------------------------------------------------------------- static int ipelet_destructor(lua_State *L) { ipeDebug("Ipelet destructor"); Ipelet **p = check_ipelet(L, 1); delete *p; *p = nullptr; return 0; } static int ipelet_tostring(lua_State *L) { check_ipelet(L, 1); lua_pushfstring(L, "Ipelet@%p", lua_topointer(L, 1)); return 1; } // -------------------------------------------------------------------- int ipelua::ipelet_constructor(lua_State *L) { String fname(luaL_checklstring(L, 1, nullptr)); #if defined(WIN32) String dllname = fname + ".dll"; #else String dllname = fname + ".so"; #endif ipeDebug("Loading dll '%s'", dllname.z()); PNewIpeletFn pIpelet = nullptr; #ifdef WIN32 HMODULE hMod = LoadLibraryW(dllname.w().data()); if (hMod) { pIpelet = (PNewIpeletFn) GetProcAddress(hMod, "newIpelet"); if (!pIpelet) pIpelet = (PNewIpeletFn) GetProcAddress(hMod, "_newIpelet"); } #else void *handle = dlopen(dllname.z(), RTLD_NOW); if (handle) { pIpelet = (PNewIpeletFn) dlsym(handle, "newIpelet"); if (!pIpelet) pIpelet = (PNewIpeletFn) dlsym(handle, "_newIpelet"); } #endif if (pIpelet) { Ipelet **p = (Ipelet **) lua_newuserdata(L, sizeof(Ipelet *)); *p = nullptr; luaL_getmetatable(L, "Ipe.ipelet"); lua_setmetatable(L, -2); Ipelet *ipelet = pIpelet(); if (ipelet == nullptr) { lua_pushnil(L); lua_pushstring(L, "ipelet returns no object"); return 2; } if (ipelet->ipelibVersion() != IPELIB_VERSION) { delete ipelet; lua_pushnil(L); lua_pushstring(L, "ipelet linked against older version of Ipelib"); return 2; } *p = ipelet; ipeDebug("Ipelet '%s' loaded", fname.z()); return 1; } else { lua_pushnil(L); #ifdef WIN32 if (hMod) lua_pushfstring(L, "Error %d finding DLL entry point", GetLastError()); else lua_pushfstring(L, "Error %d loading Ipelet DLL '%s'", GetLastError(), dllname.z()); #else lua_pushfstring(L, "Error loading Ipelet '%s': %s", dllname.z(), dlerror()); #if defined(__APPLE__) ipeDebug("DYLD_LIBRARY_PATH=%s", getenv("DYLD_LIBRARY_PATH")); ipeDebug("DYLD_FALLBACK_LIBRARY_PATH=%s", getenv("DYLD_FALLBACK_LIBRARY_PATH")); #endif #endif return 2; } } // -------------------------------------------------------------------- class Helper : public IpeletHelper { public: Helper(lua_State *L0, int luahelper); ~Helper(); virtual void message(const char *msg); virtual int messageBox(const char *text, const char *details, int buttons); virtual bool getString(const char *prompt, String &str); virtual String getParameter(const char *key); private: lua_State *L; int iHelper; }; Helper::Helper(lua_State *L0, int luahelper) { L = L0; iHelper = luahelper; } Helper::~Helper() { luaL_unref(L, LUA_REGISTRYINDEX, iHelper); } void Helper::message(const char *msg) { lua_rawgeti(L, LUA_REGISTRYINDEX, iHelper); lua_getfield(L, -1, "message"); lua_pushvalue(L, -2); // luahelper lua_remove(L, -3); lua_pushstring(L, msg); luacall(L, 2, 0); } int Helper::messageBox(const char *text, const char *details, int buttons) { lua_rawgeti(L, LUA_REGISTRYINDEX, iHelper); lua_getfield(L, -1, "messageBox"); lua_pushvalue(L, -2); // luahelper lua_remove(L, -3); lua_pushstring(L, text); if (details) lua_pushstring(L, details); else lua_pushnil(L); lua_pushnumber(L, buttons); luacall(L, 4, 1); if (lua_isnumber(L, -1)) return int(lua_tonumberx(L, -1, nullptr)); else return 0; } bool Helper::getString(const char *prompt, String &str) { lua_rawgeti(L, LUA_REGISTRYINDEX, iHelper); lua_getfield(L, -1, "getString"); lua_pushvalue(L, -2); // luahelper lua_remove(L, -3); lua_pushstring(L, prompt); push_string(L, str); luacall(L, 3, 1); if (lua_isstring(L, -1)) { str = lua_tolstring(L, -1, nullptr); return true; } else return false; } String Helper::getParameter(const char *key) { lua_rawgeti(L, LUA_REGISTRYINDEX, iHelper); lua_getfield(L, -1, "parameters"); String value; if (lua_istable(L, -1)) { lua_getfield(L, -1, key); const char *t = lua_tolstring(L, -1, nullptr); if (t) value = t; lua_pop(L, 1); // parameters[key] } lua_pop(L, 2); // helper, parameters return value; } // -------------------------------------------------------------------- static int ipelet_run(lua_State *L) { Ipelet **p = check_ipelet(L, 1); int num = (int)luaL_checkinteger(L, 2) - 1; // Lua counts starting from one IpeletData data; data.iPage = check_page(L, 3)->page; data.iDoc = *check_document(L, 4); data.iPageNo = (int)luaL_checkinteger(L, 5); data.iView = (int)luaL_checkinteger(L, 6); data.iLayer = check_layer(L, 7, data.iPage); check_allattributes(L, 8, data.iAttributes); get_snap(L, 9, data.iSnap); lua_pushvalue(L, 10); int luahelper = luaL_ref(L, LUA_REGISTRYINDEX); Helper helper(L, luahelper); bool result = (*p)->run(num, &data, &helper); lua_pushboolean(L, result); return 1; } // -------------------------------------------------------------------- static const struct luaL_Reg ipelet_methods[] = { { "__tostring", ipelet_tostring }, { "__gc", ipelet_destructor }, { "run", ipelet_run }, { nullptr, nullptr } }; // -------------------------------------------------------------------- int ipelua::open_ipelets(lua_State *L) { make_metatable(L, "Ipe.ipelet", ipelet_methods); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelua/ipeluapage.cpp0000644000175000017500000004226313561570220017131 0ustar otfriedotfried// -------------------------------------------------------------------- // ipeluapage.cpp // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipelua.h" #include "ipepage.h" #include "ipeiml.h" using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- void ipelua::push_page(lua_State *L, Page *page, bool owned) { SPage *p = (SPage *) lua_newuserdata(L, sizeof(SPage)); p->owned = owned; luaL_getmetatable(L, "Ipe.page"); lua_setmetatable(L, -2); p->page = page; } static int check_objno(lua_State *L, int i, Page *p, int extra = 0) { int n = (int)luaL_checkinteger(L, i); luaL_argcheck(L, 1 <= n && n <= p->count() + extra, i, "invalid object index"); return n - 1; } int ipelua::check_layer(lua_State *L, int i, Page *p) { const char *name = luaL_checklstring(L, i, nullptr); int l = p->findLayer(name); luaL_argcheck(L, l >= 0, i, "layer does not exist"); return l; } int ipelua::check_viewno(lua_State *L, int i, Page *p, int extra) { int n = (int)luaL_checkinteger(L, i); luaL_argcheck(L, 1 <= n && n <= p->countViews() + extra, i, "invalid view index"); return n - 1; } int ipelua::page_constructor(lua_State *L) { if (lua_isnoneornil(L, 1)) { push_page(L, Page::basic()); return 1; } else { size_t len; const char *p = luaL_checklstring(L, 1, &len); Buffer data(p, len); BufferSource source(data); ImlParser parser(source); Page *page = parser.parsePageSelection(); if (page) { push_page(L, page); return 1; } else return 0; } } static int page_destructor(lua_State *L) { SPage *p = check_page(L, 1); if (p->owned) delete p->page; p->page = nullptr; return 0; } static int page_index(lua_State *L) { Page *p = check_page(L, 1)->page; if (lua_type(L, 2) == LUA_TNUMBER) { int n = check_objno(L, 2, p); push_object(L, p->object(n), false); } else { const char *key = luaL_checklstring(L, 2, nullptr); if (!luaL_getmetafield(L, 1, key)) lua_pushnil(L); } return 1; } static int page_tostring(lua_State *L) { check_page(L, 1); lua_pushfstring(L, "Page@%p", lua_topointer(L, 1)); return 1; } static int page_len(lua_State *L) { Page *p = check_page(L, 1)->page; lua_pushinteger(L, p->count()); return 1; } static int page_clone(lua_State *L) { Page *p = check_page(L, 1)->page; push_page(L, new Page(*p)); return 1; } // -------------------------------------------------------------------- static void push_select(lua_State *L, TSelect sel) { if (sel == ENotSelected) lua_pushnil(L); else if (sel == EPrimarySelected) lua_pushnumber(L, 1); else lua_pushnumber(L, 2); } static TSelect check_select(lua_State *L, int index) { TSelect w = ENotSelected; if (!lua_isnoneornil(L, index)) { if ((int)luaL_checkinteger(L, index) == 1) w = EPrimarySelected; else w = ESecondarySelected; } return w; } // arguments: page, counter static int page_object_iterator(lua_State *L) { Page *p = check_page(L, 1)->page; int i = (int)luaL_checkinteger(L, 2); i = i + 1; if (i <= p->count()) { lua_pushinteger(L, i); // new counter push_object(L, p->object(i-1), false); // object push_select(L, p->select(i-1)); push_string(L, p->layer(p->layerOf(i-1))); // layer return 4; } else return 0; } // returns object iterator for use in for loop // returns iterator function, invariant state, control variable static int page_objects(lua_State *L) { (void) check_page(L, 1); lua_pushcfunction(L, page_object_iterator); // iterator function lua_pushvalue(L, 1); // page lua_pushinteger(L, 0); // counter return 3; } // -------------------------------------------------------------------- static int page_xml(lua_State *L) { static const char * const option_names[] = { "ipepage", "ipeselection", nullptr }; Page *p = check_page(L, 1)->page; int t = luaL_checkoption(L, 2, nullptr, option_names); String data; StringStream stream(data); if (t == 0) p->saveAsIpePage(stream); else if (t == 1) p->saveSelection(stream); push_string(L, data); return 1; } static int page_layers(lua_State *L) { Page *p = check_page(L, 1)->page; lua_createtable(L, 0, p->countLayers()); for (int i = 0; i < p->countLayers(); ++i) { push_string(L, p->layer(i)); lua_rawseti(L, -2, i + 1); } return 1; } static int page_countLayers(lua_State *L) { Page *p = check_page(L, 1)->page; lua_pushinteger(L, p->countLayers()); return 1; } static int page_isLocked(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_layer(L, 2, p); lua_pushboolean(L, p->isLocked(n)); return 1; } static int page_hasSnapping(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_layer(L, 2, p); lua_pushboolean(L, p->hasSnapping(n)); return 1; } static int page_setLocked(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_layer(L, 2, p); p->setLocked(n, lua_toboolean(L, 3)); return 0; } static int page_setSnapping(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_layer(L, 2, p); p->setSnapping(n, lua_toboolean(L, 3)); return 0; } static int page_renameLayer(lua_State *L) { Page *p = check_page(L, 1)->page; const char *s1 = luaL_checklstring(L, 2, nullptr); const char *s2 = luaL_checklstring(L, 3, nullptr); p->renameLayer(s1, s2); return 0; } static int page_addLayer(lua_State *L) { Page *p = check_page(L, 1)->page; if (lua_isnoneornil(L, 2)) { p->addLayer(); } else { const char *s = luaL_checklstring(L, 2, nullptr); p->addLayer(s); } push_string(L, p->layer(p->countLayers() - 1)); return 1; } static int page_removeLayer(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_layer(L, 2, p); p->removeLayer(p->layer(n)); return 0; } static int page_moveLayer(lua_State *L) { Page *p = check_page(L, 1)->page; int index = check_layer(L, 2, p); int newIndex = (int)luaL_checkinteger(L, 3) - 1; luaL_argcheck(L, 0 <= newIndex && newIndex < p->countLayers(), 3, "invalid target index"); p->moveLayer(index, newIndex); return 0; } // -------------------------------------------------------------------- static int page_select(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); push_select(L, p->select(n)); return 1; } static int page_setSelect(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); TSelect w = check_select(L, 3); p->setSelect(n, w); return 0; } static int page_layerOf(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); push_string(L, p->layer(p->layerOf(n))); return 1; } static int page_setLayerOf(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); const char *s = luaL_checklstring(L, 3, nullptr); int l = p->findLayer(s); luaL_argcheck(L, l >= 0, 3, "layer does not exist"); p->setLayerOf(n, l); return 0; } static int page_bbox(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); push_rect(L, p->bbox(n)); return 1; } // use index nil to append static int page_insert(lua_State *L) { Page *p = check_page(L, 1)->page; int n; if (lua_isnil(L, 2)) n = p->count(); else n = check_objno(L, 2, p, 1); SObject *obj = check_object(L, 3); TSelect select = check_select(L, 4); int l = check_layer(L, 5, p); p->insert(n, select, l, obj->obj->clone()); return 0; } static int page_remove(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); p->remove(n); return 0; } static int page_replace(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); SObject *obj = check_object(L, 3); p->replace(n, obj->obj->clone()); return 0; } static int page_invalidateBBox(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); p->invalidateBBox(n); return 0; } static int page_transform(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); Matrix *m = check_matrix(L, 3); p->transform(n, *m); return 0; } static int page_distance(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); Vector *v = check_vector(L, 3); double bound = luaL_checknumber(L, 4); lua_pushnumber(L, p->distance(n, *v, bound)); return 1; } static int page_setAttribute(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_objno(L, 2, p); Property prop = Property(luaL_checkoption(L, 3, nullptr, property_names)); Attribute value = check_property(prop, L, 4); lua_pushboolean(L, p->setAttribute(n, prop, value)); return 1; } static int page_primarySelection(lua_State *L) { Page *p = check_page(L, 1)->page; int prim = p->primarySelection(); if (prim >= 0) { lua_pushnumber(L, prim + 1); return 1; } else return 0; } static int page_hasSelection(lua_State *L) { Page *p = check_page(L, 1)->page; lua_pushboolean(L, p->hasSelection()); return 1; } static int page_deselectAll(lua_State *L) { Page *p = check_page(L, 1)->page; p->deselectAll(); return 0; } static int page_ensurePrimarySelection(lua_State *L) { Page *p = check_page(L, 1)->page; p->ensurePrimarySelection(); return 0; } static int page_titles(lua_State *L) { Page *p = check_page(L, 1)->page; lua_createtable(L, 3, 0); push_string(L, p->title()); lua_setfield(L, -2, "title"); if (!p->sectionUsesTitle(0)) { push_string(L, p->section(0)); lua_setfield(L, -2, "section"); } if (!p->sectionUsesTitle(1)) { push_string(L, p->section(1)); lua_setfield(L, -2, "subsection"); } return 1; } static int page_setTitles(lua_State *L) { Page *p = check_page(L, 1)->page; luaL_checktype(L, 2, LUA_TTABLE); lua_getfield(L, 2, "title"); if (lua_isstring(L, -1)) p->setTitle(lua_tolstring(L, -1, nullptr)); lua_getfield(L, 2, "section"); if (lua_isstring(L, -1)) p->setSection(0, false, lua_tolstring(L, -1, nullptr)); else p->setSection(0, true, ""); lua_getfield(L, 2, "subsection"); if (lua_isstring(L, -1)) p->setSection(1, false, lua_tolstring(L, -1, nullptr)); else p->setSection(1, true, ""); lua_pop(L, 3); // title, section, subsection return 0; } static int page_notes(lua_State *L) { Page *p = check_page(L, 1)->page; push_string(L, p->notes()); return 1; } static int page_setNotes(lua_State *L) { Page *p = check_page(L, 1)->page; String n = luaL_checklstring(L, 2, nullptr); p->setNotes(n); return 0; } static int page_marked(lua_State *L) { Page *p = check_page(L, 1)->page; lua_pushboolean(L, p->marked()); return 1; } static int page_setMarked(lua_State *L) { Page *p = check_page(L, 1)->page; p->setMarked(lua_toboolean(L, 2)); return 0; } // -------------------------------------------------------------------- static int page_countViews(lua_State *L) { Page *p = check_page(L, 1)->page; lua_pushinteger(L, p->countViews()); return 1; } static int page_effect(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p); push_string(L, p->effect(n).string()); return 1; } static int page_setEffect(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p); const char *eff = luaL_checklstring(L, 3, nullptr); p->setEffect(n, Attribute(true, eff)); return 0; } static int page_active(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p); push_string(L, p->active(n)); return 1; } static int page_setActive(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p); const char *name = luaL_checklstring(L, 3, nullptr); p->setActive(n, name); return 0; } static int page_insertView(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p, 1); const char *name = luaL_checklstring(L, 3, nullptr); p->insertView(n, name); return 0; } static int page_removeView(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p); p->removeView(n); return 0; } static int page_clearViews(lua_State *L) { Page *p = check_page(L, 1)->page; p->clearViews(); return 0; } static int page_markedView(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p); lua_pushboolean(L, p->markedView(n)); return 1; } static int page_setMarkedView(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p); p->setMarkedView(n, lua_toboolean(L, 3)); return 0; } static int page_viewName(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p); push_string(L, p->viewName(n)); return 1; } static int page_setViewName(lua_State *L) { Page *p = check_page(L, 1)->page; int n = check_viewno(L, 2, p); const char *s = luaL_checklstring(L, 3, nullptr); p->setViewName(n, s); return 0; } // Either: view & layername // Or: view & object index static int page_visible(lua_State *L) { Page *p = check_page(L, 1)->page; int vno = check_viewno(L, 2, p); if (lua_type(L, 3) == LUA_TNUMBER) { int objno = check_objno(L, 3, p); lua_pushboolean(L, p->objectVisible(vno, objno)); } else { int l = check_layer(L, 3, p); lua_pushboolean(L, p->visible(vno, l)); } return 1; } static int page_setVisible(lua_State *L) { Page *p = check_page(L, 1)->page; int vno = check_viewno(L, 2, p); int l = check_layer(L, 3, p); bool vis = lua_toboolean(L, 4); p->setVisible(vno, p->layer(l), vis); return 0; } // -------------------------------------------------------------------- static int page_findedge(lua_State *L) { Page *p = check_page(L, 1)->page; int view = check_viewno(L, 2, p, 0); Vector pos = *check_vector(L, 3); Snap snap; if (!snap.setEdge(pos, p, view)) return 0; push_vector(L, snap.iOrigin); lua_pushnumber(L, snap.iDir); return 2; } // -------------------------------------------------------------------- static const struct luaL_Reg page_methods[] = { { "__index", page_index }, { "__tostring", page_tostring }, { "__gc", page_destructor }, { "__len", page_len }, { "clone", page_clone }, { "objects", page_objects }, { "countViews", page_countViews }, { "countLayers", page_countLayers }, { "xml", page_xml }, { "layers", page_layers }, { "isLocked", page_isLocked }, { "hasSnapping", page_hasSnapping }, { "setLocked", page_setLocked }, { "setSnapping", page_setSnapping }, { "renameLayer", page_renameLayer }, { "addLayer", page_addLayer }, { "removeLayer", page_removeLayer }, { "moveLayer", page_moveLayer }, { "select", page_select }, { "setSelect", page_setSelect }, { "layerOf", page_layerOf }, { "setLayerOf", page_setLayerOf }, { "effect", page_effect }, { "setEffect", page_setEffect }, { "active", page_active }, { "setActive", page_setActive }, { "insertView", page_insertView }, { "removeView", page_removeView }, { "clearViews", page_clearViews }, { "markedView", page_markedView }, { "setMarkedView", page_setMarkedView }, { "viewName", page_viewName }, { "setViewName", page_setViewName }, { "visible", page_visible }, { "setVisible", page_setVisible }, { "bbox", page_bbox }, { "insert", page_insert }, { "remove", page_remove }, { "replace", page_replace }, { "invalidateBBox", page_invalidateBBox }, { "transform", page_transform }, { "distance", page_distance }, { "setAttribute", page_setAttribute }, { "primarySelection", page_primarySelection }, { "hasSelection", page_hasSelection }, { "deselectAll", page_deselectAll }, { "ensurePrimarySelection", page_ensurePrimarySelection }, { "findEdge", page_findedge }, { "titles", page_titles }, { "setTitles", page_setTitles }, { "notes", page_notes }, { "setNotes", page_setNotes }, { "marked", page_marked }, { "setMarked", page_setMarked }, { nullptr, nullptr } }; // -------------------------------------------------------------------- int ipelua::open_ipepage(lua_State *L) { luaL_newmetatable(L, "Ipe.page"); luaL_setfuncs(L, page_methods, 0); lua_pop(L, 1); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelua/Makefile0000644000175000017500000000207313561570220015744 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for Lua bindings for ipe # -------------------------------------------------------------------- OBJDIR = $(BUILDDIR)/obj/ipelua include ../common.mak TARGET = $(call dll_target,ipelua) MAKE_SYMLINKS = $(call dll_symlinks,ipelua) SONAME = $(call soname,ipelua) INSTALL_SYMLINKS = $(call install_symlinks,ipelua) CPPFLAGS += -I../include $(LUA_CFLAGS) LIBS += -L$(buildlib) -lipe $(LUA_LIBS) $(DL_LIBS) CXXFLAGS += $(DLL_CFLAGS) all: $(TARGET) sources = \ ipelib.cpp \ ipeluageo.cpp \ ipeluaobj.cpp \ ipeluastyle.cpp \ ipeluapage.cpp \ ipeluaipelet.cpp $(TARGET): $(objects) $(MAKE_LIBDIR) $(CXX) $(LDFLAGS) $(DLL_LDFLAGS) $(SONAME) -o $@ $^ $(LIBS) $(MAKE_SYMLINKS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_SYMLINKS) # -------------------------------------------------------------------- ipe-7.2.13/src/ipelua/ipeluageo.cpp0000644000175000017500000005322613561570220016770 0ustar otfriedotfried// -------------------------------------------------------------------- // ipeluageo.cpp // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipelua.h" #include using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- void ipelua::push_vector(lua_State *L, const Vector &v0) { Vector *v = (Vector *) lua_newuserdata(L, sizeof(Vector)); luaL_getmetatable(L, "Ipe.vector"); lua_setmetatable(L, -2); new (v) Vector(v0); } int ipelua::vector_constructor(lua_State *L) { if (lua_gettop(L) == 0) push_vector(L, Vector::ZERO); else push_vector(L, Vector(luaL_checknumber(L, 1), luaL_checknumber(L, 2))); return 1; } int ipelua::direction_constructor(lua_State *L) { Angle alpha(luaL_checknumber(L, 1)); push_vector(L, Vector(alpha)); return 1; } static int vector_get(lua_State *L) { Vector *v = check_vector(L, 1); const char *key = lua_tolstring(L, 2, nullptr); if (!strcmp(key, "x")) lua_pushnumber(L, v->x); else if (!strcmp(key, "y")) lua_pushnumber(L, v->y); else if (!luaL_getmetafield(L, 1, key)) lua_pushnil(L); return 1; } static int vector_tostring(lua_State *L) { Vector *v = check_vector(L, 1); lua_pushfstring(L, "(%f, %f)", v->x, v->y); return 1; } static int vector_add(lua_State *L) { Vector *v1 = check_vector(L, 1); Vector *v2 = check_vector(L, 2); push_vector(L, *v1 + *v2); return 1; } static int vector_unm(lua_State *L) { Vector *v = check_vector(L, 1); push_vector(L, Vector(-v->x, -v->y)); return 1; } static int vector_sub(lua_State *L) { Vector *v1 = check_vector(L, 1); Vector *v2 = check_vector(L, 2); push_vector(L, *v1 - *v2); return 1; } static int vector_eq(lua_State *L) { Vector *v1 = check_vector(L, 1); Vector *v2 = check_vector(L, 2); lua_pushboolean(L, *v1 == *v2); return 1; } static int vector_dot(lua_State *L) { Vector *v1 = check_vector(L, 1); Vector *v2 = check_vector(L, 2); lua_pushnumber(L, dot(*v1, *v2)); return 1; } static int vector_mul(lua_State *L) { if (lua_type(L, 1) == LUA_TNUMBER) { double scalar = luaL_checknumber(L, 1); Vector *v = check_vector(L, 2); push_vector(L, scalar * *v); } else { Vector *v = check_vector(L, 1); double scalar = luaL_checknumber(L, 2); push_vector(L, *v * scalar); } return 1; } static int vector_len(lua_State *L) { Vector *v = check_vector(L, 1); lua_pushnumber(L, v->len()); return 1; } static int vector_sqLen(lua_State *L) { Vector *v = check_vector(L, 1); lua_pushnumber(L, v->sqLen()); return 1; } static int vector_normalized(lua_State *L) { Vector *v = check_vector(L, 1); push_vector(L, v->normalized()); return 1; } static int vector_orthogonal(lua_State *L) { Vector *v = check_vector(L, 1); push_vector(L, v->orthogonal()); return 1; } static int vector_factorize(lua_State *L) { Vector *v = check_vector(L, 1); Vector *unit = check_vector(L, 2); lua_pushnumber(L, v->factorize(*unit)); return 1; } static int vector_angle(lua_State *L) { Vector *v = check_vector(L, 1); lua_pushnumber(L, double(v->angle())); return 1; } static const struct luaL_Reg vector_methods[] = { { "__index", vector_get }, { "__tostring", vector_tostring }, { "__add", vector_add }, { "__unm", vector_unm }, { "__sub", vector_sub }, { "__eq", vector_eq }, { "__mul", vector_mul }, { "__concat", vector_dot }, // for historical reasons { "__pow", vector_dot }, { "len", vector_len }, { "sqLen", vector_sqLen }, { "normalized", vector_normalized }, { "orthogonal", vector_orthogonal }, { "factorize", vector_factorize }, { "angle", vector_angle }, { nullptr, nullptr }, }; // -------------------------------------------------------------------- void ipelua::push_matrix(lua_State *L, const Matrix &m0) { Matrix *m = (Matrix *) lua_newuserdata(L, sizeof(Matrix)); luaL_getmetatable(L, "Ipe.matrix"); lua_setmetatable(L, -2); new (m) Matrix(m0); } int ipelua::matrix_constructor(lua_State *L) { int top = lua_gettop(L); if (top == 0) push_matrix(L, Matrix()); else if (top == 4 || top == 6) { double a[6]; a[4] = a[5] = 0.0; for (int i = 0; i < top; ++i) a[i] = luaL_checknumber(L, i+1); push_matrix(L, Matrix(a[0], a[1], a[2], a[3], a[4], a[5])); } else if (top == 1 && lua_type(L, 1) == LUA_TTABLE) { double a[6]; for (int i = 0; i < 6; ++i) { lua_rawgeti(L, 1, i+1); a[i] = luaL_checknumber(L, -1); lua_pop(L, 1); } push_matrix(L, Matrix(a[0], a[1], a[2], a[3], a[4], a[5])); } else luaL_error(L, "incorrect arguments for constructor"); return 1; } int ipelua::rotation_constructor(lua_State *L) { double alpha = luaL_checknumber(L, 1); push_matrix(L, Matrix(Linear(Angle(alpha)))); return 1; } int ipelua::translation_constructor(lua_State *L) { if (lua_gettop(L) == 1) { Vector *v = check_vector(L, 1); push_matrix(L, Matrix(*v)); } else { double x = luaL_checknumber(L, 1); double y = luaL_checknumber(L, 2); push_matrix(L, Matrix(Vector(x, y))); } return 1; } static int matrix_tostring(lua_State *L) { Matrix *m = check_matrix(L, 1); lua_pushfstring(L, "[%f %f %f %f %f %f]", m->a[0], m->a[1], m->a[2], m->a[3], m->a[4], m->a[5]); return 1; } static int matrix_eq(lua_State *L) { Matrix *m1 = check_matrix(L, 1); Matrix *m2 = check_matrix(L, 2); lua_pushboolean(L, *m1 == *m2); return 1; } static int matrix_coeff(lua_State *L) { Matrix *m = check_matrix(L, 1); lua_newtable(L); for (int i = 0; i < 6; ++i) { lua_pushnumber(L, m->a[i]); lua_rawseti(L, -2, i+1); } return 1; } static int matrix_isIdentity(lua_State *L) { Matrix *m = check_matrix(L, 1); lua_pushboolean(L, m->isIdentity()); return 1; } static int matrix_isSingular(lua_State *L) { Matrix *m = check_matrix(L, 1); double t = m->a[0]*m->a[3]-m->a[1]*m->a[2]; lua_pushboolean(L, t == 0); return 1; } static int matrix_inverse(lua_State *L) { Matrix *m = check_matrix(L, 1); double t = m->a[0]*m->a[3]-m->a[1]*m->a[2]; luaL_argcheck(L, t != 0, 1, "matrix is singular"); push_matrix(L, m->inverse()); return 1; } static int matrix_translation(lua_State *L) { Matrix *m = check_matrix(L, 1); push_vector(L, m->translation()); return 1; } static int matrix_linear(lua_State *L) { Matrix *m = check_matrix(L, 1); push_matrix(L, Matrix(m->linear())); return 1; } static int matrix_elements(lua_State *L) { Matrix *m = check_matrix(L, 1); lua_createtable(L, 6, 0); for (int i = 0; i < 6; ++i) { lua_pushnumber(L, m->a[i]); lua_rawseti(L, -2, i+1); } return 1; } static int matrix_mul(lua_State *L) { Matrix *lhs = check_matrix(L, 1); if (is_type(L, 2, "Ipe.matrix")) { Matrix *rhs = check_matrix(L, 2); push_matrix(L, *lhs * *rhs); } else if (is_type(L, 2, "Ipe.arc")) { Arc *rhs = check_arc(L, 2); push_arc(L, *lhs * *rhs); } else { Vector *v = check_vector(L, 2); push_vector(L, *lhs * *v); } return 1; } static const struct luaL_Reg matrix_methods[] = { { "__tostring", matrix_tostring }, { "__eq", matrix_eq }, { "coeff", matrix_coeff }, { "isIdentity", matrix_isIdentity }, { "linear", matrix_linear }, { "translation", matrix_translation }, { "__mul", matrix_mul }, { "isSingular", matrix_isSingular }, { "inverse", matrix_inverse }, { "elements", matrix_elements }, { nullptr, nullptr } }; // -------------------------------------------------------------------- void ipelua::push_rect(lua_State *L, const Rect &r0) { Rect *r = (Rect *) lua_newuserdata(L, sizeof(Rect)); luaL_getmetatable(L, "Ipe.rect"); lua_setmetatable(L, -2); new (r) Rect(r0); } int ipelua::rect_constructor(lua_State *L) { push_rect(L, Rect()); return 1; } static int rect_tostring(lua_State *L) { Rect *r = check_rect(L, 1); lua_pushfstring(L, "Rect(%f,%f,%f,%f)", r->bottomLeft().x, r->bottomLeft().y, r->topRight().x, r->topRight().y); return 1; } static int rect_isEmpty(lua_State *L) { Rect *r = check_rect(L, 1); lua_pushboolean(L, r->isEmpty()); return 1; } static int rect_topRight(lua_State *L) { Rect *r = check_rect(L, 1); push_vector(L, r->topRight()); return 1; } static int rect_bottomLeft(lua_State *L) { Rect *r = check_rect(L, 1); push_vector(L, r->bottomLeft()); return 1; } static int rect_topLeft(lua_State *L) { Rect *r = check_rect(L, 1); push_vector(L, r->topLeft()); return 1; } static int rect_bottomRight(lua_State *L) { Rect *r = check_rect(L, 1); push_vector(L, r->bottomLeft()); return 1; } static int rect_left(lua_State *L) { Rect *r = check_rect(L, 1); lua_pushnumber(L, r->left()); return 1; } static int rect_right(lua_State *L) { Rect *r = check_rect(L, 1); lua_pushnumber(L, r->right()); return 1; } static int rect_bottom(lua_State *L) { Rect *r = check_rect(L, 1); lua_pushnumber(L, r->bottom()); return 1; } static int rect_top(lua_State *L) { Rect *r = check_rect(L, 1); lua_pushnumber(L, r->top()); return 1; } static int rect_width(lua_State *L) { Rect *r = check_rect(L, 1); lua_pushnumber(L, r->width()); return 1; } static int rect_height(lua_State *L) { Rect *r = check_rect(L, 1); lua_pushnumber(L, r->height()); return 1; } static int rect_add(lua_State *L) { Rect *r = check_rect(L, 1); if (is_type(L, 2, "Ipe.vector")) r->addPoint(*check_vector(L, 2)); else r->addRect(*check_rect(L, 2)); return 0; } static int rect_clipTo(lua_State *L) { Rect *r1 = check_rect(L, 1); Rect *r2 = check_rect(L, 2); r1->clipTo(*r2); return 0; } static int rect_contains(lua_State *L) { Rect *r = check_rect(L, 1); if (is_type(L, 2, "Ipe.vector")) lua_pushboolean(L, r->contains(*check_vector(L, 2))); else lua_pushboolean(L, r->contains(*check_rect(L, 2))); return 1; } static int rect_intersects(lua_State *L) { Rect *r1 = check_rect(L, 1); Rect *r2 = check_rect(L, 2); lua_pushboolean(L, r1->intersects(*r2)); return 1; } static const struct luaL_Reg rect_methods[] = { { "__tostring", rect_tostring }, { "isEmpty", rect_isEmpty }, { "topRight", rect_topRight }, { "bottomLeft", rect_bottomLeft }, { "topLeft", rect_topLeft }, { "bottomRight", rect_bottomRight }, { "left", rect_left }, { "right", rect_right }, { "bottom", rect_bottom }, { "top", rect_top }, { "width", rect_width }, { "height", rect_height }, { "add", rect_add }, { "clipTo", rect_clipTo }, { "contains", rect_contains }, { "intersects", rect_intersects }, { nullptr, nullptr } }; // -------------------------------------------------------------------- void ipelua::push_line(lua_State *L, const Line &l0) { Line *l = (Line *) lua_newuserdata(L, sizeof(Line)); luaL_getmetatable(L, "Ipe.line"); lua_setmetatable(L, -2); new (l) Line(l0); } int ipelua::line_constructor(lua_State *L) { Vector *p = check_vector(L, 1); Vector *dir = check_vector(L, 2); push_line(L, Line(*p, *dir)); return 1; } int ipelua::line_through(lua_State *L) { Vector *p = check_vector(L, 1); Vector *q = check_vector(L, 2); push_line(L, Line::through(*p, *q)); return 1; } int ipelua::line_bisector(lua_State *L) { Vector *p = check_vector(L, 1); Vector *q = check_vector(L, 2); luaL_argcheck(L, *p != *q, 2, "points are not distinct"); Vector mid = 0.5 * (*p + *q); Vector dir = (*p - *q).normalized().orthogonal(); push_line(L, Line(mid, dir)); return 1; } static int line_tostring(lua_State *L) { Line *l = check_line(L, 1); lua_pushfstring(L, "Line[(%f,%f)->(%f,%f)]", l->iP.x, l->iP.y, l->dir().x, l->dir().y); return 1; } static int line_side(lua_State *L) { Line *l = check_line(L, 1); Vector *p = check_vector(L, 2); double s = l->side(*p); if (s > 0.0) lua_pushnumber(L, 1.0); else if (s < 0.0) lua_pushnumber(L, -1.0); else lua_pushnumber(L, 0.0); return 1; } static int line_point(lua_State *L) { Line *l = check_line(L, 1); push_vector(L, l->iP); return 1; } static int line_dir(lua_State *L) { Line *l = check_line(L, 1); push_vector(L, l->dir()); return 1; } static int line_normal(lua_State *L) { Line *l = check_line(L, 1); push_vector(L, l->normal()); return 1; } static int line_distance(lua_State *L) { Line *l = check_line(L, 1); Vector *v = check_vector(L, 2); lua_pushnumber(L, l->distance(*v)); return 1; } static int line_intersects(lua_State *L) { Line *l1 = check_line(L, 1); Line *l2 = check_line(L, 2); Vector pt; if (l1->intersects(*l2, pt)) push_vector(L, pt); else lua_pushnil(L); return 1; } static int line_project(lua_State *L) { Line *l = check_line(L, 1); Vector *v = check_vector(L, 2); push_vector(L, l->project(*v)); return 1; } static const struct luaL_Reg line_methods[] = { { "__tostring", line_tostring }, { "side", line_side }, { "point", line_point }, { "dir", line_dir }, { "normal", line_normal }, { "distance", line_distance }, { "intersects", line_intersects }, { "project", line_project }, { nullptr, nullptr } }; // -------------------------------------------------------------------- void ipelua::push_segment(lua_State *L, const Segment &s0) { Segment *s = (Segment *) lua_newuserdata(L, sizeof(Segment)); luaL_getmetatable(L, "Ipe.segment"); lua_setmetatable(L, -2); new (s) Segment(s0); } int ipelua::segment_constructor(lua_State *L) { Vector *p = check_vector(L, 1); Vector *q = check_vector(L, 2); push_segment(L, Segment(*p, *q)); return 1; } static int segment_tostring(lua_State *L) { Segment *s = check_segment(L, 1); lua_pushfstring(L, "Segment[(%f,%f)-(%f,%f)]", s->iP.x, s->iP.y, s->iQ.x, s->iQ.y); return 1; } static int segment_endpoints(lua_State *L) { Segment *s = check_segment(L, 1); push_vector(L, s->iP); push_vector(L, s->iQ); return 2; } static int segment_line(lua_State *L) { Segment *s = check_segment(L, 1); push_line(L, s->line()); return 1; } static int segment_project(lua_State *L) { Segment *s = check_segment(L, 1); Vector *v = check_vector(L, 2); Vector pt; if (s->project(*v, pt)) push_vector(L, pt); else lua_pushnil(L); return 1; } static int segment_distance(lua_State *L) { Segment *s = check_segment(L, 1); Vector *v = check_vector(L, 2); lua_pushnumber(L, s->distance(*v)); return 1; } static int segment_intersects(lua_State *L) { Segment *s = check_segment(L, 1); Vector pt; if (is_type(L, 2, "Ipe.segment")) { Segment *rhs = check_segment(L, 2); if (s->intersects(*rhs, pt)) push_vector(L, pt); else lua_pushnil(L); } else { Line *rhs = check_line(L, 2); if (s->intersects(*rhs, pt)) push_vector(L, pt); else lua_pushnil(L); } return 1; } static const struct luaL_Reg segment_methods[] = { { "__tostring", segment_tostring }, { "endpoints", segment_endpoints }, { "line", segment_line }, { "project", segment_project }, { "distance", segment_distance }, { "intersects", segment_intersects }, { nullptr, nullptr } }; // -------------------------------------------------------------------- void ipelua::push_bezier(lua_State *L, const Bezier &b0) { Bezier *b = (Bezier *) lua_newuserdata(L, sizeof(Bezier)); luaL_getmetatable(L, "Ipe.bezier"); lua_setmetatable(L, -2); new (b) Bezier(b0); } int ipelua::bezier_constructor(lua_State *L) { Vector *p[4]; for (int i = 0; i < 4; ++i) p[i] = check_vector(L, i + 1); push_bezier(L, Bezier(*p[0], *p[1], *p[2], *p[3])); return 1; } int ipelua::quad_constructor(lua_State *L) { Vector *p[3]; for (int i = 0; i < 3; ++i) p[i] = check_vector(L, i + 1); push_bezier(L, Bezier::quadBezier(*p[0], *p[1], *p[2])); return 1; } static int bezier_tostring(lua_State *L) { check_bezier(L, 1); lua_pushfstring(L, "Bezier@%p", lua_topointer(L, 1)); return 1; } static int bezier_controlpoints(lua_State *L) { Bezier *b = check_bezier(L, 1); for (int i = 0; i < 4; ++i) push_vector(L, b->iV[i]); return 4; } static int bezier_point(lua_State *L) { Bezier *b = check_bezier(L, 1); double t = luaL_checknumber(L, 2); push_vector(L, b->point(t)); return 1; } static int bezier_bbox(lua_State *L) { Bezier *b = check_bezier(L, 1); push_rect(L, b->bbox()); return 1; } static int bezier_intersect(lua_State *L) { Bezier *b = check_bezier(L, 1); std::vector pts; if (is_type(L, 2, "Ipe.segment")) { Segment *rhs = check_segment(L, 2); b->intersect(*rhs, pts); } else if (is_type(L, 2, "Ipe.line")) { Line *rhs = check_line(L, 2); b->intersect(*rhs, pts); } else if (is_type(L, 2, "Ipe.bezier")) { Bezier *rhs = check_bezier(L, 2); b->intersect(*rhs, pts); } lua_createtable(L, pts.size(), 0); for (int i = 0; i < int(pts.size()); ++i) { push_vector(L, pts[i]); lua_rawseti(L, -2, i+1); } return 1; } static int bezier_snap(lua_State *L) { Bezier *b = check_bezier(L, 1); Vector *v = check_vector(L, 2); double t; Vector pos; double bound = 10e9; if (b->snap(*v, t, pos, bound)) { lua_pushnumber(L, t); push_vector(L, pos); return 2; } else return 0; } static const struct luaL_Reg bezier_methods[] = { { "__tostring", bezier_tostring }, { "controlpoints", bezier_controlpoints }, { "point", bezier_point }, { "bbox", bezier_bbox }, { "intersect", bezier_intersect }, { "snap", bezier_snap }, { nullptr, nullptr } }; // -------------------------------------------------------------------- /* inline Arc(const Matrix &m, Angle alpha, Angle beta); Arc(const Matrix &m0, const Vector &begp, const Vector &endp); */ void ipelua::push_arc(lua_State *L, const Arc &a0) { Arc *a = (Arc *) lua_newuserdata(L, sizeof(Arc)); luaL_getmetatable(L, "Ipe.arc"); lua_setmetatable(L, -2); new (a) Arc(a0); } int ipelua::arc_constructor(lua_State *L) { Matrix *m = check_matrix(L, 1); if (lua_gettop(L) == 1) { push_arc(L, Arc(*m)); } else if (is_type(L, 2, "Ipe.vector")) { Vector *v1 = check_vector(L, 2); Vector *v2 = check_vector(L, 3); push_arc(L, Arc(*m, *v1, *v2)); } else { double alpha = luaL_checknumber(L, 2); double beta = luaL_checknumber(L, 3); push_arc(L, Arc(*m, Angle(alpha), Angle(beta))); } return 1; } static int arc_tostring(lua_State *L) { (void) check_arc(L, 1); lua_pushfstring(L, "Arc@%p", lua_topointer(L, 1)); return 1; } static int arc_endpoints(lua_State *L) { Arc *b = check_arc(L, 1); push_vector(L, b->beginp()); push_vector(L, b->endp()); return 2; } static int arc_angles(lua_State *L) { Arc *b = check_arc(L, 1); lua_pushnumber(L, b->iAlpha); lua_pushnumber(L, b->iBeta); return 2; } static int arc_bbox(lua_State *L) { Arc *b = check_arc(L, 1); push_rect(L, b->bbox()); return 1; } static int arc_matrix(lua_State *L) { Arc *b = check_arc(L, 1); push_matrix(L, b->iM); return 1; } static int arc_isEllipse(lua_State *L) { Arc *b = check_arc(L, 1); lua_pushboolean(L, b->isEllipse()); return 1; } static int arc_intersect(lua_State *L) { Arc *a = check_arc(L, 1); std::vector pts; if (is_type(L, 2, "Ipe.segment")) { Segment *rhs = check_segment(L, 2); a->intersect(*rhs, pts); } else if (is_type(L, 2, "Ipe.line")) { Line *rhs = check_line(L, 2); a->intersect(*rhs, pts); } else if (is_type(L, 2, "Ipe.arc")) { Arc *rhs = check_arc(L, 2); a->intersect(*rhs, pts); } else if (is_type(L, 2, "Ipe.bezier")) { Bezier *rhs = check_bezier(L, 2); a->intersect(*rhs, pts); } lua_createtable(L, pts.size(), 0); for (int i = 0; i < int(pts.size()); ++i) { push_vector(L, pts[i]); lua_rawseti(L, -2, i+1); } return 1; } static int arc_snap(lua_State *L) { Arc *a = check_arc(L, 1); Vector *v = check_vector(L, 2); Vector pos; Angle alpha; (void) a->distance(*v, 10e9, pos, alpha); lua_pushnumber(L, double(alpha)); push_vector(L, pos); return 2; } static const struct luaL_Reg arc_methods[] = { { "__tostring", arc_tostring }, { "endpoints", arc_endpoints }, { "angles", arc_angles }, { "bbox", arc_bbox }, { "matrix", arc_matrix }, { "isEllipse", arc_isEllipse }, { "intersect", arc_intersect }, { "snap", arc_snap }, { nullptr, nullptr } }; // -------------------------------------------------------------------- int ipelua::open_ipegeo(lua_State *L) { luaL_newmetatable(L, "Ipe.vector"); luaL_setfuncs(L, vector_methods, 0); lua_pop(L, 1); make_metatable(L, "Ipe.matrix", matrix_methods); make_metatable(L, "Ipe.rect", rect_methods); make_metatable(L, "Ipe.line", line_methods); make_metatable(L, "Ipe.segment", segment_methods); make_metatable(L, "Ipe.bezier", bezier_methods); make_metatable(L, "Ipe.arc", arc_methods); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelua/ipeluaobj.cpp0000644000175000017500000006445713561570220017000 0ustar otfriedotfried// -------------------------------------------------------------------- // ipeluaobj.cpp // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipelua.h" #include "ipereference.h" #include "ipegroup.h" #include "ipepath.h" #include "ipetext.h" #include "ipeimage.h" #include "ipeiml.h" using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- static const char *const type_names[] = { "group", "path", "text", "image", "reference", nullptr }; static const char *const pinned_names[] = { "none", "horizontal", "vertical", "fixed", nullptr }; static const char *const pathmode_names[] = { "stroked", "strokedfilled", "filled", nullptr }; static const char *const transformation_names[] = { "translations", "rigid", "affine", nullptr }; static const char *const horizontal_alignment_names[] = { "left", "right", "hcenter", nullptr }; static const char *const vertical_alignment_names[] = { "bottom", "baseline", "top", "vcenter", nullptr }; const char *const ipelua::linejoin_names[] = { "normal", "miter", "round", "bevel", nullptr }; const char *const ipelua::linecap_names[] = { "normal", "butt", "round", "square", nullptr }; const char *const ipelua::fillrule_names[] = { "normal", "wind", "evenodd", nullptr }; // -------------------------------------------------------------------- void ipelua::push_string(lua_State *L, String str) { lua_pushlstring(L, str.data(), str.size()); } void ipelua::push_object(lua_State *L, Object *s0, bool owned) { SObject *s = (SObject *) lua_newuserdata(L, sizeof(SObject)); s->owned = owned; s->obj = s0; luaL_getmetatable(L, "Ipe.object"); lua_setmetatable(L, -2); } void ipelua::push_color(lua_State *L, Color color) { lua_createtable(L, 0, 3); lua_pushnumber(L, color.iRed.toDouble()); lua_setfield(L, -2, "r"); lua_pushnumber(L, color.iGreen.toDouble()); lua_setfield(L, -2, "g"); lua_pushnumber(L, color.iBlue.toDouble()); lua_setfield(L, -2, "b"); } void ipelua::push_attribute(lua_State *L, Attribute att) { if (att.isBoolean()) lua_pushboolean(L, att.boolean()); else if (att.isSymbolic() || att.isString() || att.isEnum()) push_string(L, att.string()); else if (att.isNumber()) lua_pushnumber(L, att.number().toDouble()); else // must be color push_color(L, att.color()); } // i must be positive Color ipelua::check_color(lua_State *L, int i) { luaL_checktype(L, i, LUA_TTABLE); lua_getfield(L, i, "r"); lua_getfield(L, i, "g"); lua_getfield(L, i, "b"); double r = luaL_checknumber(L, -3); double g = luaL_checknumber(L, -2); double b = luaL_checknumber(L, -1); lua_pop(L, 3); Color color; color.iRed = Fixed::fromDouble(r); color.iGreen = Fixed::fromDouble(g); color.iBlue = Fixed::fromDouble(b); return color; } #if 0 // i must be positive Attribute ipelua::check_attribute(lua_State *L, int i) { if (lua_type(L, i) == LUA_TNUMBER) { double v = luaL_checknumber(L, i); return Attribute(Fixed::fromInternal(int(v * 1000 + 0.5))); } else if (lua_type(L, i) == LUA_TSTRING) { const char *s = luaL_checklstring(L, i, nullptr); if (!strcmp(s, "true")) return Attribute::Boolean(true); if (!strcmp(s, "false")) return Attribute::Boolean(false); if (('a' <= s[0] && s[0] <= 'z') || ('A' <= s[0] && s[0] <= 'Z')) return Attribute(true, s); else return Attribute(false, s); } else if (lua_type(L, i) == LUA_TTABLE) { Color color = check_color(L, i); return Attribute(color); } else if (lua_type(L, i) == LUA_TBOOLEAN) { return Attribute::Boolean(lua_toboolean(L, i)); } else { luaL_argerror(L, i, "attribute expected"); return Attribute::NORMAL(); // placate compiler } } #endif // i must be positive Attribute ipelua::check_color_attribute(lua_State *L, int i) { if (lua_type(L, i) == LUA_TSTRING) { const char *s = luaL_checklstring(L, i, nullptr); return Attribute(true, s); } else { Color color = check_color(L, i); return Attribute(color); } } // i must be positive Attribute ipelua::check_bool_attribute(lua_State *L, int i) { static const char * const bool_names[] = { "false", "true" }; if (lua_type(L, i) == LUA_TBOOLEAN) return Attribute::Boolean(lua_toboolean(L, i)); int val = luaL_checkoption(L, i, nullptr, bool_names); return Attribute::Boolean(val); } // i must be positive Attribute ipelua::check_number_attribute(lua_State *L, int i) { if (lua_type(L, i) == LUA_TNUMBER) { double v = luaL_checknumber(L, i); return Attribute(Fixed::fromInternal(int(v * 1000 + 0.5))); } const char *s = luaL_checklstring(L, i, nullptr); return Attribute(true, s); } Attribute ipelua::check_property(Property prop, lua_State *L, int i) { int val; switch (prop) { case EPropHorizontalAlignment: val = luaL_checkoption(L, i, nullptr, horizontal_alignment_names); return Attribute(THorizontalAlignment(val)); case EPropVerticalAlignment: val = luaL_checkoption(L, i, nullptr, vertical_alignment_names); return Attribute(TVerticalAlignment(val)); case EPropLineJoin: val = luaL_checkoption(L, i, nullptr, linejoin_names); return Attribute(TLineJoin(val)); case EPropLineCap: val = luaL_checkoption(L, i, nullptr, linecap_names); return Attribute(TLineCap(val)); case EPropFillRule: val = luaL_checkoption(L, i, nullptr, fillrule_names); return Attribute(TFillRule(val)); case EPropPinned: val = luaL_checkoption(L, i, nullptr, pinned_names); return Attribute(TPinned(val)); case EPropTransformations: val = luaL_checkoption(L, i, nullptr, transformation_names); return Attribute(TTransformations(val)); case EPropPathMode: val = luaL_checkoption(L, i, nullptr, pathmode_names); return Attribute(TPathMode(val)); case EPropPen: case EPropSymbolSize: case EPropFArrowSize: case EPropRArrowSize: case EPropTextSize: return check_number_attribute(L, i); case EPropWidth: { // absolute number only! double v = luaL_checknumber(L, i); return Attribute(Fixed::fromInternal(int(v * 1000 + 0.5))); } case EPropFArrowShape: case EPropRArrowShape: case EPropMarkShape: case EPropTextStyle: case EPropLabelStyle: case EPropOpacity: case EPropStrokeOpacity: case EPropGradient: case EPropDecoration: case EPropTiling: // symbolic string only return Attribute(true, luaL_checklstring(L, i, nullptr)); case EPropStrokeColor: case EPropFillColor: return check_color_attribute(L, i); case EPropDashStyle: return Attribute::makeDashStyle(luaL_checklstring(L, i, nullptr)); case EPropFArrow: case EPropRArrow: case EPropMinipage: case EPropTransformableText: return check_bool_attribute(L, i); } return Attribute::NORMAL(); // placate compiler } static void get_attribute(lua_State *L, int i, Property prop, const char *key, Attribute &att) { lua_getfield(L, i, key); if (!lua_isnil(L, -1)) att = check_property(prop, L, lua_gettop(L)); // arg must be positive lua_pop(L, 1); } static void get_boolean(lua_State *L, int i, const char *key, bool &att) { lua_getfield(L, i, key); att = lua_toboolean(L, -1); lua_pop(L, 1); } static int get_option(lua_State *L, int i, const char *key, const char *const *names) { lua_getfield(L, i, key); int val; if (!lua_isnil(L, -1)) val = luaL_checkoption(L, -1, nullptr, names); else val = -1; lua_pop(L, 1); return val; } // i must be positive void ipelua::check_allattributes(lua_State *L, int i, AllAttributes &all) { luaL_checktype(L, i, LUA_TTABLE); get_attribute(L, i, EPropStrokeColor, "stroke", all.iStroke); get_attribute(L, i, EPropFillColor, "fill", all.iFill); get_attribute(L, i, EPropDashStyle, "dashstyle", all.iDashStyle); get_attribute(L, i, EPropPen, "pen", all.iPen); get_boolean(L, i, "farrow", all.iFArrow); get_boolean(L, i, "rarrow", all.iRArrow); get_attribute(L, i, EPropFArrowShape, "farrowshape", all.iFArrowShape); get_attribute(L, i, EPropRArrowShape, "rarrowshape", all.iRArrowShape); get_attribute(L, i, EPropFArrowSize, "farrowsize", all.iFArrowSize); get_attribute(L, i, EPropRArrowSize, "rarrowsize", all.iRArrowSize); get_attribute(L, i, EPropSymbolSize, "symbolsize", all.iSymbolSize); get_attribute(L, i, EPropMarkShape, "markshape", all.iMarkShape); get_attribute(L, i, EPropTextSize, "textsize", all.iTextSize); get_boolean(L, i, "transformabletext", all.iTransformableText); get_attribute(L, i, EPropTextStyle, "textstyle", all.iTextStyle); get_attribute(L, i, EPropTextStyle, "labelstyle", all.iLabelStyle); get_attribute(L, i, EPropOpacity, "opacity", all.iOpacity); get_attribute(L, i, EPropStrokeOpacity, "strokeopacity", all.iStrokeOpacity); get_attribute(L, i, EPropTiling, "tiling", all.iTiling); get_attribute(L, i, EPropGradient, "gradient", all.iGradient); int t; t = get_option(L, i, "horizontalalignment", horizontal_alignment_names); if (t >= 0) all.iHorizontalAlignment = THorizontalAlignment(t); t = get_option(L, i, "verticalalignment", vertical_alignment_names); if (t >= 0) all.iVerticalAlignment = TVerticalAlignment(t); t = get_option(L, i, "linejoin", linejoin_names); if (t >= 0) all.iLineJoin = TLineJoin(t); t = get_option(L, i, "linecap", linecap_names); if (t >= 0) all.iLineCap = TLineCap(t); t = get_option(L, i, "fillrule", fillrule_names); if (t >= 0) all.iFillRule = TFillRule(t); t = get_option(L, i, "pinned", pinned_names); if (t >= 0) all.iPinned = TPinned(t); t = get_option(L, i, "transformations", transformation_names); if (t >= 0) all.iTransformations = TTransformations(t); t = get_option(L, i, "pathmode", pathmode_names); if (t >= 0) all.iPathMode = TPathMode(t); } // -------------------------------------------------------------------- int ipelua::reference_constructor(lua_State *L) { AllAttributes all; check_allattributes(L, 1, all); Attribute name(true, luaL_checklstring(L, 2, nullptr)); Vector *v = check_vector(L, 3); Reference *r = new Reference(all, name, *v); push_object(L, r); return 1; } int ipelua::text_constructor(lua_State *L) { AllAttributes all; check_allattributes(L, 1, all); const char *s = luaL_checklstring(L, 2, nullptr); Vector *v = check_vector(L, 3); double width = 10.0; Text::TextType type = Text::ELabel; if (lua_isnumber(L, 4)) { type = Text::EMinipage; width = luaL_checknumber(L, 4); } Text *t = new Text(all, s, *v, type, width); push_object(L, t); return 1; } int ipelua::path_constructor(lua_State *L) { AllAttributes all; check_allattributes(L, 1, all); Shape shape = check_shape(L, 2); bool withArrows = lua_toboolean(L, 3); Path *p = new Path(all, shape, withArrows); push_object(L, p); return 1; } int ipelua::group_constructor(lua_State *L) { luaL_checktype(L, 1, LUA_TTABLE); Group *g = new Group(); // make sure Lua will collect it if exception happens push_object(L, g); int no = lua_rawlen(L, 1); for (int i = 1; i <= no; ++i) { lua_rawgeti(L, 1, i); luaL_argcheck(L, is_type(L, -1, "Ipe.object"), 1, "element is not an Ipe object"); SObject *p = (SObject *) lua_touserdata(L, -1); g->push_back(p->obj->clone()); lua_pop(L, 1); // object i } return 1; } int ipelua::xml_constructor(lua_State *L) { String s = luaL_checklstring(L, 1, nullptr); Buffer buffer(s.data(), s.size()); BufferSource source(buffer); ImlParser parser(source); String tag = parser.parseToTag(); if (tag == "ipeselection") { lua_newtable(L); int index = 1; XmlAttributes attr; if (!parser.parseAttributes(attr)) return 0; tag = parser.parseToTag(); while (tag == "bitmap") { if (!parser.parseBitmap()) return false; tag = parser.parseToTag(); } for (;;) { if (tag == "/ipeselection") return 1; Object *obj = parser.parseObject(tag); if (!obj) return 0; push_object(L, obj); lua_rawseti(L, -2, index); ++index; tag = parser.parseToTag(); } } else { Object *obj = parser.parseObject(tag); if (obj) { push_object(L, obj); return 1; } } return 0; } // -------------------------------------------------------------------- static int object_destructor(lua_State *L) { SObject *r = check_object(L, 1); if (r->owned && r->obj) delete r->obj; r->obj = nullptr; return 0; } static int object_tostring(lua_State *L) { SObject *s = check_object(L, 1); lua_pushfstring(L, "Object(%s)@%p", type_names[s->obj->type()], lua_topointer(L, 1)); return 1; } static int object_type(lua_State *L) { SObject *s = check_object(L, 1); lua_pushstring(L, type_names[s->obj->type()]); return 1; } static int object_set(lua_State *L) { SObject *s = check_object(L, 1); Property prop = Property(luaL_checkoption(L, 2, nullptr, property_names)); Attribute value = check_property(prop, L, 3); s->obj->setAttribute(prop, value); return 0; } static int object_get(lua_State *L) { SObject *s = check_object(L, 1); Property prop = Property(luaL_checkoption(L, 2, nullptr, property_names)); Attribute value = s->obj->getAttribute(prop); push_attribute(L, value); return 1; } static int object_position(lua_State *L) { Object *obj = check_object(L, 1)->obj; luaL_argcheck(L, obj->type() == Object::EText || obj->type() == Object::EReference, 1, "not a text or reference object"); if (obj->asReference()) { push_vector(L, obj->asReference()->position()); return 1; } else if (obj->asText()) { push_vector(L, obj->asText()->position()); return 1; } return 0; } static int object_text(lua_State *L) { Object *obj = check_object(L, 1)->obj; if (obj->type() == Object::EGroup) { push_string(L, obj->asGroup()->url()); } else { luaL_argcheck(L, obj->type() == Object::EText, 1, "not a text object"); push_string(L, obj->asText()->text()); } return 1; } static int object_setText(lua_State *L) { Object *obj = check_object(L, 1)->obj; String s = luaL_checklstring(L, 2, nullptr); if (obj->type() == Object::EGroup) { obj->asGroup()->setUrl(s); } else { luaL_argcheck(L, obj->type() == Object::EText, 1, "not a text object"); obj->asText()->setText(s); } return 0; } static int object_clone(lua_State *L) { SObject *s = check_object(L, 1); push_object(L, s->obj->clone()); return 1; } static int object_matrix(lua_State *L) { SObject *s = check_object(L, 1); push_matrix(L, s->obj->matrix()); return 1; } static int object_setMatrix(lua_State *L) { SObject *s = check_object(L, 1); Matrix *m = check_matrix(L, 2); s->obj->setMatrix(*m); return 0; } static int object_elements(lua_State *L) { Object *obj = check_object(L, 1)->obj; luaL_argcheck(L, obj->type() == Object::EGroup, 1, "not a group object"); Group *g = obj->asGroup(); lua_createtable(L, g->count(), 0); for (int i = 0; i < g->count(); ++i) { push_object(L, g->object(i)->clone()); lua_rawseti(L, -2, i+1); } return 1; } static int object_element(lua_State *L) { Object *obj = check_object(L, 1)->obj; luaL_argcheck(L, obj->type() == Object::EGroup, 1, "not a group object"); int idx = (int) luaL_checkinteger(L, 2); Group *g = obj->asGroup(); luaL_argcheck(L, 1 <= idx && idx <= g->count(), 2, "incorrect element index"); push_object(L, g->object(idx-1)->clone()); return 1; } static int object_elementType(lua_State *L) { Object *obj = check_object(L, 1)->obj; luaL_argcheck(L, obj->type() == Object::EGroup, 1, "not a group object"); int idx = (int) luaL_checkinteger(L, 2); Group *g = obj->asGroup(); luaL_argcheck(L, 1 <= idx && idx <= g->count(), 2, "incorrect element index"); lua_pushstring(L, type_names[g->object(idx-1)->type()]); return 1; } static int object_xml(lua_State *L) { SObject *obj = check_object(L, 1); String s; StringStream stream(s); obj->obj->saveAsXml(stream, String()); push_string(L, s); return 1; } static int object_addToBBox(lua_State *L) { SObject *s = check_object(L, 1); Rect *r = check_rect(L, 2); Matrix *m = check_matrix(L, 3); bool cp = true; if (lua_type(L, 4) == LUA_TBOOLEAN) cp = lua_toboolean(L, 4); s->obj->addToBBox(*r, *m, cp); return 0; } // -------------------------------------------------------------------- static const char * const segtype_names[] = { "arc", "segment", "spline", "oldspline", nullptr }; static int segtype_cp[] = { 2, 2, 0, 0 }; static const char * const subpath_names[] = { "curve", "ellipse", "closedspline", nullptr }; static bool collect_cp(lua_State *L, std::vector &cp) { for (int i = 0; ; ++i) { lua_rawgeti(L, -1, i+1); if (lua_isnil(L, -1)) { lua_pop(L, 1); return true; } if (!is_type(L, -1, "Ipe.vector")) return false; Vector *v = check_vector(L, -1); cp.push_back(*v); lua_pop(L, 1); // cp } } static SubPath *get_ellipse(lua_State *L, int index) { lua_rawgeti(L, -1, 1); // get matrix if (!is_type(L, -1, "Ipe.matrix")) luaL_error(L, "element %d has no matrix", index); Matrix *m = check_matrix(L, -1); lua_pop(L, 1); // matrix return new Ellipse(*m); } static SubPath *get_closedspline(lua_State *L, int index) { std::vector cp; if (!collect_cp(L, cp)) luaL_error(L, "non-vector control point in element %d", index); return new ClosedSpline(cp); } static SubPath *get_curve(lua_State *L, int index) { std::unique_ptr c(new Curve()); lua_getfield(L, -1, "closed"); if (!lua_isboolean(L, -1)) luaL_error(L, "element %d has no 'closed' field", index); c->setClosed(lua_toboolean(L, -1)); lua_pop(L, 1); // closed for (int i = 0; ; ++i) { lua_rawgeti(L, -1, i+1); if (lua_isnil(L, -1)) { lua_pop(L, 1); if (c->countSegments() == 0) luaL_error(L, "element %d has no segments", index); return c.release(); } if (!lua_istable(L, -1)) luaL_error(L, "segment %d of element %d is not a table", i+1, index); lua_getfield(L, -1, "type"); if (!lua_isstring(L, -1)) luaL_error(L, "segment %d of element %d has no type", i+1, index); int type = test_option(L, -1, segtype_names); if (type < 0) luaL_error(L, "segment %d of element %d has invalid type", i+1, index); lua_pop(L, 1); // pop type std::vector cp; if (!collect_cp(L, cp)) luaL_error(L, "non-vector control point in segment %d of element %d", i+1, index); int cpn = segtype_cp[type]; if (int(cp.size()) < 2 || (cpn > 0 && int(cp.size()) != cpn)) luaL_error(L, "invalid # of control points in segment %d of element %d", i+1, index); switch (type) { case CurveSegment::EArc: { lua_getfield(L, -1, "arc"); if (!is_type(L, -1, "Ipe.arc")) luaL_error(L, "segment %d of element %d has no arc", i+1, index); Arc *a = check_arc(L, -1); lua_pop(L, 1); // arc c->appendArc(a->iM, cp[0], cp[1]); break; } case CurveSegment::ESegment: c->appendSegment(cp[0], cp[1]); break; case CurveSegment::ESpline: c->appendSpline(cp); break; case CurveSegment::EOldSpline: c->appendOldSpline(cp); break; default: break; } lua_pop(L, 1); // pop segment table } } // index must be positive Shape ipelua::check_shape(lua_State *L, int index) { luaL_checktype(L, index, LUA_TTABLE); Shape shape; for (int i = 0; ; ++i) { lua_rawgeti(L, index, i+1); if (lua_isnil(L, -1)) { lua_pop(L, 1); return shape; } if (!lua_istable(L, -1)) luaL_error(L, "element %d is not a table", i+1); lua_getfield(L, -1, "type"); // stack: subpath, type if (!lua_isstring(L, -1)) luaL_error(L, "element %d has no type", i+1); int type = test_option(L, -1, subpath_names); lua_pop(L, 1); // type switch (type) { case SubPath::EEllipse: shape.appendSubPath(get_ellipse(L, i+1)); break; case SubPath::EClosedSpline: shape.appendSubPath(get_closedspline(L, i+1)); break; case SubPath::ECurve: shape.appendSubPath(get_curve(L, i+1)); break; default: luaL_error(L, "element %d has invalid type", i+1); } lua_pop(L, 1); // subpath } } static void push_segment(lua_State *L, const CurveSegment &seg) { lua_createtable(L, seg.countCP(), (seg.type() == CurveSegment::EArc ? 2 : 1)); lua_pushstring(L, segtype_names[seg.type()]); lua_setfield(L, -2, "type"); for (int i = 0; i < seg.countCP(); ++i) { push_vector(L, seg.cp(i)); lua_rawseti(L, -2, i+1); } if (seg.type() == CurveSegment::EArc) { push_arc(L, seg.arc()); lua_setfield(L, -2, "arc"); } } static void push_subpath(lua_State *L, const SubPath *sp) { switch (sp->type()) { case SubPath::EEllipse: lua_createtable(L, 1, 1); lua_pushstring(L, "ellipse"); lua_setfield(L, -2, "type"); push_matrix(L, sp->asEllipse()->matrix()); lua_rawseti(L, -2, 1); break; case SubPath::EClosedSpline: { const ClosedSpline *cs = sp->asClosedSpline(); lua_createtable(L, cs->iCP.size(), 1); lua_pushstring(L, "closedspline"); lua_setfield(L, -2, "type"); for (int j = 0; j < size(cs->iCP); ++j) { push_vector(L, cs->iCP[j]); lua_rawseti(L, -2, j+1); } break; } case SubPath::ECurve: { const Curve *c = sp->asCurve(); lua_createtable(L, c->countSegments(), 2); lua_pushstring(L, "curve"); lua_setfield(L, -2, "type"); lua_pushboolean(L, c->closed()); lua_setfield(L, -2, "closed"); for (int j = 0; j < c->countSegments(); ++j) { push_segment(L, c->segment(j)); lua_rawseti(L, -2, j+1); } break; } } } static void push_shape(lua_State *L, const Shape &shape) { lua_createtable(L, shape.countSubPaths(), 0); for (int i = 0; i < shape.countSubPaths(); ++i) { push_subpath(L, shape.subPath(i)); lua_rawseti(L, -2, i+1); } } static int object_shape(lua_State *L) { Object *s = check_object(L, 1)->obj; luaL_argcheck(L, s->type() == Object::EPath, 1, "not a path object"); const Shape &shape = s->asPath()->shape(); push_shape(L, shape); return 1; } static int object_setShape(lua_State *L) { Object *s = check_object(L, 1)->obj; luaL_argcheck(L, s->type() == Object::EPath, 1, "not a path object"); Shape shape = check_shape(L, 2); s->asPath()->setShape(shape); return 1; } static int object_count(lua_State *L) { Object *s = check_object(L, 1)->obj; luaL_argcheck(L, s->type() == Object::EGroup, 1, "not a group object"); lua_pushnumber(L, s->asGroup()->count()); return 1; } static int object_clip(lua_State *L) { Object *s = check_object(L, 1)->obj; luaL_argcheck(L, s->type() == Object::EGroup, 1, "not a group object"); const Shape &shape = s->asGroup()->clip(); if (shape.countSubPaths() > 0) { push_shape(L, shape); return 1; } else return 0; } static int object_setclip(lua_State *L) { Object *s = check_object(L, 1)->obj; luaL_argcheck(L, s->type() == Object::EGroup, 1, "not a group object"); if (lua_isnoneornil(L, 2)) { s->asGroup()->setClip(Shape()); } else { Shape shape = check_shape(L, 2); s->asGroup()->setClip(shape); } return 0; } static int object_symbol(lua_State *L) { Object *s = check_object(L, 1)->obj; luaL_argcheck(L, s->type() == Object::EReference, 1, "not a reference object"); push_string(L, s->asReference()->name().string()); return 1; } static int object_info(lua_State *L) { Object *s = check_object(L, 1)->obj; luaL_argcheck(L, s->type() == Object::EImage, 1, "not an image object"); Bitmap bm = s->asImage()->bitmap(); lua_createtable(L, 0, 7); lua_pushnumber(L, bm.width()); lua_setfield(L, -2, "width"); lua_pushnumber(L, bm.height()); lua_setfield(L, -2, "height"); String format; if (bm.isJpeg()) format = "jpg"; else { if (bm.isGray()) format = "gray"; else format = "rgb"; if (bm.hasAlpha()) format += " alpha"; else if (bm.colorKey() >= 0) format += " colorkeyed"; } push_string(L, format); lua_setfield(L, -2, "format"); return 1; } static int object_savePixels(lua_State *L) { Object *s = check_object(L, 1)->obj; luaL_argcheck(L, s->type() == Object::EImage, 1, "not an image object"); String fname = luaL_checklstring(L, 2, nullptr); Bitmap bm = s->asImage()->bitmap(); bm.savePixels(fname.z()); return 0; } // -------------------------------------------------------------------- static const struct luaL_Reg object_methods[] = { { "__tostring", object_tostring }, { "__gc", object_destructor }, { "type", object_type }, { "set", object_set }, { "get", object_get }, { "xml", object_xml }, { "clone", object_clone }, { "matrix", object_matrix }, { "setMatrix", object_setMatrix }, { "addToBBox", object_addToBBox }, { "position", object_position }, { "shape", object_shape }, { "setShape", object_setShape }, { "count", object_count }, { "clip", object_clip }, { "setClip", object_setclip }, { "symbol", object_symbol }, { "info", object_info }, { "savePixels", object_savePixels }, { "position", object_position }, { "text", object_text }, { "setText", object_setText }, { "elements", object_elements }, { "element", object_element }, { "elementType", object_elementType }, { nullptr, nullptr } }; // -------------------------------------------------------------------- int ipelua::open_ipeobj(lua_State *L) { make_metatable(L, "Ipe.object", object_methods); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelua/ipelua.h0000644000175000017500000001563613561570220015745 0ustar otfriedotfried// -------------------------------------------------------------------- // ipelua.h // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPELUA_H #define IPELUA_H extern "C" { #include #include #include } #include "ipestyle.h" #include "ipepage.h" #include "ipeshape.h" #include "ipedoc.h" #include "ipelet.h" namespace ipelua { struct SSheet { bool owned; ipe::StyleSheet *sheet; }; struct SCascade { bool owned; ipe::Cascade *cascade; }; struct SPage { bool owned; ipe::Page *page; }; struct SObject { bool owned; ipe::Object *obj; }; inline ipe::Document **check_document(lua_State *L, int i) { return (ipe::Document **) luaL_checkudata(L, i, "Ipe.document"); } inline ipe::Vector *check_vector(lua_State *L, int i) { return (ipe::Vector *) luaL_checkudata(L, i, "Ipe.vector"); } inline ipe::Matrix *check_matrix(lua_State *L, int i) { return (ipe::Matrix *) luaL_checkudata(L, i, "Ipe.matrix"); } inline ipe::Rect *check_rect(lua_State *L, int i) { return (ipe::Rect *) luaL_checkudata(L, i, "Ipe.rect"); } inline ipe::Line *check_line(lua_State *L, int i) { return (ipe::Line *) luaL_checkudata(L, i, "Ipe.line"); } inline ipe::Segment *check_segment(lua_State *L, int i) { return (ipe::Segment *) luaL_checkudata(L, i, "Ipe.segment"); } inline ipe::Bezier *check_bezier(lua_State *L, int i) { return (ipe::Bezier *) luaL_checkudata(L, i, "Ipe.bezier"); } inline ipe::Arc *check_arc(lua_State *L, int i) { return (ipe::Arc *) luaL_checkudata(L, i, "Ipe.arc"); } inline SObject *check_object(lua_State *L, int i) { return (SObject *) luaL_checkudata(L, i, "Ipe.object"); } inline SSheet *check_sheet(lua_State *L, int i) { return (SSheet *) luaL_checkudata(L, i, "Ipe.sheet"); } inline SCascade *check_cascade(lua_State *L, int i) { return (SCascade *) luaL_checkudata(L, i, "Ipe.cascade"); } inline SPage *check_page(lua_State *L, int i) { return (SPage *) luaL_checkudata(L, i, "Ipe.page"); } inline ipe::Ipelet **check_ipelet(lua_State *L, int i) { return (ipe::Ipelet **) luaL_checkudata(L, i, "Ipe.ipelet"); } inline void luacall(lua_State *L, int nargs, int nresults) { lua_callk(L, nargs, nresults, 0, nullptr); } // -------------------------------------------------------------------- extern void make_metatable(lua_State *L, const char *name, const struct luaL_Reg *methods); extern bool is_type(lua_State *L, int ud, const char *tname); extern const char *const linejoin_names[]; extern const char *const linecap_names[]; extern const char *const fillrule_names[]; extern ipe::String check_filename(lua_State *L, int index); // geo extern void push_vector(lua_State *L, const ipe::Vector &v); extern int vector_constructor(lua_State *L); extern int direction_constructor(lua_State *L); extern void push_matrix(lua_State *L, const ipe::Matrix &m); extern int matrix_constructor(lua_State *L); extern int rotation_constructor(lua_State *L); extern int translation_constructor(lua_State *L); extern void push_rect(lua_State *L, const ipe::Rect &r); extern int rect_constructor(lua_State *L); extern void push_line(lua_State *L, const ipe::Line &l); extern int line_constructor(lua_State *L); extern int line_through(lua_State *L); extern int line_bisector(lua_State *L); extern void push_segment(lua_State *L, const ipe::Segment &s); extern int segment_constructor(lua_State *L); extern void push_bezier(lua_State *L, const ipe::Bezier &b); extern int bezier_constructor(lua_State *L); extern int quad_constructor(lua_State *L); extern void push_arc(lua_State *L, const ipe::Arc &a); extern int arc_constructor(lua_State *L); // obj extern void push_string(lua_State *L, ipe::String str); extern void push_color(lua_State *L, ipe::Color color); extern void push_attribute(lua_State *L, ipe::Attribute att); extern ipe::Attribute check_color_attribute(lua_State *L, int i); extern ipe::Attribute check_number_attribute(lua_State *L, int i); extern ipe::Attribute check_bool_attribute(lua_State *L, int i); extern ipe::Color check_color(lua_State *L, int i); extern ipe::Attribute check_property(ipe::Property prop, lua_State *L, int i); extern void check_allattributes(lua_State *L, int i, ipe::AllAttributes &all); extern void push_object(lua_State *L, ipe::Object *obj, bool owned = true); extern int reference_constructor(lua_State *L); extern int text_constructor(lua_State *L); extern int path_constructor(lua_State *L); extern int group_constructor(lua_State *L); extern int xml_constructor(lua_State *L); extern ipe::Shape check_shape(lua_State *L, int index); // style extern void push_sheet(lua_State *L, ipe::StyleSheet *s, bool owned = true); extern void push_cascade(lua_State *L, ipe::Cascade *s, bool owned = true); extern int sheet_constructor(lua_State *L); extern int cascade_constructor(lua_State *L); extern int test_option(lua_State *L, int i, const char * const *names); // page extern void push_page(lua_State *L, ipe::Page *page, bool owned = true); extern int check_layer(lua_State *L, int i, ipe::Page *p); extern int check_viewno(lua_State *L, int i, ipe::Page *p, int extra = 0); extern int page_constructor(lua_State *L); // ipelet extern int ipelet_constructor(lua_State *L); extern void get_snap(lua_State *L, int i, ipe::Snap &snap); // open components extern int open_ipegeo(lua_State *L); extern int open_ipeobj(lua_State *L); extern int open_ipestyle(lua_State *L); extern int open_ipepage(lua_State *L); extern int open_ipelets(lua_State *L); } // namespace extern "C" int luaopen_ipe(lua_State *L); // -------------------------------------------------------------------- #endif ipe-7.2.13/src/iperender/0000755000175000017500000000000013561570220015000 5ustar otfriedotfriedipe-7.2.13/src/iperender/Makefile0000644000175000017500000000142513561570220016442 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for Iperender # -------------------------------------------------------------------- OBJDIR = $(BUILDDIR)/obj/iperender include ../common.mak TARGET = $(call exe_target,iperender) CPPFLAGS += -I../include $(CAIRO_CFLAGS) -I../ipecairo LIBS += -L$(buildlib) -lipecairo -lipe $(CAIRO_LIBS) all: $(TARGET) sources = iperender.cpp $(TARGET): $(objects) $(MAKE_BINDIR) $(CXX) $(LDFLAGS) -o $@ $^ $(LIBS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPEBINDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPEBINDIR) # -------------------------------------------------------------------- ipe-7.2.13/src/iperender/iperender.cpp0000644000175000017500000001147613561570220017472 0ustar otfriedotfried// -------------------------------------------------------------------- // iperender // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipedoc.h" #include "ipethumbs.h" #include #include #include using ipe::Document; using ipe::Page; using ipe::Thumbnail; // -------------------------------------------------------------------- static int renderPage(Thumbnail::TargetFormat fm, const char *src, const char *dst, const char *pageSpec, const char *viewSpec, double zoom, bool transparent, bool nocrop) { Document *doc = Document::loadWithErrorReport(src); if (!doc) return 1; int pageIdx = pageSpec ? doc->findPage(pageSpec) : 0; if (pageIdx < 0) { fprintf(stderr, "Incorrect -page specification.\n"); delete doc; return 1; } const Page *page = doc->page(pageIdx); int viewIdx = viewSpec ? page->findView(viewSpec) : 0; if (viewIdx < 0) { fprintf(stderr, "Incorrect -view specification.\n"); delete doc; return 1; } if (doc->runLatex(src)) { delete doc; return 1; } Thumbnail tn(doc, 0); if (!tn.saveRender(fm, dst, page, viewIdx, zoom, transparent, nocrop)) fprintf(stderr, "Failure to render page.\n"); delete doc; return 0; } // -------------------------------------------------------------------- static void usage() { fprintf(stderr, "Usage: iperender [ -png "); #ifdef CAIRO_HAS_PS_SURFACE fprintf(stderr, "| -eps "); #endif #ifdef CAIRO_HAS_PDF_SURFACE fprintf(stderr, "| -pdf "); #endif #ifdef CAIRO_HAS_SVG_SURFACE fprintf(stderr, "| -svg "); #endif fprintf(stderr, "] " "[ -page ] [ -view ] [ -resolution ] " "[ -transparent ] [ -nocrop ] " "infile outfile\n" "Iperender saves a single page of the Ipe document in some formats.\n" " -page : page to save (default 1).\n" " -view : view to save (default 1).\n" " -resolution : resolution for png format (default 72.0 ppi).\n" " -transparent: use transparent background in png format.\n" " -nocrop : do not crop page.\n" " can be a page number or a page name.\n" ); exit(1); } int main(int argc, char *argv[]) { ipe::Platform::initLib(ipe::IPELIB_VERSION); // ensure at least three arguments (handles -help as well :-) if (argc < 4) usage(); Thumbnail::TargetFormat fm = Thumbnail::EPNG; if (!strcmp(argv[1], "-png")) fm = Thumbnail::EPNG; #ifdef CAIRO_HAS_PS_SURFACE else if (!strcmp(argv[1], "-eps")) fm = Thumbnail::EPS; #endif #ifdef CAIRO_HAS_PDF_SURFACE else if (!strcmp(argv[1], "-pdf")) fm = Thumbnail::EPDF; #endif #ifdef CAIRO_HAS_SVG_SURFACE else if (!strcmp(argv[1], "-svg")) fm = Thumbnail::ESVG; #endif else usage(); const char *page = nullptr; const char *view = nullptr; double dpi = 72.0; bool transparent = false; bool nocrop = false; int i = 2; while (i < argc - 2) { if (!strcmp(argv[i], "-page")) { if (i + 1 == argc) usage(); page = argv[i+1]; i += 2; } else if (!strcmp(argv[i], "-view")) { if (i + 1 == argc) usage(); view = argv[i+1]; i += 2; } else if (!strcmp(argv[i], "-resolution")) { if (i + 1 == argc) usage(); dpi = ipe::Lex(ipe::String(argv[i+1])).getDouble(); i += 2; } else if (!strcmp(argv[i], "-transparent")) { transparent = true; ++i; } else if (!strcmp(argv[i], "-nocrop")) { nocrop = true; ++i; } else usage(); } // remaining arguments must be two filenames const char *src = argv[i]; const char *dst = argv[i+1]; return renderPage(fm, src, dst, page, view, dpi / 72.0, transparent, nocrop); } // -------------------------------------------------------------------- ipe-7.2.13/src/macos.mak0000644000175000017500000000264513561570220014626 0ustar otfriedotfried# -*- makefile -*- # -------------------------------------------------------------------- # # Ipe configuration for Mac OS X # # -------------------------------------------------------------------- # # Where are the dependencies? # # Setting to use Macports libraries: IPEDEPS ?= /opt/local # # Setting to use X11 libraries: #IPEDEPS ?= /opt/X11 # # -------------------------------------------------------------------- # # We build as an application bundle (a directory "Ipe.app" that # contains Ipe and all its files). # If you don't want this, you'll need to also set IPEPREFIX and # all the variables in the "config.mak" file. # IPEBUNDLE = 1 # # Compile support for online Latex translation? (Needs curl library) # #IPECURL = 1 # # -------------------------------------------------------------------- # PNG_CFLAGS ?= -I$(IPEDEPS)/include/libpng16 PNG_LIBS ?= -L$(IPEDEPS)/lib -lpng16 FREETYPE_CFLAGS ?= -I$(IPEDEPS)/include/freetype2 -I$(IPEDEPS)/include FREETYPE_LIBS ?= -L$(IPEDEPS)/lib -lfreetype CAIRO_CFLAGS ?= -I$(IPEDEPS)/include/cairo CAIRO_LIBS ?= -L$(IPEDEPS)/lib -lcairo LUA_CFLAGS ?= -I$(IPEDEPS)/include/lua LUA_LIBS ?= -L$(IPEDEPS)/lib -llua53 -lm ifdef IPECURL CURL_CFLAGS ?= -DCURL_STATICLIB -I$(IPEDEPS)/include CURL_LIBS ?= -L$(IPEDEPS)/lib -lcurl -lz -framework Security endif # IPEVERS = 7.2.13 # CXX = clang++ # # -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/0000755000175000017500000000000013561570220014267 5ustar otfriedotfriedipe-7.2.13/src/ipelib/ipetext.cpp0000644000175000017500000004036513561570220016465 0ustar otfriedotfried// -------------------------------------------------------------------- // The Text object. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipetext.h" #include "ipepainter.h" using namespace ipe; /*! \class ipe::Text \ingroup obj \brief The text object. The text object stores a Latex source representation, which needs to be translated into PDF by Pdflatex before it can be saved as PDF. There are two types of text objects: labels and minipages. The textType() method tells you which, or use isMinipage(). The dimensions of a text object are given by width(), height(), and depth(). They are recomputed by Ipe when running LaTeX, with the exception of the width for minipage objects (whose width is fixed). Before Latex has been run, the dimensions are not reliable. The position of the reference point relative to the text box is given by verticalAlignment() and horizontalAlignment(). The text() must be a legal LaTeX fragment that can be interpreted by LaTeX inside \c \\hbox, possibly using the macros or packages defined in the preamble. */ //! Construct an empty internal text object. Text::Text() : Object() { iXForm = nullptr; iPos = Vector::ZERO; iType = TextType(0); iStroke = Attribute::BLACK(); iOpacity = Attribute::OPAQUE(); iStyle = Attribute::NORMAL(); iWidth = 10.0; iHeight = 10.0; iDepth = 0.0; iVerticalAlignment = EAlignBottom; iHorizontalAlignment = EAlignLeft; } //! Create text object. Text::Text(const AllAttributes &attr, String data, const Vector &pos, TextType type, double width) : Object(attr) { iXForm = nullptr; iText = data; iStroke = attr.iStroke; iOpacity = attr.iOpacity; iSize = attr.iTextSize; iPos = pos; iType = type; iWidth = width; iHeight = 10.0; iDepth = 0.0; if (iType == ELabel) { iStyle = attr.iLabelStyle; iVerticalAlignment = attr.iVerticalAlignment; } else { iStyle = attr.iTextStyle; iVerticalAlignment = EAlignTop; } iHorizontalAlignment = attr.iHorizontalAlignment; if (!attr.iTransformableText) // override setting iTransformations = ETransformationsTranslations; } //! Copy constructor. Text::Text(const Text &rhs) : Object(rhs) { iPos = rhs.iPos; iText = rhs.iText; iStroke = rhs.iStroke; iOpacity = rhs.iOpacity; iSize = rhs.iSize; iStyle = rhs.iStyle; iWidth = rhs.iWidth; iHeight = rhs.iHeight; iDepth = rhs.iDepth; iType = rhs.iType; iVerticalAlignment = rhs.iVerticalAlignment; iHorizontalAlignment = rhs.iHorizontalAlignment; iXForm = rhs.iXForm; if (iXForm) iXForm->iRefCount++; } //! Destructor. Text::~Text() { if (iXForm && --iXForm->iRefCount == 0) delete iXForm; } // -------------------------------------------------------------------- //! Create from XML stream. Text::Text(const XmlAttributes &attr, String data) : Object(attr) { iXForm = nullptr; iText = data; iStroke = Attribute::makeColor(attr["stroke"], Attribute::BLACK()); Lex st(attr["pos"]); st >> iPos.x >> iPos.y; iSize = Attribute::makeTextSize(attr["size"]); String str; iType = ELabel; iWidth = 10.0; if (attr.has("type", str)) { if (str == "minipage") iType = EMinipage; } else if (attr.has("width", str)) iType = EMinipage; // no type attribute if (attr.has("width", str)) iWidth = Lex(str).getDouble(); iHeight = 10.0; if (attr.has("height", str)) iHeight = Lex(str).getDouble(); iDepth = 0.0; if (attr.has("depth", str)) iDepth = Lex(str).getDouble(); iVerticalAlignment = makeVAlign(attr["valign"], isMinipage() ? EAlignTop : EAlignBottom); iHorizontalAlignment = makeHAlign(attr["halign"], EAlignLeft); if (attr.has("style", str) && str != "normal") iStyle = Attribute(true, str); else iStyle = Attribute::NORMAL(); if (attr.has("opacity", str)) iOpacity = Attribute(true, str); else iOpacity = Attribute::OPAQUE(); if (iType == ELabel && iStyle == Attribute::NORMAL() && iText.size() >= 3 && iText[0] == '$' && iText[iText.size()-1] == '$') { for (int i = 1; i < iText.size() - 1; ++i) // check if no other $ in text if (iText[i] == '$') return; iStyle = Attribute(true, "math"); iText = iText.substr(1, iText.size() - 2); } } // -------------------------------------------------------------------- //! Clone object Object *Text::clone() const { return new Text(*this); } //! Return pointer to this object. Text *Text::asText() { return this; } Object::Type Text::type() const { return EText; } // -------------------------------------------------------------------- //! Return vertical alignment indicated by a name, or else default. TVerticalAlignment Text::makeVAlign(String str, TVerticalAlignment def) { if (str == "top") return EAlignTop; else if (str == "bottom") return EAlignBottom; else if (str == "baseline") return EAlignBaseline; else if (str == "center") return EAlignVCenter; else return def; } //! Return horizontal alignment indicated by a name, or else default. THorizontalAlignment Text::makeHAlign(String str, THorizontalAlignment def) { if (str == "left") return EAlignLeft; else if (str == "right") return EAlignRight; else if (str == "center") return EAlignHCenter; else return def; } //! Call visitText of visitor. void Text::accept(Visitor &visitor) const { visitor.visitText(this); } //! Return type of text object. Text::TextType Text::textType() const { if (iType == 0) // internal for title return ELabel; return iType; } //! Save object to XML stream. void Text::saveAsXml(Stream &stream, String layer) const { stream << ""; stream.putXmlString(iText); stream << "\n"; } void Text::saveAlignment(Stream &stream, THorizontalAlignment h, TVerticalAlignment v) { switch (h) { case EAlignLeft: break; case EAlignHCenter: stream << " halign=\"center\""; break; case EAlignRight: stream << " halign=\"right\""; break; } switch (v) { case EAlignTop: stream << " valign=\"top\""; break; case EAlignBottom: stream << " valign=\"bottom\""; break; case EAlignBaseline: stream << " valign=\"baseline\""; break; case EAlignVCenter: stream << " valign=\"center\""; break; } } //! Save text as PDF. void Text::draw(Painter &painter) const { painter.push(); painter.pushMatrix(); painter.transform(matrix()); painter.translate(iPos); painter.untransform(transformations()); painter.setStroke(iStroke); painter.setOpacity(iOpacity); // Adjust alignment: make lower left corner of text box the origin painter.translate(-align()); painter.drawText(this); painter.popMatrix(); painter.pop(); } void Text::drawSimple(Painter &painter) const { painter.pushMatrix(); painter.transform(matrix()); painter.translate(iPos); painter.untransform(transformations()); painter.newPath(); double wid = iWidth; double ht = totalHeight(); Vector offset = -align(); painter.moveTo(offset + Vector(0, 0)); painter.lineTo(offset + Vector(wid, 0)); painter.lineTo(offset + Vector(wid, ht)); painter.lineTo(offset + Vector(0, ht)); painter.closePath(); painter.drawPath(EStrokedOnly); painter.popMatrix(); } double Text::distance(const Vector &v, const Matrix &m, double bound) const { Vector u[5]; quadrilateral(m, u); u[4] = u[0]; double d = bound; double d1; for (int i = 0; i < 4; ++i) { if ((d1 = Segment(u[i], u[i+1]).distance(v, d)) < d) d = d1; } return d1; } void Text::addToBBox(Rect &box, const Matrix &m, bool) const { Vector v[4]; quadrilateral(m, v); for (int i = 0; i < 4; ++i) box.addPoint(v[i]); } void Text::snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { (m * (matrix() * iPos)).snap(mouse, pos, bound); Vector v[4]; quadrilateral(m, v); for (int i = 0; i < 4; ++i) v[i].snap(mouse, pos, bound); } // -------------------------------------------------------------------- //! Set stroke color void Text::setStroke(Attribute stroke) { iStroke = stroke; } //! Set opacity of the object. void Text::setOpacity(Attribute opaq) { iOpacity = opaq; } //! Set width of paragraph. /*! This invalidates (and destroys) the XForm. The function panics if object is not a (true) minipage. */ void Text::setWidth(double width) { assert(textType() == EMinipage); iWidth = width; setXForm(nullptr); } //! Set font size of text. /*! This invalidates (and destroys) the XForm. */ void Text::setSize(Attribute size) { iSize = size; setXForm(nullptr); } //! Set Latex style of text. /*! This invalidates (and destroys) the XForm. */ void Text::setStyle(Attribute style) { iStyle = style; setXForm(nullptr); } //! Sets the text of the text object. /*! This invalidates (and destroys) the XForm. */ void Text::setText(String text) { iText = text; setXForm(nullptr); } //! Change type. /*! This invalidates (and destroys) the XForm. */ void Text::setTextType(TextType type) { if (type != iType) { iType = type; iStyle = Attribute::NORMAL(); setXForm(nullptr); } } //! Change horizontal alignment (text moves with respect to reference point). void Text::setHorizontalAlignment(THorizontalAlignment align) { iHorizontalAlignment = align; } //! Change vertical alignment (text moves with respect to reference point). void Text::setVerticalAlignment(TVerticalAlignment align) { iVerticalAlignment = align; } bool Text::setAttribute(Property prop, Attribute value) { switch (prop) { case EPropStrokeColor: if (value != stroke()) { setStroke(value); return true; } break; case EPropTextSize: if (value != size()) { setSize(value); return true; } break; case EPropTextStyle: case EPropLabelStyle: if ((isMinipage() != (prop == EPropTextStyle)) || value == style()) return false; setStyle(value); return true; case EPropOpacity: if (value != opacity()) { setOpacity(value); return true; } break; case EPropHorizontalAlignment: assert(value.isEnum()); if (value.horizontalAlignment() != horizontalAlignment()) { iHorizontalAlignment = THorizontalAlignment(value.horizontalAlignment()); return true; } break; case EPropVerticalAlignment: assert(value.isEnum()); if (value.verticalAlignment() != verticalAlignment()) { iVerticalAlignment = TVerticalAlignment(value.verticalAlignment()); return true; } break; case EPropMinipage: assert(value.isEnum()); if (value.boolean() != isMinipage()) { iType = value.boolean() ? EMinipage : ELabel; iStyle = Attribute::NORMAL(); return true; } break; case EPropWidth: assert(value.isNumber()); if (value.number().toDouble() != width()) { setWidth(value.number().toDouble()); return true; } break; case EPropTransformableText: assert(value.isEnum()); if (value.boolean() && transformations() != ETransformationsAffine) { setTransformations(ETransformationsAffine); return true; } else if (!value.boolean() && transformations() != ETransformationsTranslations) { setTransformations(ETransformationsTranslations); return true; } break; default: return Object::setAttribute(prop, value); } return false; } Attribute Text::getAttribute(Property prop) const noexcept { switch (prop) { case EPropStrokeColor: return stroke(); case EPropTextSize: return size(); case EPropTextStyle: case EPropLabelStyle: return style(); case EPropOpacity: return opacity(); case EPropHorizontalAlignment: return Attribute(horizontalAlignment()); case EPropVerticalAlignment: return Attribute(verticalAlignment()); case EPropMinipage: return Attribute::Boolean(isMinipage()); case EPropWidth: return Attribute(Fixed::fromDouble(width())); default: return Object::getAttribute(prop); } } // -------------------------------------------------------------------- //! Check symbolic size attribute. void Text::checkStyle(const Cascade *sheet, AttributeSeq &seq) const { checkSymbol(EColor, iStroke, sheet, seq); checkSymbol(ETextSize, iSize, sheet, seq); checkSymbol((iType == ELabel ? ELabelStyle : ETextStyle), iStyle, sheet, seq); checkSymbol(EOpacity, iOpacity, sheet, seq); } //! Return quadrilateral including the text. /*! This is the bounding box, correctly transformed by matrix(), taking into consideration whether the object is transformable. */ void Text::quadrilateral(const Matrix &m, Vector v[4]) const { double wid = iWidth; double ht = totalHeight(); Vector offset = -align(); v[0] = offset + Vector(0, 0); v[1] = offset + Vector(wid, 0); v[2] = offset + Vector(wid, ht); v[3] = offset + Vector(0, ht); Matrix m1 = m * matrix() * Matrix(iPos); if (iTransformations == ETransformationsTranslations) { m1 = Matrix(m1.translation()); } else if (iTransformations == ETransformationsRigidMotions) { Angle alpha = Vector(m1.a[0], m1.a[1]).angle(); // ensure that (1,0) is rotated into this orientation m1 = Matrix(m1.translation()) * Linear(alpha); } for (int i = 0; i < 4; ++i) v[i] = m1 * v[i]; } //! Update the PDF code for this object. void Text::setXForm(XForm *xform) const { if (iXForm && --iXForm->iRefCount == 0) delete iXForm; iXForm = xform; if (iXForm) { iXForm->iRefCount = 1; iDepth = iXForm->iStretch * iXForm->iDepth / 100.0; iHeight = iXForm->iStretch * iXForm->iBBox.height() - iDepth; if (!isMinipage()) iWidth = iXForm->iStretch * iXForm->iBBox.width(); } } //! Return position of reference point in text box coordinate system. /*! Assume a coordinate system where the text box has corners (0,0) and (Width(), TotalHeight()). This function returns the coordinates of the reference point in this coordinate system. */ Vector Text::align() const { Vector align(0.0, 0.0); switch (verticalAlignment()) { case EAlignTop: align.y = totalHeight(); break; case EAlignBottom: break; case EAlignVCenter: align.y = 0.5 * totalHeight(); break; case EAlignBaseline: align.y = depth(); break; } if (!isMinipage()) { switch (horizontalAlignment()) { case EAlignLeft: break; case EAlignRight: align.x = width(); break; case EAlignHCenter: align.x = 0.5 * width(); break; } } return align; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipefactory.cpp0000644000175000017500000000434413561570220017145 0ustar otfriedotfried// -------------------------------------------------------------------- // The Ipe object factory. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipefactory.h" #include "ipepath.h" #include "ipetext.h" #include "ipeimage.h" #include "ipereference.h" // -------------------------------------------------------------------- using namespace ipe; /*! \class ipe::ObjectFactory \ingroup high \brief Factory for Ipe leaf objects. */ //! Create an Ipe object by calling the right constructor. Object *ObjectFactory::createObject(String name, const XmlAttributes &attr, String data) { if (name == "path") return Path::create(attr, data); else if (name == "text") return new Text(attr, data); else if (name == "image") return new Image(attr, data); else if (name == "use") return new Reference(attr, data); else return nullptr; } //! Create an Image with a given bitmap. Object *ObjectFactory::createImage(String /*name*/, const XmlAttributes &attr, Bitmap bitmap) { return new Image(attr, bitmap); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipegeo.cpp0000644000175000017500000010310613561570220016244 0ustar otfriedotfried// -------------------------------------------------------------------- // Ipe geometry primitives // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /*! \defgroup geo Ipe Geometry \brief Geometric primitives for Ipe. The IpeGeo module provides a few classes for constant-size geometric primitives, such as vector, axis-aligned rectangles, lines, rays, line segments, etc. */ const double BEZIER_INTERSECT_PRECISION = 1.0; #include "ipegeo.h" using namespace ipe; inline double sq(double x) { return x * x; } // -------------------------------------------------------------------- /*! \class ipe::Angle \ingroup geo \brief A double that's an angle. An Angle is really nothing more than a double. Having a separate type is sometimes useful, for instance in the Vector constructor, and this class serves as the right place for a few utility functions. It also makes it clear whether a value is in radians or in degrees. */ double Angle::degrees() const { return (iAlpha / IpePi * 180.0); } //! Normalize the value to the range lowlimit .. lowlimit + 2 pi. /*! This Angle object is modified, a copy is returned. */ Angle Angle::normalize(double lowlimit) { while (iAlpha >= lowlimit + IpeTwoPi) iAlpha -= IpeTwoPi; while (iAlpha < lowlimit) iAlpha += IpeTwoPi; return *this; } /*! When considering the positively oriented circle arc from angle \a small to \a large, does it cover this angle? */ bool Angle::liesBetween(Angle small, Angle large) const { large.normalize(iAlpha); small.normalize(large.iAlpha - IpeTwoPi); return (iAlpha >= small.iAlpha); } // -------------------------------------------------------------------- /*! \class ipe::Vector \ingroup geo \brief Two-dimensional vector. Unlike some other libraries, I don't make a difference between points and vectors. */ //! Construct a unit vector with this direction. Vector::Vector(Angle alpha) { x = cos(alpha); y = sin(alpha); } //! Return angle of the vector (with positive x-direction). /*! The returned angle lies between -pi and +pi. Returns zero for the zero vector. */ Angle Vector::angle() const { if (x == 0.0 && y == 0.0) return Angle(0.0); else return Angle(atan2(y, x)); } //! The origin (zero vector). Vector Vector::ZERO = Vector(0.0, 0.0); double Vector::len() const { return sqrt(sqLen()); } //! Return this vector normalized (with length one). /*! Normalizing the zero vector returns the vector (1,0). */ Vector Vector::normalized() const { double len = sqLen(); if (len == 1.0) return *this; if (len == 0.0) return Vector(1,0); return (1.0/sqrt(len)) * (*this); } //! Return this vector turned 90 degrees to the left. Vector Vector::orthogonal() const { return Vector(-y, x); } /*! Normalizes this vector into \a unit and returns length. If this is the zero vector, \a unit is set to (1,0). */ double Vector::factorize(Vector &unit) const { double len = sqLen(); if (len == 0.0) { unit = Vector(1,0); return len; } if (len == 1.0) { unit = *this; return len; } len = sqrt(len); unit = (1.0 / len) * (*this); return len; } //! Snap to nearby vertex. /*! If distance between \a mouse and this vector is less than \a bound, set \a pos to this vector and \a bound to the distance, and return \c true. */ bool Vector::snap(const Vector &mouse, Vector &pos, double &bound) const { double d = (mouse - *this).len(); if (d < bound) { pos = *this; bound = d; return true; } return false; } //! Output operator for Vector. Stream &ipe::operator<<(Stream &stream, const Vector &rhs) { return stream << rhs.x << " " << rhs.y; } // -------------------------------------------------------------------- /*! \class ipe::Rect \ingroup geo \brief Axis-parallel rectangle (which can be empty) */ //! Create rectangle containing points \a c1 and \a c2. Rect::Rect(const Vector &c1, const Vector &c2) : iMin(1,0), iMax(-1,0) { addPoint(c1); addPoint(c2); } //! Does (closed) rectangle contain the point? bool Rect::contains(const Vector &rhs) const { // this correctly handles empty this return (iMin.x <= rhs.x && rhs.x <= iMax.x && iMin.y <= rhs.y && rhs.y <= iMax.y); } //! Does rectangle contain other rectangle? bool Rect::contains(const Rect &rhs) const { if (rhs.isEmpty()) return true; if (isEmpty()) return false; return (iMin.x <= rhs.iMin.x && rhs.iMax.x <= iMax.x && iMin.y <= rhs.iMin.y && rhs.iMax.y <= iMax.y); } //! Does rectangle intersect other rectangle? bool Rect::intersects(const Rect &rhs) const { if (isEmpty() || rhs.isEmpty()) return false; return (iMin.x <= rhs.iMax.x && rhs.iMin.x <= iMax.x && iMin.y <= rhs.iMax.y && rhs.iMin.y <= iMax.y); } //! Enlarge rectangle to contain point. void Rect::addPoint(const Vector &rhs) { if (isEmpty()) { iMin = rhs; iMax = rhs; } else { if (rhs.x > iMax.x) iMax.x = rhs.x; else if (rhs.x < iMin.x) iMin.x = rhs.x; if (rhs.y > iMax.y) iMax.y = rhs.y; else if (rhs.y < iMin.y) iMin.y = rhs.y; } } //! Enlarge rectangle to contain rhs rectangle. /*! Does nothing if \a rhs is empty. */ void Rect::addRect(const Rect &rhs) { if (isEmpty()) { iMin = rhs.iMin; iMax = rhs.iMax; } else if (!rhs.isEmpty()) { if (rhs.iMax.x > iMax.x) iMax.x = rhs.iMax.x; if (rhs.iMin.x < iMin.x) iMin.x = rhs.iMin.x; if (rhs.iMax.y > iMax.y) iMax.y = rhs.iMax.y; if (rhs.iMin.y < iMin.y) iMin.y = rhs.iMin.y; } } //! Clip rectangle to fit inside \a cbox. /*! Does nothing if either rectangle is empty. */ void Rect::clipTo(const Rect &cbox) { if (isEmpty() || cbox.isEmpty()) return; if (!intersects(cbox)) { // make box empty iMin = Vector(1, 0); iMax = Vector(-1, 0); } else { if (iMin.x < cbox.iMin.x) iMin.x = cbox.iMin.x; if (iMin.y < cbox.iMin.y) iMin.y = cbox.iMin.y; if (iMax.x > cbox.iMax.x) iMax.x = cbox.iMax.x; if (iMax.y > cbox.iMax.y) iMax.y = cbox.iMax.y; } } /*! Returns false if the distance between the box and v is smaller than \a bound. Often returns true if their distance is larger than \a bound. */ bool Rect::certainClearance(const Vector &v, double bound) const { return ((iMin.x - v.x) >= bound || (v.x - iMax.x) >= bound || (iMin.y - v.y) >= bound || (v.y - iMax.y) >= bound); } //! Output operator for Rect. Stream &ipe::operator<<(Stream &stream, const Rect &rhs) { return stream << rhs.bottomLeft() << " " << rhs.topRight(); } // -------------------------------------------------------------------- /*! \class ipe::Line \ingroup geo \brief A directed line. */ //! Construct a line from \a p with direction \a dir. /*! Asserts unit length of \a dir. */ Line::Line(const Vector &p, const Vector &dir) { assert(sq(dir.sqLen() - 1.0) < 1e-10); iP = p; iDir = dir; } //! Construct a line through two points. Line Line::through(const Vector &p, const Vector &q) { assert(q != p); return Line(p, (q - p).normalized()); } //! Result is > 0, = 0, < 0 if point lies to the left, on, to the right. double Line::side(const Vector &p) const { return dot(normal(), p - iP); } //! Returns distance between line and \a v. double Line::distance(const Vector &v) const { Vector diff = v - iP; return (diff - dot(diff, iDir) * iDir).len(); } inline double cross(const Vector &v1, const Vector &v2) { return v1.x * v2.y - v1.y * v2.x; } static bool line_intersection(double &lambda, const Line &l, const Line &m) { double denom = cross(m.dir(), l.dir()); if (denom == 0.0) return false; lambda = cross(l.iP - m.iP, m.dir()) / denom; return true; } //! Does this line intersect \a line? If so, computes intersection point. bool Line::intersects(const Line &line, Vector &pt) { double lambda; if (line_intersection(lambda, *this, line)) { pt = iP + lambda * iDir; return true; } return false; } //! Orthogonally project point \a v onto the line. Vector Line::project(const Vector &v) const { double dx = dot(iDir, v - iP); return iP + dx * iDir; } // -------------------------------------------------------------------- /*! \class ipe::Segment \ingroup geo \brief A directed line segment. */ /*! Returns distance between segment and point \a v, but may just return \a bound when its larger than \a bound. */ double Segment::distance(const Vector &v, double bound) const { if (Rect(iP, iQ).certainClearance(v, bound)) return bound; return distance(v); } /*! Returns distance between segment and point \a v */ double Segment::distance(const Vector &v) const { Vector dir = iQ - iP; Vector udir; double len = dir.factorize(udir); double dx = dot(udir, v - iP); if (dx <= 0) return (v - iP).len(); if (dx >= len) return (v - iQ).len(); return (v - (iP + dx * udir)).len(); } /*! Project point \a v orthogonally on segment. Returns false if the point falls outside the segment. */ bool Segment::project(const Vector &v, Vector &projection) const { Vector dir = iQ - iP; Vector udir; double len = dir.factorize(udir); double dx = dot(udir, v - iP); if (dx <= 0 || dx >= len) return false; projection = iP + dx * udir; return true; } //! Compute intersection point. Return \c false if segs don't intersect. bool Segment::intersects(const Segment &seg, Vector &pt) const { if (iP == iQ || seg.iP == seg.iQ) return false; if (!Rect(iP, iQ).intersects(Rect(seg.iP, seg.iQ))) return false; if (!line().intersects(seg.line(), pt)) return false; // have intersection point, check whether it's on both segments. Vector dir = iQ - iP; Vector dir1 = seg.iQ - seg.iP; return (dot(pt - iP, dir) >= 0 && dot(pt - iQ, dir) <= 0 && dot(pt - seg.iP, dir1) >= 0 && dot(pt - seg.iQ, dir1) <= 0); } //! Compute intersection point. Return \c false if no intersection. bool Segment::intersects(const Line &l, Vector &pt) const { if (!line().intersects(l, pt)) return false; // have intersection point, check whether it's on the segment Vector dir = iQ - iP; return (dot(pt - iP, dir) >= 0 && dot(pt - iQ, dir) <= 0); } //! Snap mouse position to this segment. /*! If distance between \a mouse and the segment is less than \a bound, then set \a pos to the point on the segment, \a bound to the distance, and return true. */ bool Segment::snap(const Vector &mouse, Vector &pos, double &bound) const { if (Rect(iP, iQ).certainClearance(mouse, bound)) return false; Vector v; if (project(mouse, v)) { double d = (mouse - v).len(); if (d < bound) { pos = v; bound = d; return true; } return false; } else return iQ.snap(mouse, pos, bound); } // -------------------------------------------------------------------- /*! \class ipe::Linear \ingroup geo \brief Linear transformation in the plane (2x2 matrix). */ //! Create matrix representing a rotation by angle. Linear::Linear(Angle angle) { a[0] = cos(angle); a[1] = sin(angle); a[2] = -a[1]; a[3] = a[0]; } //! Parse string. Linear::Linear(String str) { Lex lex(str); lex >> a[0] >> a[1] >> a[2] >> a[3]; } //! Return inverse. Linear Linear::inverse() const { double t = determinant(); assert(t != 0); t = 1.0/t; return Linear(a[3]*t, -a[1]*t, -a[2]*t, a[0]*t); } //! Output operator for Linear. Stream &ipe::operator<<(Stream &stream, const Linear &rhs) { return stream << rhs.a[0] << " " << rhs.a[1] << " " << rhs.a[2] << " " << rhs.a[3]; } // -------------------------------------------------------------------- /*! \class ipe::Matrix \ingroup geo \brief Homogeneous transformation in the plane. */ //! Parse string. Matrix::Matrix(String str) { Lex lex(str); lex >> a[0] >> a[1] >> a[2] >> a[3] >> a[4] >> a[5]; } //! Return inverse. Matrix Matrix::inverse() const { double t = determinant(); assert(t != 0); t = 1.0/t; return Matrix(a[3]*t, -a[1]*t, -a[2]*t, a[0]*t, (a[2]*a[5]-a[3]*a[4])*t, -(a[0]*a[5]-a[1]*a[4])*t); } //! Output operator for Matrix. Stream &ipe::operator<<(Stream &stream, const Matrix &rhs) { return stream << rhs.a[0] << " " << rhs.a[1] << " " << rhs.a[2] << " " << rhs.a[3] << " " << rhs.a[4] << " " << rhs.a[5]; } // -------------------------------------------------------------------- /*! \class ipe::Bezier \ingroup geo \brief A cubic Bezier spline. */ inline Vector midpoint(const Vector& p, const Vector& q) { return 0.5 * (p + q); } inline Vector thirdpoint(const Vector& p, const Vector& q) { return (1.0/3.0) * ((2 * p) + q); } //! Return point on curve with parameter \a t (from 0.0 to 1.0). Vector Bezier::point(double t) const { double t1 = 1.0 - t; return t1 * t1 * t1 * iV[0] + 3 * t * t1 * t1 * iV[1] + 3 * t * t * t1 * iV[2] + t * t * t * iV[3]; } //! Return tangent direction of curve at parameter \a t (from 0.0 to 1.0). /*! The returned vector is not normalized. */ Vector Bezier::tangent(double t) const { double tt = 1.0 - t; Vector p = tt * iV[0] + t * iV[1]; Vector q = tt * iV[1] + t * iV[2]; Vector r = tt * iV[2] + t * iV[3]; p = tt * p + t * q; q = tt * q + t * r; r = tt * p + t * q; return r - p; } /*! Returns true if the Bezier curve is nearly identical to the line segment iV[0]..iV[3]. */ bool Bezier::straight(double precision) const { if (iV[0] == iV[3]) { return ((iV[1] - iV[0]).len() < precision && (iV[2] - iV[0]).len() < precision); } else { Line l = Line::through(iV[0], iV[3]); double d1 = l.distance(iV[1]); double d2 = l.distance(iV[2]); return (d1 < precision && d2 < precision); } } //! Subdivide this Bezier curve in the middle. void Bezier::subdivide(Bezier &l, Bezier &r) const { Vector h; l.iV[0] = iV[0]; l.iV[1] = 0.5 * (iV[0] + iV[1]); h = 0.5 * (iV[1] + iV[2]); l.iV[2] = 0.5 * (l.iV[1] + h); r.iV[2] = 0.5 * (iV[2] + iV[3]); r.iV[1] = 0.5 * (h + r.iV[2]); r.iV[0] = 0.5 * (l.iV[2] + r.iV[1]); l.iV[3] = r.iV[0]; r.iV[3] = iV[3]; } //! Approximate by a polygonal chain. /*! \a result must be empty when calling this. */ void Bezier::approximate(double precision, std::vector &result) const { if (straight(precision)) { result.push_back(iV[3]); } else { Bezier l, r; subdivide(l, r); l.approximate(precision, result); r.approximate(precision, result); } } //! Convert a quadratic Bezier-spline to a cubic one. /*! The quadratic Bezier-spline with control points p0, p1, p2 is identical to the cubic Bezier-spline with control points q0 = p0, q1 = (2p1 + p0)/3, q2 = (2p1 + p2)/3, q3 = p2. */ Bezier Bezier::quadBezier(const Vector &p0, const Vector &p1, const Vector &p2) { Vector q1 = thirdpoint(p1, p0); Vector q2 = thirdpoint(p1, p2); return Bezier(p0, q1, q2, p2); } //! Convert an old-style Ipe B-spline to a series of Bezier splines. /*! For some reason lost in the mist of time, this was the definition of splines in Ipe for many years. It doesn't use knots. The first and last control point are simply given multiplicity 3. Bezier splines are appended to \a result. */ void Bezier::oldSpline(int n, const Vector *v, std::vector &result) { Vector p0, p1, p2, p3, q0, q1, q2, q3; // First segment (p1 = p2 = p0 => q1 = q2 = q0 = p0) p0 = v[0]; p3 = v[1]; q3 = midpoint(thirdpoint(p0, p3), p0); result.push_back(Bezier(p0, p0, p0, q3)); if (n > 2) { // Second segment p1 = v[0]; p2 = v[1]; p3 = v[2]; q0 = q3; // from previous q1 = thirdpoint(p1, p2); q2 = thirdpoint(p2, p1); q3 = midpoint(thirdpoint(p2, p3), q2); result.push_back(Bezier(q0, q1, q2, q3)); // create n - 3 segments for (int i = 0; i < n - 3; ++i) { p0 = v[i]; p1 = v[i + 1]; p2 = v[i + 2]; p3 = v[i + 3]; q0 = q3; // from previous // q0 = midpoint(thirdpoint(p1, p0), q1); // the real formula q1 = thirdpoint(p1, p2); q2 = thirdpoint(p2, p1); q3 = midpoint(thirdpoint(p2, p3), q2); result.push_back(Bezier(q0, q1, q2, q3)); } } // Second to last segment p1 = v[n-2]; p2 = v[n-1]; p3 = v[n-1]; q0 = q3; // from previous q1 = thirdpoint(p1, p2); q2 = thirdpoint(p2, p1); q3 = midpoint(p3, q2); result.push_back(Bezier(q0, q1, q2, q3)); // Last segment (p1 = p2 = p3 => q1 = q2 = q3 = p3) result.push_back(Bezier(q3, p3, p3, p3)); } //! Convert a clamped uniform B-spline to a series of Bezier splines. /*! See Thomas Sederberg, Computer-Aided Geometric Design, Chapter 6. In polar coordinates, a control point is defined by three knots, so n control points need n + 2 knots. To clamp the spline to the first and last control point, the first and last knot are repeated three times. This leads to k knot intervals and the knot sequence [0, 0, 0, 1, 2, 3, 4, 5, 6, ..., k-2, k-1, k, k, k] There are k + 5 = n + 2 knots in this sequence, so k = n-3 is the number of knot intervals and therefore the number of output Bezier curves. If n = 4, the knot sequence is [0, 0, 0, 1, 1, 1] and the result is simply the Bezier curve on the four control points. When n in {2, 3}, returns a single Bezier curve that is a segment or quadratic Bezier spline. This is different from the behaviour of the "old" Ipe splines. Bezier splines are appended to \a result. */ void Bezier::spline(int n, const Vector *v, std::vector &result) { if (n == 2) { result.push_back(Bezier(v[0], v[0], v[1], v[1])); } else if (n == 3) { result.push_back(quadBezier(v[0], v[1], v[2])); } else if (n == 4) { result.push_back(Bezier(v[0], v[1], v[2], v[3])); } else if (n == 5) { // Given are [0,0,0], [0,0,1], [0,1,2], [1,2,2], [2,2,2] // Interval 0-1: [0,0,0], [0,0,1], [0,1,1], [1,1,1] Vector q0 = v[0]; // [0,0,0] Vector q1 = v[1]; // [0,0,1] Vector q2 = midpoint(q1, v[2]); // [0,1,1] = 1/2 [0,1,0] + 1/2 [0,1,2] Vector r = midpoint(v[2], v[3]); // [1,1,2] = 1/3 [0,1,2] + 1/2 [2,1,2] Vector q3 = midpoint(q2, r); // [1,1,1] = 1/2 [1,0,1] + 1/2 [1,2,1] result.push_back(Bezier(q0, q1, q2, q3)); // Interval 1-2: [1,1,1], [1,1,2], [1,2,2], [2,2,2] result.push_back(Bezier(q3, r, v[3], v[4])); } else { int k = n-3; // Interval 0-1: [0,0,0], [0,0,1], [0,1,1], [1,1,1] Vector q0 = v[0]; // [0,0,0] Vector q1 = v[1]; // [0,0,1] Vector q2 = midpoint(q1, v[2]); // [0,1,1] = 1/2 [0,1,0] + 1/2 [0,1,2] Vector r = thirdpoint(v[2], v[3]); // [1,2,1] = 2/3 [0,1,2] + 1/3 [3,1,2] Vector q3 = midpoint(q2, r); // [1,1,1] = 1/2 [1,0,1] + 1/2 [1,2,1] result.push_back(Bezier(q0, q1, q2, q3)); for (int i = 1; i < k-2; ++i) { // Interval i-i+1: [i,i,i], [i,i,i+1], [i,i+1,i+1], [i+1,i+1,i+1] q0 = q3; // [i,i,i] q1 = r; // [i,i,i+1] // [i,i+1,i+1] = 1/2 [i,i+1,i] + 1/2 [i, i+1, i+2] q2 = midpoint(q1, v[i+2]); // [i+1,i+1,i+2] = 2/3 [i,i+1,i+2] + [i+3,i+1,i+2] r = thirdpoint(v[i+2], v[i+3]); // [i+1,i+1,i+1] = 1/2 [i+1,i+1,i] + 1/2 [i+1,i+1,i+2] q3 = midpoint(q2, r); result.push_back(Bezier(q0, q1, q2, q3)); } // Interval (k-2)-(k-1): // [k-2,k-2,k-2], [k-2,k-2,k-1], [k-2,k-1,k-1], [k-1,k-1,k-1] q0 = q3; q1 = r; // [k-2,k-2,k-1] // [k-2,k-1,k-1] = 1/2 [k-2,k-1,k-2] + 1/2 [k-2,k-1,k] q2 = midpoint(q1, v[k]); // [k-1,k-1,k] = 1/2 [k-2,k-1,k] + 1/2 [k,k-1,k] r = midpoint(v[k], v[k+1]); // [k-1,k-1,k-1] = 1/2 [k-1,k-1,k-2] + 1/2 [k-1,k-1,k] q3 = midpoint(q2, r); result.push_back(Bezier(q0, q1, q2, q3)); // Interval (k-1)-k: [k-1,k-1,k-1], [k-1,k-1,k], [k-1,k,k], [k,k,k] q0 = q3; q1 = r; q2 = v[n-2]; // [k-1,k,k] q3 = v[n-1]; // [k,k,k] result.push_back(Bezier(q0, q1, q2, q3)); } } //! Convert a closed uniform cubic B-spline to a series of Bezier splines. /*! Bezier splines are appended to \a result. */ void Bezier::closedSpline(int n, const Vector *v, std::vector &result) { for (int i = 0; i < n; ++i) { Vector p0 = v[i % n]; // [0, 1, 2] Vector p1 = v[(i+1) % n]; // [1, 2, 3] Vector p2 = v[(i+2) % n]; // [2, 3, 4] Vector p3 = v[(i+3) % n]; // [3, 4, 5] Vector r = thirdpoint(p1, p0); // [1, 2, 2] Vector u = thirdpoint(p2, p3); // [3, 3, 4] Vector q1 = thirdpoint(p1, p2); // [2, 2, 3] Vector q2 = thirdpoint(p2, p1); // [2, 3, 3] Vector q0 = midpoint(r, q1); // [2, 2, 2] Vector q3 = midpoint(u, q2); // [3, 3, 3] result.push_back(Bezier(q0, q1, q2, q3)); } } //! Return distance to Bezier spline. /*! But may just return \a bound if actual distance is larger. The Bezier spline is approximated to a precision of 1.0, and the distance to the approximation is returned. */ double Bezier::distance(const Vector &v, double bound) { Rect box; box.addPoint(iV[0]); box.addPoint(iV[1]); box.addPoint(iV[2]); box.addPoint(iV[3]); if (box.certainClearance(v, bound)) return bound; std::vector approx; approximate(1.0, approx); Vector cur = iV[0]; double d = bound; double d1; for (std::vector::const_iterator it = approx.begin(); it != approx.end(); ++it) { if ((d1 = Segment(cur, *it).distance(v, d)) < d) d = d1; cur = *it; } return d; } //! Return a tight bounding box (accurate to within 0.5). Rect Bezier::bbox() const { Rect box(iV[0]); std::vector approx; approximate(0.5, approx); for (std::vector::const_iterator it = approx.begin(); it != approx.end(); ++it) { box.addPoint(*it); } return Rect(box.bottomLeft() - Vector(0.5, 0.5), box.topRight() + Vector(0.5, 0.5)); } //! Find (approximately) nearest point on Bezier spline. /*! Find point on spline nearest to \a v, but only if it is closer than \a bound. If a point is found, sets \a t to the parameter value and \a pos to the actual point, and returns true. */ bool Bezier::snap(const Vector &v, double &t, Vector &pos, double &bound) const { Rect box(iV[0], iV[1]); box.addPoint(iV[2]); box.addPoint(iV[3]); if (box.certainClearance(v, bound)) return false; // handle straight ends of B-splines if (iV[0] != iV[1] && iV[1] == iV[2] && iV[2] == iV[3]) { Vector prj; double d; if (Segment(iV[0], iV[3]).project(v, prj) && (d = (v - prj).len()) < bound) { bound = d; pos = prj; t = 1.0 - pow((pos - iV[3]).len()/(iV[0] - iV[3]).len(), 1.0/3.0); return true; } // endpoints handled by code below } if (iV[0] == iV[1] && iV[1] == iV[2] && iV[2] != iV[3]) { Vector prj; double d; if (Segment(iV[3], iV[0]).project(v, prj) && (d = (v - prj).len()) < bound) { bound = d; pos = prj; t = 1.0 - pow((pos - iV[0]).len()/(iV[3] - iV[0]).len(), 1.0/3.0); return true; } // endpoints handled by code below } if (straight(1.0)) { Vector prj; if (iV[0] != iV[3] && Segment(iV[0], iV[3]).project(v, prj)) { double t1 = (prj - iV[0]).len() / (iV[3] - iV[0]).len(); Vector u = point(t1); double d = (v - u).len(); if (d < bound) { t = t1; bound = d; pos = u; return true; } else return false; } else { bool v0 = iV[0].snap(v, pos, bound); bool v1 = iV[3].snap(v, pos, bound); if (v0) t = 0.0; if (v1) t = 1.0; return v0 || v1; } } else { Bezier l, r; subdivide(l, r); bool p1 = l.snap(v, t, pos, bound); bool p2 = r.snap(v, t, pos, bound); if (p1 || p2) t = 0.5 * t; if (p2) t = t + 0.5; return p1 || p2; } } // -------------------------------------------------------------------- /* Determines intersection point(s) of two cubic Bezier-Splines. * The found intersection points are stored in the vector intersections. */ static void intersectBeziers(std::vector &intersections, const Bezier &a, const Bezier &b) { /* Recursive approximation procedure to find intersections: * If the bounding boxes of two Beziers overlap, both are subdivided, * each one into two partial Beziers. * In the next recursion steps, it is checked if the bounding boxes * of the partial Beziers overlap. If they do, they are subdivided * again and so on, until a special precision is achieved: * Then the Beziers are converted to Segments and checked for intersection. */ Rect abox(a.iV[0], a.iV[1]); abox.addPoint(a.iV[2]); abox.addPoint(a.iV[3]); Rect bbox(b.iV[0], b.iV[1]); bbox.addPoint(b.iV[2]); bbox.addPoint(b.iV[3]); if (!abox.intersects(bbox)) return; if (a.straight(BEZIER_INTERSECT_PRECISION) && b.straight(BEZIER_INTERSECT_PRECISION)) { Segment as = Segment(a.iV[0], a.iV[3]); Segment bs = Segment(b.iV[0], b.iV[3]); Vector p; if (as.intersects(bs, p)) intersections.push_back(p); } else { Bezier leftA, rightA, leftB, rightB; a.subdivide(leftA, rightA); b.subdivide(leftB, rightB); intersectBeziers(intersections, leftA, leftB); intersectBeziers(intersections, rightA, leftB); intersectBeziers(intersections, leftA, rightB); intersectBeziers(intersections, rightA, rightB); } } //! Compute intersection points of Bezier with Line. void Bezier::intersect(const Line &l, std::vector &result) const { double sgn = l.side(iV[0]); if (sgn < 0 && l.side(iV[1]) < 0 && l.side(iV[2]) < 0 && l.side(iV[3]) < 0) return; if (sgn > 0 && l.side(iV[1]) > 0 && l.side(iV[2]) > 0 && l.side(iV[3]) > 0) return; if (straight(BEZIER_INTERSECT_PRECISION)) { Vector p; if (Segment(iV[0], iV[3]).intersects(l, p)) result.push_back(p); } else { Bezier leftA, rightA; subdivide(leftA, rightA); leftA.intersect(l, result); rightA.intersect(l, result); } } //! Compute intersection points of Bezier with Segment. void Bezier::intersect(const Segment &s, std::vector &result) const { // convert Segment to Bezier and use Bezier-Bezier-intersection // this works well since the segment is immediately "straight" intersectBeziers(result, *this, Bezier(s.iQ, s.iQ, s.iP, s.iP)); } //! Compute intersection points of Bezier with Bezier. void Bezier::intersect(const Bezier &b, std::vector &result) const { intersectBeziers(result, *this, b); } // -------------------------------------------------------------------- /*! \class ipe::Arc \ingroup geo \brief An arc of an ellipse. The ellipse is represented using the matrix that transforms the unit circle x^2 + y^2 = 1 to the desired ellipse. The arc coordinate system is the coordinate system of this unit circle. A full ellipse is described by iAlpha = 0, iBeta = IpeTwoPi. An elliptic arc is the image of the circular arc from iAlpha to iBeta (in increasing angle in arc coordinate system). */ //! Construct arc for ellipse defined by m, from begp to endp. /*! This assumes that \a m has been correctly computed such that \a begb and \a endp already lie on the ellipse. */ Arc::Arc(const Matrix &m, const Vector &begp, const Vector &endp) { iM = m; Matrix inv = m.inverse(); iAlpha = (inv * begp).angle(); iBeta = (inv * endp).angle(); } //! This doesn't really compute the distance, but a reasonable approximation. double Arc::distance(const Vector &v, double bound) const { Vector pos; Angle angle; return distance(v, bound, pos, angle); } /*! Like distance(), but sets pos to point on arc and angle to its angle in arc coordinates. \a angle and \a pos are not modified if result is larger than bound. */ double Arc::distance(const Vector &v, double bound, Vector &pos, Angle &angle) const { Matrix inv1 = iM.inverse(); Vector v1 = inv1 * v; Vector pos1 = iM * v1.normalized(); double d = (v - pos1).len(); if (isEllipse()) { if (d < bound) { bound = d; pos = pos1; angle = v1.angle(); } } else { // elliptic arc if (d < bound && v1.angle().liesBetween(iAlpha, iBeta)) { bound = d; pos = pos1; angle = v1.angle(); } pos1 = iM * Vector(iAlpha); d = (v - pos1).len(); if (d < bound) { bound = d; pos = pos1; angle = iAlpha; } pos1 = iM * Vector(iBeta); d = (v - pos1).len(); if (d < bound) { bound = d; pos = pos1; angle = iBeta; } } return bound; } //! Return a tight bounding box. Rect Arc::bbox() const { Rect box; // add begin and end point box.addPoint(iM * Vector(iAlpha)); box.addPoint(iM * Vector(iBeta)); Linear inv = iM.linear().inverse(); bool ell = isEllipse(); Angle alpha = (inv * Vector(0,1)).angle() - IpeHalfPi; if (ell || alpha.liesBetween(iAlpha, iBeta)) box.addPoint(iM * Vector(alpha)); alpha = (inv * Vector(0,-1)).angle() - IpeHalfPi; if (ell || alpha.liesBetween(iAlpha, iBeta)) box.addPoint(iM * Vector(alpha)); alpha = (inv * Vector(1,0)).angle() - IpeHalfPi; if (ell || alpha.liesBetween(iAlpha, iBeta)) box.addPoint(iM * Vector(alpha)); alpha = (inv * Vector(-1,0)).angle() - IpeHalfPi; if (ell || alpha.liesBetween(iAlpha, iBeta)) box.addPoint(iM * Vector(alpha)); return box; } // -------------------------------------------------------------------- //! Compute intersection points of Arc with Line. void Arc::intersect(const Line &l, std::vector &result) const { Matrix m = iM.inverse(); Vector p = m * l.iP; Vector d = (m.linear() * l.dir()).normalized(); // solve quadratic equation double b = 2 * dot(p, d); double c = dot(p, p) - 1.0; double D = b*b - 4*c; if (D < 0) return; double sD = (b < 0) ? -sqrt(D) : sqrt(D); double t1 = -0.5 * (b + sD); Vector v = p + t1 * d; if (v.angle().liesBetween(iAlpha, iBeta)) result.push_back(iM * v); if (D > 0) { v = p + (c/t1) * d; if (v.angle().liesBetween(iAlpha, iBeta)) result.push_back(iM * v); } } //! Compute intersection points of Arc with Segment. void Arc::intersect(const Segment &s, std::vector &result) const { std::vector pt; intersect(s.line(), pt); Vector dir = s.iQ - s.iP; for (int i = 0; i < size(pt); ++i) { // check whether it's on the segment Vector v = pt[i]; if (dot(v - s.iP, dir) >= 0 && dot(v - s.iQ, dir) <= 0) result.push_back(v); } } //! Compute intersection points of Arc with Arc. void Arc::intersect(const Arc &a, std::vector &result) const { /* Recursive approximation procedure to find intersections: * If the bounding boxes of two Arcs overlap, both are subdivided, * each one into two partial Arcs. * In the next recursion steps, it is checked if the bounding boxes * of the partial Arcs overlap. If they do, they are subdivided * again and so on, until a special precision is achieved. */ const double PRECISION = 0.05; // 0.05 is about ~2.8647 degrees if (!bbox().intersects(a.bbox())) return; if (straight(PRECISION) && a.straight(PRECISION)) { intersect(Segment(a.beginp(), a.endp()), result); } else { Arc al, ar; subdivide(al, ar); Arc bl, br; a.subdivide(bl, br); al.intersect(bl, result); al.intersect(br, result); ar.intersect(bl, result); ar.intersect(br, result); } } //! Compute intersection points of Arc with Bezier. void Arc::intersect(const Bezier &b, std::vector &result) const { /* Recursive approximation procedure to find intersections: If the * bounding boxes of the Bezier and the Arc overlap, both are * subdivided, the Bezier into two Beziers and the Arc into two * Arcs. In the next recursion steps, it is checked if a bounding * box of a partial Bezier overlap one of a partial Arc. If they * overlap, they are subdivided again and so on, until a special * precision is achieved. */ const double PRECISION = 0.05; // 0.05 is about ~2.8647 degrees Rect bboxB(b.iV[0], b.iV[1]); bboxB.addPoint(b.iV[2]); bboxB.addPoint(b.iV[3]); if (!bbox().intersects(bboxB)) return; if (b.straight(PRECISION)) { intersect(Segment(b.iV[0], b.iV[3]), result); } else { // is it really useful to divide the arc? // the hope is to achieve emptiness of intersection more quickly Arc al, ar; subdivide(al, ar); Bezier bl, br; b.subdivide(bl, br); al.intersect(bl, result); al.intersect(br, result); ar.intersect(bl, result); ar.intersect(br, result); } } //! Subdivide this arc into two. void Arc::subdivide(Arc &l, Arc &r) const { if (iAlpha == 0.0 && iBeta == IpeTwoPi) { l = Arc(iM, Angle(0), Angle(IpePi)); r = Arc(iM, Angle(IpePi), Angle(IpeTwoPi)); } else { // delta is length of arc double delta = Angle(iBeta).normalize(iAlpha) - iAlpha; Angle gamma(iAlpha + delta/2); l = Arc(iM, iAlpha, gamma); r = Arc(iM, gamma, iBeta); } } /*! Returns true if the difference between start- and endangle is less * than precision. */ bool Arc::straight(const double precision) const { if (iAlpha == 0.0 && iBeta == IpeTwoPi) return false; return Angle(iBeta).normalize(iAlpha) - iAlpha < precision; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipebitmap_win.cpp0000644000175000017500000000770713561570220017635 0ustar otfriedotfried// ipebitmap_win.cpp /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebitmap.h" #include "ipeutils.h" #include #include #include using namespace ipe; // -------------------------------------------------------------------- typedef IStream* WINAPI (*LPFNSHCREATEMEMSTREAM)(const BYTE *, UINT); static bool libLoaded = false; static LPFNSHCREATEMEMSTREAM pSHCreateMemStream = nullptr; bool dctDecode(Buffer dctData, Buffer pixelData) { if (!libLoaded) { libLoaded = true; HMODULE hDll = LoadLibraryA("shlwapi.dll"); if (hDll) pSHCreateMemStream = (LPFNSHCREATEMEMSTREAM) GetProcAddress(hDll, (LPCSTR) 12); } if (!pSHCreateMemStream) return false; IStream *stream = pSHCreateMemStream((const BYTE *) dctData.data(), dctData.size()); if (!stream) return false; Gdiplus::Bitmap *bitmap = Gdiplus::Bitmap::FromStream(stream); if (bitmap->GetLastStatus() != Gdiplus::Ok) { delete bitmap; stream->Release(); return false; } int w = bitmap->GetWidth(); int h = bitmap->GetHeight(); // ipeDebug("dctDecode: %d x %d format %x", w, h, bitmap->GetPixelFormat()); Gdiplus::BitmapData* bitmapData = new Gdiplus::BitmapData; bitmapData->Scan0 = pixelData.data(); bitmapData->Stride = 4 * w; bitmapData->Width = w; bitmapData->Height = h; bitmapData->PixelFormat = PixelFormat32bppARGB; Gdiplus::Rect rect(0, 0, w, h); bitmap->LockBits(&rect, Gdiplus::ImageLockModeRead | Gdiplus::ImageLockModeUserInputBuf, PixelFormat32bppARGB, bitmapData); bitmap->UnlockBits(bitmapData); delete bitmapData; delete bitmap; stream->Release(); return true; } // -------------------------------------------------------------------- // The graphics file formats supported by GDI+ are // BMP, GIF, JPEG, PNG, TIFF. Bitmap Bitmap::readPNG(const char *fname, Vector &dotsPerInch, const char * &errmsg) { // load without color correction Gdiplus::Bitmap *bitmap = Gdiplus::Bitmap::FromFile(String(fname).w().data(), FALSE); if (bitmap->GetLastStatus() != Gdiplus::Ok) { delete bitmap; return Bitmap(); } dotsPerInch = Vector(bitmap->GetHorizontalResolution(), bitmap->GetVerticalResolution()); int w = bitmap->GetWidth(); int h = bitmap->GetHeight(); Buffer pixelData(4 * w * h); Gdiplus::BitmapData* bitmapData = new Gdiplus::BitmapData; bitmapData->Scan0 = pixelData.data(); bitmapData->Stride = 4 * w; bitmapData->Width = w; bitmapData->Height = h; bitmapData->PixelFormat = PixelFormat32bppARGB; Gdiplus::Rect rect(0, 0, w, h); bitmap->LockBits(&rect, Gdiplus::ImageLockModeRead | Gdiplus::ImageLockModeUserInputBuf, PixelFormat32bppARGB, bitmapData); Bitmap bm(w, h, Bitmap::ENative, pixelData); bitmap->UnlockBits(bitmapData); delete bitmapData; delete bitmap; return bm; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipeobject.cpp0000644000175000017500000003262113561570220016743 0ustar otfriedotfried// -------------------------------------------------------------------- // The Ipe object type // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /*! \mainpage The Ipe library documentation The Ipe library ("Ipelib") provides the geometric primitives and implements all the geometric objects that appear in Ipe. Many tasks related to modifying an Ipe document are actually performed by Ipelib. For instance, the ipetoipe program consists of only a few calls to Ipelib. Ipelib can easily be used by C++ programs to read, write, and modify Ipe documents. Compiling Ipelib is easy, it requires only the standard C++ library (including the STL), and the zlib compression library. Nearly all symbols in Ipelib are in the \ref ipe "ipe" namespace, those that aren't start with the letters "Ipe". Before using Ipelib in your own program, make sure to initialize the library by calling ipe::Platform::initLib(). Many of the Ipelib classes are also made available as Lua objects. \subpage lua describes the Lua bindings to Ipelib, to ipeui, and to the Ipe program itself. The Ipe program itself is mostly written in Lua and uses these Lua bindings. On Unix, all filenames passed to Ipelib are assumed to be in the local system's encoding. On Windows, all filenames passed to Ipelib are assumed to be UTF-8. All Lua strings are assumed to be UTF-8 (filenames are converted by the ipelua bindings). \subpage ipelets explains how to write ipelets, that is, extensions to Ipe. Ipelets are either written in Lua or in C++ (using a small Lua wrapper to describe the ipelet). C++ ipelets have to be linked with Ipelib to access and modify Ipe objects. The classes documented here are implemented in five different libraries: \li \e libipe is the core Ipelib library. It implements geometric primitives, Ipe objects, and the Ipe document. However, it doesn't know anything about drawing to the screen or about the Lua bindings. \li \e libipecairo implements the \ref cairo "Ipe cairo module". It provides drawing of Ipe objects using the Cairo library. \li \e libipelua implements the \ref lua "Lua bindings" for Ipelib. If installed properly, it can be loaded dynamically from Lua using \c require. It is also used by ipescript. \li \e libipecanvas implements the \ref qtcanvas "Ipe canvas module". It provides a widget for displaying and editing Ipe objects. \li \e libipeui implements Lua bindings for user interfaces. This library does not depend on any other Ipe component, and can be used for other Lua projects. Here is an annotated list of the modules: \li \ref base : Some basic datatypes: ipe::String, ipe::Buffer, ipe::Stream, ipe::Fixed \li \ref geo : Geometric types and linear algebra: ipe::Vector, ipe::Matrix, ipe::Line, ipe::Segment, ipe::Arc, ipe::Bezier, ipe::Shape. \li \ref attr : Attributes such as ipe::Color, ipe::Kind, ipe::Attribute \li \ref obj : The five ipe::Object types: ipe::Group, ipe::Path, ipe::Text, ipe::Image, and ipe::Reference \li \ref doc : The Ipe document: ipe::Document, ipe::Page, and ipe::StyleSheet \li \ref high : Some utility classes: ipe::ImlParser, ipe::BitmapFinder, etc. \li \ref ipelet : The ipe::Ipelet interface \li \ref cairo : Classes to draw Ipe objects on a Cairo surface: ipe::CairoPainter, ipe::Fonts, ipe::Face \li \ref canvas : A widget ipe::Canvas to display Ipe objects, and tools for this canvas: ipe::PanTool, ipe::SelectTool, ipe::TransformTool. Finally, here is list of the pages describing Lua bindings: \li \ref luageo Lua bindings for basic geometric objects \li \ref luaobj Lua bindings for Ipe objects \li \ref luapage Lua bindings for documents, pages, and stylesheets \li \ref luaipeui Lua bindings for dialogs, menus, etc. \li \ref luaipe Lua bindings for the Ipe program itself. */ /* namespace ipe brief Ipe library namespace Nearly all symbols defined by the Ipe library and the Ipe-Cairo interface are in the namespace ipe. (Other symbols all start with the letters "Ipe" (or "ipe" or "IPE"). */ // -------------------------------------------------------------------- /*! \defgroup obj Ipe Objects \brief The Ipe object model. This module deals with the actual objects inside an Ipe document. All Ipe objects are derived from Object. */ #include "ipegeo.h" #include "ipeobject.h" #include "ipepainter.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::Object \ingroup obj \brief Base class for all Ipe objects, composite or leaf. All objects are derived from this class. It provides functionality common to all objects, and carries the standard attributes. All Object's provide a constant time copy constructor (and a virtual Object::clone() method). Objects of non-constant size realize this by separating the implementation and using reference counting. In particular, copying a composite object does not create new copies of the components. Object has only three attributes: the transformation matrix, the pinning status, and the allowed transformations. If an object is pinned, it cannot be moved at all (or only in the non-pinned direction) from the Ipe user interface. Restricting the allowed transformations works somewhat differently: It doesn't stop transformations being applied to the object, but they only effect the position of the reference point (the origin of the object coordinate system), and (if transformations() == ETransformationsRigidMotions) the orientation of the object coordinate system. */ //! Construct from XML stream. Object::Object(const XmlAttributes &attr) { String str; if (attr.has("matrix", str)) iMatrix = Matrix(str); iPinned = ENoPin; if (attr.has("pin", str)) { if (str == "yes") iPinned = EFixedPin; else if (str == "h") iPinned = EHorizontalPin; else if (str == "v") iPinned = EVerticalPin; } iTransformations = ETransformationsAffine; if (attr.has("transformations", str) && !str.empty()) { if (str == "rigid") iTransformations = ETransformationsRigidMotions; else if (str == "translations") iTransformations = ETransformationsTranslations; } } /*! Create object by taking pinning/transforming from \a attr and setting identity matrix. */ Object::Object(const AllAttributes &attr) { iPinned = attr.iPinned; iTransformations = attr.iTransformations; } /*! Create object with identity matrix, no pinning, all transformations. */ Object::Object() { iPinned = ENoPin; iTransformations = ETransformationsAffine; } //! Copy constructor. Object::Object(const Object &rhs) { iMatrix = rhs.iMatrix; iPinned = rhs.iPinned; iTransformations = rhs.iTransformations; } //! Pure virtual destructor. Object::~Object() { // nothing } //! Write layer, pin, transformations, matrix to XML stream. void Object::saveAttributesAsXml(Stream &stream, String layer) const { if (!layer.empty()) stream << " layer=\"" << layer << "\""; if (!iMatrix.isIdentity()) stream << " matrix=\"" << iMatrix << "\""; switch (iPinned) { case EFixedPin: stream << " pin=\"yes\""; break; case EHorizontalPin: stream << " pin=\"h\""; break; case EVerticalPin: stream << " pin=\"v\""; break; case ENoPin: default: break; } if (iTransformations == ETransformationsTranslations) stream << " transformations=\"translations\""; else if (iTransformations == ETransformationsRigidMotions) stream << " transformations=\"rigid\""; } //! Return pointer to this object if it is an Group, nullptr otherwise. Group *Object::asGroup() { return nullptr; } //! Return pointer to this object if it is an Group, nullptr otherwise. const Group *Object::asGroup() const { return nullptr; } //! Return pointer to this object if it is an Text, nullptr otherwise. Text *Object::asText() { return nullptr; } //! Return pointer to this object if it is an Path, nullptr otherwise. Path *Object::asPath() { return nullptr; } //! Return pointer to this object if it is an Image , nullptr otherwise. Image *Object::asImage() { return nullptr; } //! Return pointer to this object if it is an Ref, nullptr otherwise. Reference *Object::asReference() { return nullptr; } // -------------------------------------------------------------------- //! Set the transformation matrix. /*! Don't use this on an Object in a Page, because it wouldn't invalidate its bounding box. Call Page::transform instead. */ void Object::setMatrix(const Matrix &matrix) { iMatrix = matrix; } //! Return pinning mode of the object. TPinned Object::pinned() const { return iPinned; } //! Set pinning mode of the object. void Object::setPinned(TPinned pin) { iPinned = pin; } //! Set allowed transformations of the object. void Object::setTransformations(TTransformations trans) { iTransformations = trans; } //! Set an attribute on this object. /*! Returns true if an attribute was actually changed. */ bool Object::setAttribute(Property prop, Attribute value) { switch (prop) { case EPropPinned: assert(value.isEnum()); if (value.pinned() != iPinned) { iPinned = value.pinned(); return true; } break; case EPropTransformations: assert(value.isEnum()); if (value.transformations() != iTransformations) { iTransformations = value.transformations(); return true; } break; default: break; } return false; } //! Get setting of an attribute of this object. /*! If object does not have this attribute, returnes "undefined" attribute. */ Attribute Object::getAttribute(Property prop) const noexcept { switch (prop) { case EPropPinned: return Attribute(pinned()); case EPropTransformations: return Attribute(iTransformations); default: return Attribute::UNDEFINED(); } } // -------------------------------------------------------------------- //! Check all symbolic attributes. void Object::checkStyle(const Cascade *, AttributeSeq &) const { // nothing } /*! Check whether attribute \a is either absolute or defined in the style sheet cascade \a sheet. Add \a attr to \a seq if this is not the case. */ void Object::checkSymbol(Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq) { if (attr.isSymbolic() && sheet->findDefinition(kind, attr) < 0) { AttributeSeq::const_iterator it = std::find(seq.begin(), seq.end(), attr); if (it == seq.end()) seq.push_back(attr); } } //! Compute vertex snapping position for transformed object. /*! Looks only for positions closer than \a bound. If successful, modify \a pos and \a bound. The default implementation does nothing. */ void Object::snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { // nothing } //! Compute control point snapping position for transformed object. /*! Looks only for positions closer than \a bound. If successful, modify \a pos and \a bound. The default implementation does nothing. */ void Object::snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { // nothing } //! Compute boundary snapping position for transformed object. /*! Looks only for positions closer than \a bound. If successful, modify \a pos and \a bound. The default implementation does nothing. */ void Object::snapBnd(const Vector &/* mouse */, const Matrix &/* m */, Vector &/* pos */, double &/* bound */) const { // nothing } // -------------------------------------------------------------------- /*! \class ipe::Visitor \ingroup high \brief Base class for visitors to Object. Many operations on Ipe Objects are implemented as visitors, all derived from Visitor. The default implementation of each visitXXX member does nothing. */ //! Pure virtual destructor. Visitor::~Visitor() { // void } //! Called on an Group object. void Visitor::visitGroup(const Group *) { // nothing } //! Called on an Path object. void Visitor::visitPath(const Path *) { // nothing } //! Called on an Image object. void Visitor::visitImage(const Image * ) { // nothing } //! Called on an Text object. void Visitor::visitText(const Text * ) { // nothing } //! Called on an Reference object. void Visitor::visitReference(const Reference * ) { // nothing } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipestyle.cpp0000644000175000017500000005430113561570220016634 0ustar otfriedotfried// -------------------------------------------------------------------- // Ipe style sheet // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipestyle.h" #include "ipeobject.h" #include "ipepainter.h" #include "ipeutils.h" #include "ipeiml.h" #include using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::Symbol \ingroup attr \brief A symbol is a named object defined in an ipe::StyleSheet. */ //! Default constructor Symbol::Symbol() { iObject = nullptr; iXForm = false; iTransformations = ETransformationsAffine; } //! Create symbol for \a object (takes ownership). Symbol::Symbol(Object *object) { iObject = object; iXForm = false; iTransformations = ETransformationsAffine; } //! Copy constructor. Symbol::Symbol(const Symbol &rhs) { iObject = rhs.iObject ? rhs.iObject->clone() : nullptr; iXForm = rhs.iXForm; iTransformations = rhs.iTransformations; iSnap = rhs.iSnap; } //! Assignment operator. Symbol &Symbol::operator=(const Symbol &rhs) { if (this != &rhs) { delete iObject; iObject = rhs.iObject ? rhs.iObject->clone() : nullptr; iXForm = rhs.iXForm; iTransformations = rhs.iTransformations; iSnap = rhs.iSnap; } return *this; } //! Destructor. Symbol::~Symbol() { delete iObject; } // -------------------------------------------------------------------- /*! \class ipe::StyleSheet \ingroup doc \brief A style sheet maps symbolic names to absolute values. Ipe documents can use symbolic attributes, such as 'normal', 'fat', or 'thin' for line thickness, or 'red', 'navy', 'turquoise' for color. The mapping to an absolute pen thickness or RGB value is performed by a StyleSheet. Style sheets are always included when the document is saved, so that an Ipe document is self-contained. The built-in standard style sheet is minimal, and only needed to provide sane fallbacks for all the "normal" settings. */ #define MASK 0x00ffffff #define SHIFT 24 #define KINDMASK 0x7f000000 // -------------------------------------------------------------------- //! The default constructor creates an empty style sheet. StyleSheet::StyleSheet() { iStandard = false; iTitleStyle.iDefined = false; iPageNumberStyle.iDefined = false; iTextPadding.iLeft = -1.0; iLineJoin = EDefaultJoin; iLineCap = EDefaultCap; iFillRule = EDefaultRule; } //! Set page layout. void StyleSheet::setLayout(const Layout &layout) { iLayout = layout; } //! Return page layout (or 0 if none defined). const Layout *StyleSheet::layout() const { if (iLayout.isNull()) return nullptr; else return &iLayout; } //! Return text object padding (for bbox computation). const TextPadding *StyleSheet::textPadding() const { if (iTextPadding.iLeft < 0) return nullptr; else return &iTextPadding; } //! Set padding for text object bbox computation. void StyleSheet::setTextPadding(const TextPadding &pad) { iTextPadding = pad; } //! Set style of page titles. void StyleSheet::setTitleStyle(const TitleStyle &ts) { iTitleStyle = ts; } //! Return title style (or 0 if none defined). const StyleSheet::TitleStyle *StyleSheet::titleStyle() const { if (iTitleStyle.iDefined) return &iTitleStyle; else return nullptr; } //! Set style of page numbering. void StyleSheet::setPageNumberStyle(const PageNumberStyle &pns) { iPageNumberStyle = pns; } //! Return page number style. const StyleSheet::PageNumberStyle *StyleSheet::pageNumberStyle() const { if (iPageNumberStyle.iDefined) return &iPageNumberStyle; else return nullptr; } //! Add gradient to this style sheet. void StyleSheet::addGradient(Attribute name, const Gradient &s) { assert(name.isSymbolic()); iGradients[name.index()] = s; } //! Find gradient in style sheet cascade. const Gradient *StyleSheet::findGradient(Attribute sym) const { if (!sym.isSymbolic()) return nullptr; GradientMap::const_iterator it = iGradients.find(sym.index()); if (it != iGradients.end()) return &it->second; else return nullptr; } //! Add tiling to this style sheet. void StyleSheet::addTiling(Attribute name, const Tiling &s) { assert(name.isSymbolic()); iTilings[name.index()] = s; } //! Find tiling in style sheet cascade. const Tiling *StyleSheet::findTiling(Attribute sym) const { if (!sym.isSymbolic()) return nullptr; TilingMap::const_iterator it = iTilings.find(sym.index()); if (it != iTilings.end()) return &it->second; else return nullptr; } void StyleSheet::addEffect(Attribute name, const Effect &e) { assert(name.isSymbolic()); iEffects[name.index()] = e; } const Effect *StyleSheet::findEffect(Attribute sym) const { if (!sym.isSymbolic()) return nullptr; EffectMap::const_iterator it = iEffects.find(sym.index()); if (it != iEffects.end()) return &it->second; else return nullptr; } // -------------------------------------------------------------------- //! Set line cap. void StyleSheet::setLineCap(TLineCap s) { iLineCap = s; } //! Set line join. void StyleSheet::setLineJoin(TLineJoin s) { iLineJoin = s; } //! Set fill rule. void StyleSheet::setFillRule(TFillRule s) { iFillRule = s; } // -------------------------------------------------------------------- //! Add a symbol object. void StyleSheet::addSymbol(Attribute name, const Symbol &symbol) { assert(name.isSymbolic()); iSymbols[name.index()] = symbol; } //! Find a symbol object with given name. /*! If attr is not symbolic or if the symbol doesn't exist, returns 0. */ const Symbol *StyleSheet::findSymbol(Attribute attr) const { if (!attr.isSymbolic()) return nullptr; SymbolMap::const_iterator it = iSymbols.find(attr.index()); if (it != iSymbols.end()) return &it->second; else return nullptr; } // -------------------------------------------------------------------- //! Add an attribute. /*! Does nothing if \a name is not symbolic. */ void StyleSheet::add(Kind kind, Attribute name, Attribute value) { if (!name.isSymbolic()) return; iMap[name.index() | (kind << SHIFT)] = value; } //! Find a symbolic attribute. /*! If \a sym is not symbolic, returns \a sym itself. If \a sym cannot be found, returns the "undefined" attribute. In all other cases, the returned attribute is guaranteed to be absolute. */ Attribute StyleSheet::find(Kind kind, Attribute sym) const { if (!sym.isSymbolic()) return sym; Map::const_iterator it = iMap.find(sym.index() | (kind << SHIFT)); if (it != iMap.end()) { return it->second; } else return Attribute::UNDEFINED(); } //! Check whether symbolic attribute is defined. /*! This method also works for ESymbol, EGradient, ETiling, and EEffect. Returns true if \a sym is not symbolic. */ bool StyleSheet::has(Kind kind, Attribute sym) const { if (!sym.isSymbolic()) return true; switch (kind) { case ESymbol: { SymbolMap::const_iterator it = iSymbols.find(sym.index()); return (it != iSymbols.end()); } case EGradient: { GradientMap::const_iterator it = iGradients.find(sym.index()); return (it != iGradients.end()); } case ETiling: { TilingMap::const_iterator it = iTilings.find(sym.index()); return (it != iTilings.end()); } case EEffect: { EffectMap::const_iterator it = iEffects.find(sym.index()); return (it != iEffects.end()); } default: { Map::const_iterator it = iMap.find(sym.index() | (kind << SHIFT)); return (it != iMap.end()); } } } //! Removes definition for a symbolic attribute from this stylesheet. /*! This method also works for ESymbol, EGradient, ETiling, and EEffect. It is okay if the symbolic attribute is not defined in the stylesheet, nothing happens in this case. */ void StyleSheet::remove(Kind kind, Attribute sym) { switch (kind) { case ETiling: iTilings.erase(sym.index()); break; case ESymbol: iSymbols.erase(sym.index()); break; case EGradient: iGradients.erase(sym.index()); break; case EEffect: iEffects.erase(sym.index()); break; default: iMap.erase(sym.index() | (kind << SHIFT)); break; }; } // -------------------------------------------------------------------- //! Return all symbolic names in the style sheet cascade. /*! Names are simply appended from top to bottom of the cascade. Names are inserted only once. */ void StyleSheet::allNames(Kind kind, AttributeSeq &seq) const { if (kind == ESymbol) { for (SymbolMap::const_iterator it = iSymbols.begin(); it != iSymbols.end(); ++it) { Attribute attr(true, it->first); if (std::find(seq.begin(), seq.end(), attr) == seq.end()) seq.push_back(attr); } } else if (kind == EGradient) { for (GradientMap::const_iterator it = iGradients.begin(); it != iGradients.end(); ++it) { Attribute attr(true, it->first); if (std::find(seq.begin(), seq.end(), attr) == seq.end()) seq.push_back(attr); } } else if (kind == ETiling) { for (TilingMap::const_iterator it = iTilings.begin(); it != iTilings.end(); ++it) { Attribute attr(true, it->first); if (std::find(seq.begin(), seq.end(), attr) == seq.end()) seq.push_back(attr); } } else if (kind == EEffect) { for (EffectMap::const_iterator it = iEffects.begin(); it != iEffects.end(); ++it) { Attribute attr(true, it->first); if (std::find(seq.begin(), seq.end(), attr) == seq.end()) seq.push_back(attr); } } else { uint32_t kindMatch = (kind << SHIFT); for (Map::const_iterator it = iMap.begin(); it != iMap.end(); ++it) { if (uint32_t(it->first & KINDMASK) == kindMatch) { Attribute attr(true, (it->first & MASK)); if (std::find(seq.begin(), seq.end(), attr) == seq.end()) seq.push_back(attr); } } } } // -------------------------------------------------------------------- //! Save style sheet in XML format. void StyleSheet::saveAsXml(Stream &stream, bool saveBitmaps) const { stream << "\n"; if (saveBitmaps) { BitmapFinder bm; for (SymbolMap::const_iterator it = iSymbols.begin(); it != iSymbols.end(); ++it) it->second.iObject->accept(bm); if (!bm.iBitmaps.empty()) { int id = 1; Bitmap prev; for (std::vector::iterator it = bm.iBitmaps.begin(); it != bm.iBitmaps.end(); ++it) { if (!it->equal(prev)) { it->saveAsXml(stream, id); it->setObjNum(id); } else it->setObjNum(prev.objNum()); // noop if prev == it prev = *it; ++id; } } } Repository *rep = Repository::get(); for (SymbolMap::const_iterator it = iSymbols.begin(); it != iSymbols.end(); ++it) { stream << "toString(it->first) << "\""; if (it->second.iTransformations == ETransformationsTranslations) stream << " transformations=\"translations\""; else if (it->second.iTransformations == ETransformationsRigidMotions) stream << " transformations=\"rigid\""; if (it->second.iXForm) stream << " xform=\"yes\""; if (it->second.iSnap.size() > 0) { stream << " snap=\""; String sep = ""; for (const Vector & pos : it->second.iSnap) { stream << sep << pos; sep = " "; } stream << "\""; } stream << ">\n"; it->second.iObject->saveAsXml(stream, String()); stream << "\n"; } for (Map::const_iterator it = iMap.begin(); it != iMap.end(); ++it) { int kind = (it->first >> SHIFT); int kind1 = (kind == ELabelStyle) ? ETextStyle : kind; stream << "<" << kind_names[kind1] << " name=\"" << rep->toString(it->first & MASK) << "\""; if (kind1 == ETextStyle) { String s = it->second.string(); int i = s.find('\0'); if (kind == ELabelStyle) stream << " type=\"label\""; stream << " begin=\"" << s.substr(0, i) << "\" end=\"" << s.substr(i+1) << "\"/>\n"; } else stream << " value=\"" << it->second.string() << "\"/>\n"; } if (!iPreamble.empty()) { stream << ""; stream.putXmlString(iPreamble); stream << "\n"; } if (!iLayout.isNull()) { stream << " 0.0) stream << "\" skip=\"" << iLayout.iParagraphSkip; if (!iLayout.iCrop) stream << "\" crop=\"no"; stream << "\"/>\n"; } if (iTextPadding.iLeft >= 0.0) { stream << "\n"; } if (iPageNumberStyle.iDefined) { stream << "" << iPageNumberStyle.iText << "\n"; } if (iTitleStyle.iDefined) { stream << "\n"; } if (iLineCap != EDefaultCap || iLineJoin != EDefaultJoin || iFillRule != EDefaultRule) { stream << "\n"; } for (GradientMap::const_iterator it = iGradients.begin(); it != iGradients.end(); ++it) { stream << "toString(it->first) << "\""; const Gradient &g = it->second; if (g.iType == Gradient::EAxial) stream << " type=\"axial\" coords=\"" << g.iV[0] << " " << g.iV[1] << "\""; else stream << " type=\"radial\" coords=\"" << g.iV[0] << " " << g.iRadius[0] << " " << g.iV[1] << " " << g.iRadius[1] << "\""; if (g.iExtend) stream << " extend=\"yes\""; if (!g.iMatrix.isIdentity()) stream << " matrix=\"" << g.iMatrix << "\""; stream << ">\n"; for (int i = 0; i < size(g.iStops); ++i) stream << " \n"; stream << "\n"; } for (TilingMap::const_iterator it = iTilings.begin(); it != iTilings.end(); ++it) { const Tiling &t = it->second; stream << "toString(it->first) << "\"" << " angle=\"" << t.iAngle.degrees() << "\"" << " step=\"" << t.iStep << "\"" << " width=\"" << t.iWidth << "\"/>\n"; } for (EffectMap::const_iterator it = iEffects.begin(); it != iEffects.end(); ++it) { stream << "toString(it->first) << "\""; const Effect &e = it->second; if (e.iDuration != 0) stream << " duration=\"" << e.iDuration << "\""; if (e.iTransitionTime != 1) stream << " transition=\"" << e.iTransitionTime << "\""; stream << " effect=\"" << int(e.iEffect) << "\"/>\n"; } stream << "\n"; } // -------------------------------------------------------------------- /*! \class ipe::Cascade \ingroup doc \brief A cascade of style sheets. The StyleSheets of a document cascade in the sense that a document can refer to several StyleSheets, which are arranged in a stack. A lookup is done from top to bottom, and returns as soon as a match is found. Ipe always appends the built-in "standard" style sheet at the bottom of the cascade. */ //! Create an empty cascade. /*! This does not add the standard style sheet. */ Cascade::Cascade() { // nothing } static void destruct_sheets(std::vector &sheets) { for (int i = 0; i < size(sheets); ++i) { delete sheets[i]; sheets[i] = nullptr; } sheets.clear(); } //! Copy constructor. Cascade::Cascade(const Cascade &rhs) { destruct_sheets(iSheets); for (int i = 0; i < rhs.count(); ++i) iSheets.push_back(new StyleSheet(*rhs.iSheets[i])); } //! Assignment operator. Cascade &Cascade::operator=(const Cascade &rhs) { if (this != &rhs) { destruct_sheets(iSheets); for (int i = 0; i < rhs.count(); ++i) iSheets.push_back(new StyleSheet(*rhs.iSheets[i])); } return *this; } //! Destructor. Cascade::~Cascade() { destruct_sheets(iSheets); } //! Insert a style sheet into the cascade. /*! Takes ownership of \a sheet. */ void Cascade::insert(int index, StyleSheet *sheet) { iSheets.insert(iSheets.begin() + index, sheet); } //! Remove a style sheet from the cascade. /*! The old sheet is deleted. */ void Cascade::remove(int index) { iSheets.erase(iSheets.begin() + index); } void Cascade::saveAsXml(Stream &stream) const { for (int i = count() - 1; i >= 0; --i) { if (!iSheets[i]->isStandard()) iSheets[i]->saveAsXml(stream); } } bool Cascade::has(Kind kind, Attribute sym) const { for (int i = 0; i < count(); ++i) { if (iSheets[i]->has(kind, sym)) return true; } return false; } Attribute Cascade::find(Kind kind, Attribute sym) const { for (int i = 0; i < count(); ++i) { Attribute a = iSheets[i]->find(kind, sym); if (a != Attribute::UNDEFINED()) return a; } Attribute normal = Attribute::normal(kind); for (int i = 0; i < count(); ++i) { Attribute a = iSheets[i]->find(kind, normal); if (a != Attribute::UNDEFINED()) return a; } // this shouldn't happen return Attribute::UNDEFINED(); } const Symbol *Cascade::findSymbol(Attribute sym) const { for (int i = 0; i < count(); ++i) { const Symbol *s = iSheets[i]->findSymbol(sym); if (s) return s; } return nullptr; } const Gradient *Cascade::findGradient(Attribute sym) const { for (int i = 0; i < count(); ++i) { const Gradient *s = iSheets[i]->findGradient(sym); if (s) return s; } return nullptr; } const Tiling *Cascade::findTiling(Attribute sym) const { for (int i = 0; i < count(); ++i) { const Tiling *s = iSheets[i]->findTiling(sym); if (s) return s; } return nullptr; } const Effect *Cascade::findEffect(Attribute sym) const { for (int i = 0; i < count(); ++i) { const Effect *s = iSheets[i]->findEffect(sym); if (s) return s; } return nullptr; } //! Find page layout (such as text margins). const Layout *Cascade::findLayout() const { for (int i = 0; i < count(); ++i) { const Layout *l = iSheets[i]->layout(); if (l) return l; } // must never happen assert(false); return nullptr; } //! Find text padding (for text bbox computation). const TextPadding *Cascade::findTextPadding() const { for (int i = 0; i < count(); ++i) { const TextPadding *t = iSheets[i]->textPadding(); if (t) return t; } // must never happen assert(false); return nullptr; } //! Get style of page titles (or 0 if none defined). const StyleSheet::TitleStyle *Cascade::findTitleStyle() const { for (int i = 0; i < count(); ++i) { const StyleSheet::TitleStyle *ts = iSheets[i]->titleStyle(); if (ts) return ts; } return nullptr; } //! Return style of page numbering (or 0 if none defined). const StyleSheet::PageNumberStyle *Cascade::findPageNumberStyle() const { for (int i = 0; i < count(); ++i) { const StyleSheet::PageNumberStyle *pns = iSheets[i]->pageNumberStyle(); if (pns) return pns; } return nullptr; } //! Return total LaTeX preamble (of the whole cascade). String Cascade::findPreamble() const { String s; for (int i = 0; i < count(); ++i) { s = iSheets[i]->preamble() + "\n" + s; } return s; } TLineCap Cascade::lineCap() const { for (int i = 0; i < count(); ++i) { if (iSheets[i]->lineCap() != EDefaultCap) return iSheets[i]->lineCap(); } return EButtCap; // should not happen } TLineJoin Cascade::lineJoin() const { for (int i = 0; i < count(); ++i) { if (iSheets[i]->lineJoin() != EDefaultJoin) return iSheets[i]->lineJoin(); } return ERoundJoin; // should not happen } TFillRule Cascade::fillRule() const { for (int i = 0; i < count(); ++i) { if (iSheets[i]->fillRule() != EDefaultRule) return iSheets[i]->fillRule(); } return EEvenOddRule; // should not happen } void Cascade::allNames(Kind kind, AttributeSeq &seq) const { if (has(kind, Attribute::NORMAL())) seq.push_back(Attribute::NORMAL()); for (int i = 0; i < count(); ++i) iSheets[i]->allNames(kind, seq); } //! Find stylesheet defining the attribute. /*! This method goes through the cascade looking for a definition of the symbolic attribute \a sym. It returns the index of the stylesheet defining the attribute, or -1 if the attribute is not defined. The method panics if \a sym is not symbolic. It also works for ESymbol, EGradient, ETiling, and EEffect. */ int Cascade::findDefinition(Kind kind, Attribute sym) const { assert(sym.isSymbolic()); for (int i = 0; i < count(); ++i) { if (iSheets[i]->has(kind, sym)) return i; } return -1; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipedoc.cpp0000644000175000017500000005510413561570220016243 0ustar otfriedotfried// -------------------------------------------------------------------- // The Ipe document. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipedoc.h" #include "ipeiml.h" #include "ipestyle.h" #include "ipereference.h" #include "ipepainter.h" #include "ipeutils.h" #include "ipepdfparser.h" #include "ipepdfwriter.h" #include "ipelatex.h" #include using namespace ipe; // -------------------------------------------------------------------- /*! \defgroup doc Ipe Document \brief The classes managing an Ipe document. The main class, Document, represents an entire Ipe document, and allows you to load, save, access, and modify such a document. Other classes represent pages, layers, and views of a document. Another important class is the StyleSheet, which maps symbolic attributes to absolute values. */ /*! \class ipe::Document \ingroup doc \brief The model for an Ipe document. The Document class represents the contents of an Ipe document, and all the methods necessary to load, save, and modify it. */ //! Construct an empty document for filling by a client. /*! As constructed, it has no pages, A4 media, and only the standard style sheet. */ Document::Document() { iResources = nullptr; iCascade = new Cascade(); iCascade->insert(0, StyleSheet::standard()); } //! Destructor. Document::~Document() { for (int i = 0; i < countPages(); ++i) delete page(i); delete iCascade; delete iResources; } //! Copy constructor. Document::Document(const Document &rhs) { iCascade = new Cascade(*rhs.iCascade); for (int i = 0; i < rhs.countPages(); ++i) iPages.push_back(new Page(*rhs.page(i))); iProperties = rhs.iProperties; iResources = nullptr; } // --------------------------------------------------------------------- String readLine(DataSource &source) { String s; int ch = source.getChar(); while (ch != EOF && ch != '\n') { s += char(ch); ch = source.getChar(); } return s; } //! Determine format of file in \a source. FileFormat Document::fileFormat(DataSource &source) { String s1 = readLine(source); String s2 = readLine(source); if (s1.substr(0, 5) == "dict() || obj->dict()->stream().size() == 0) return Buffer(); return obj->dict()->stream(); } // -------------------------------------------------------------------- class PsSource : public DataSource { public: PsSource(DataSource &source) : iSource(source) { /* nothing */ } bool skipToXml(); String readLine(); Buffer image(int index) const; int getNext() const; inline bool deflated() const { return iDeflated; } virtual int getChar(); private: DataSource &iSource; std::vector iImages; bool iEos; bool iDeflated; }; int PsSource::getChar() { int ch = iSource.getChar(); if (ch == '\n') iSource.getChar(); // remove '%' return ch; } String PsSource::readLine() { String s; int ch = iSource.getChar(); while (ch != EOF && ch != '\n') { s += char(ch); ch = iSource.getChar(); } iEos = (ch == EOF); return s; } Buffer PsSource::image(int index) const { if (1 <= index && index <= int(iImages.size())) return iImages[index - 1]; else return Buffer(); } bool PsSource::skipToXml() { iDeflated = false; String s1 = readLine(); String s2 = readLine(); if (s1.substr(0, 11) != "%!PS-Adobe-" || s2.substr(0, 17) != "%%Creator: Ipelib") return false; do { s1 = readLine(); if (s1.substr(0, 17) == "%%BeginIpeImage: ") { Lex lex(s1.substr(17)); int num, len; lex >> num >> len; if (num != int(iImages.size() + 1)) return false; (void) readLine(); // skip 'image' Buffer buf(len); A85Source a85(iSource); char *p = buf.data(); char *p1 = p + buf.size(); while (p < p1) { int ch = a85.getChar(); if (ch == EOF) return false; *p++ = char(ch); } iImages.push_back(buf); } } while (!iEos && s1.substr(0, 13) != "%%BeginIpeXml"); iDeflated = (s1.substr(13, 14) == ": /FlateDecode"); if (iEos) return false; (void) iSource.getChar(); // skip '%' before return true; } class PsStreamParser : public ImlParser { public: explicit PsStreamParser(DataSource &source, PsSource &psSource); virtual Buffer pdfStream(int objNum); private: PsSource &iPsSource; }; PsStreamParser::PsStreamParser(DataSource &source, PsSource &psSource) : ImlParser(source), iPsSource(psSource) { // nothing } Buffer PsStreamParser::pdfStream(int objNum) { return iPsSource.image(objNum); } // -------------------------------------------------------------------- Document *doParse(Document *self, ImlParser &parser, int &reason) { int res = parser.parseDocument(*self); if (res) { delete self; self = nullptr; if (res == ImlParser::ESyntaxError) reason = parser.parsePosition(); else reason = -res; } return self; } Document *doParseXml(DataSource &source, int &reason) { Document *self = new Document; ImlParser parser(source); return doParse(self, parser, reason); } Document *doParsePs(DataSource &source, int &reason) { PsSource psSource(source); reason = Document::EFileOpenError; // could not find Xml stream if (!psSource.skipToXml()) return nullptr; Document *self = new Document; if (psSource.deflated()) { A85Source a85(psSource); InflateSource source(a85); PsStreamParser parser(source, psSource); return doParse(self, parser, reason); } else { PsStreamParser parser(psSource, psSource); return doParse(self, parser, reason); } } Document *doParsePdf(DataSource &source, int &reason) { PdfFile loader; reason = Document::ENotAnIpeFile; if (!loader.parse(source)) // could not parse PDF container return nullptr; const PdfObj *obj = loader.catalog()->get("PieceInfo", &loader); if (obj && obj->dict()) { obj = obj->dict()->get("Ipe", &loader); if (obj && obj->dict()) obj = obj->dict()->get("Private", &loader); } if (!obj) obj = loader.object(1); // was the object really created by Ipe? if (!obj || !obj->dict()) return nullptr; const PdfObj *type = obj->dict()->get("Type", nullptr); if (!type || !type->name() || type->name()->value() != "Ipe") return nullptr; Buffer buffer = obj->dict()->stream(); BufferSource xml(buffer); Document *self = new Document; if (obj->dict()->deflated()) { InflateSource xml1(xml); PdfStreamParser parser(loader, xml1); return doParse(self, parser, reason); } else { PdfStreamParser parser(loader, xml); return doParse(self, parser, reason); } } //! Construct a document from an input stream. /*! Returns 0 if the stream couldn't be parsed, and a reason explaining that in \a reason. If \a reason is positive, it is a file (stream) offset where parsing failed. If \a reason is negative, it is an error code, see Document::LoadErrors. */ Document *Document::load(DataSource &source, FileFormat format, int &reason) { if (format == FileFormat::Xml) return doParseXml(source, reason); if (format == FileFormat::Pdf) return doParsePdf(source, reason); if (format == FileFormat::Eps) return doParsePs(source, reason); reason = (format == FileFormat::Ipe5) ? EVersionTooOld : ENotAnIpeFile; return nullptr; } Document *Document::load(const char *fname, int &reason) { reason = EFileOpenError; std::FILE *fd = Platform::fopen(fname, "rb"); if (!fd) return nullptr; FileSource source(fd); FileFormat format = fileFormat(source); std::rewind(fd); Document *self = load(source, format, reason); std::fclose(fd); return self; } Document *Document::loadWithErrorReport(const char *fname) { int reason; Document *doc = load(fname, reason); if (doc) return doc; fprintf(stderr, "Could not read Ipe file '%s'\n", fname); switch (reason) { case Document::EVersionTooOld: fprintf(stderr, "The Ipe version of this document is too old.\n" "Please convert it using 'ipe6upgrade'.\n"); break; case Document::EVersionTooRecent: fprintf(stderr, "The document was created by a newer version of Ipe.\n" "Please upgrade your Ipe installation.\n"); break; case Document::EFileOpenError: perror("Error opening the file"); break; case Document::ENotAnIpeFile: fprintf(stderr, "The document was not created by Ipe.\n"); break; default: fprintf(stderr, "Error parsing the document at position %d\n.", reason); break; } return nullptr; } // -------------------------------------------------------------------- //! Save in a stream. /*! Returns true if sucessful. */ bool Document::save(TellStream &stream, FileFormat format, uint32_t flags) const { if (format == FileFormat::Xml) { stream << "\n"; stream << "\n"; saveAsXml(stream); return true; } int compresslevel = 9; if (flags & SaveFlag::NoZip) compresslevel = 0; if (format == FileFormat::Pdf) { PdfWriter writer(stream, this, iResources, flags, 0, -1, compresslevel); writer.createPages(); writer.createBookmarks(); writer.createNamedDests(); if (!(flags & SaveFlag::Export)) { String xmlData; StringStream stream(xmlData); if (compresslevel > 0) { DeflateStream dfStream(stream, compresslevel); // all bitmaps have been embedded and carry correct object number saveAsXml(dfStream, true); dfStream.close(); writer.createXmlStream(xmlData, true); } else { saveAsXml(stream, true); writer.createXmlStream(xmlData, false); } } writer.createTrailer(); return true; } return false; } bool Document::save(const char *fname, FileFormat format, uint32_t flags) const { std::FILE *fd = Platform::fopen(fname, "wb"); if (!fd) return false; FileStream stream(fd); bool result = save(stream, format, flags); std::fclose(fd); return result; } //! Export a single view to PDF bool Document::exportView(const char *fname, FileFormat format, uint32_t flags, int pno, int vno) const { if (format != FileFormat::Pdf) return false; int compresslevel = 9; if (flags & SaveFlag::NoZip) compresslevel = 0; std::FILE *fd = Platform::fopen(fname, "wb"); if (!fd) return false; FileStream stream(fd); PdfWriter writer(stream, this, iResources, flags, pno, pno, compresslevel); writer.createPageView(pno, vno); writer.createTrailer(); std::fclose(fd); return true; } //! Export a range of pages to PDF. bool Document::exportPages(const char *fname, uint32_t flags, int fromPage, int toPage) const { int compresslevel = 9; if (flags & SaveFlag::NoZip) compresslevel = 0; std::FILE *fd = Platform::fopen(fname, "wb"); if (!fd) return false; FileStream stream(fd); PdfWriter writer(stream, this, iResources, flags, fromPage, toPage, compresslevel); writer.createPages(); writer.createTrailer(); std::fclose(fd); return true; } // -------------------------------------------------------------------- //! Create a list of all bitmaps in the document. void Document::findBitmaps(BitmapFinder &bm) const { for (int i = 0; i < countPages(); ++i) bm.scanPage(page(i)); // also need to look at all templates AttributeSeq seq; iCascade->allNames(ESymbol, seq); for (AttributeSeq::iterator it = seq.begin(); it != seq.end(); ++it) { const Symbol *symbol = iCascade->findSymbol(*it); symbol->iObject->accept(bm); } std::sort(bm.iBitmaps.begin(), bm.iBitmaps.end()); } //! Save in XML format into an Stream. void Document::saveAsXml(Stream &stream, bool usePdfBitmaps) const { stream << "\n"; String info; StringStream infoStr(info); infoStr << "\n"; if (info.size() > 10) stream << info; if (!iProperties.iPreamble.empty()) { stream << ""; stream.putXmlString(iProperties.iPreamble); stream << "\n"; } // save bitmaps BitmapFinder bm; findBitmaps(bm); if (!bm.iBitmaps.empty()) { int id = 1; Bitmap prev; for (std::vector::iterator it = bm.iBitmaps.begin(); it != bm.iBitmaps.end(); ++it) { if (!it->equal(prev)) { if (usePdfBitmaps) { it->saveAsXml(stream, it->objNum(), it->objNum()); } else { it->saveAsXml(stream, id); it->setObjNum(id); } } else it->setObjNum(prev.objNum()); // noop if prev == it prev = *it; ++id; } } // now save style sheet iCascade->saveAsXml(stream); // save pages for (int i = 0; i < countPages(); ++i) page(i)->saveAsXml(stream); stream << "\n"; } // -------------------------------------------------------------------- //! Set document properties. void Document::setProperties(const SProperties &props) { iProperties = props; } //! Replace the entire style sheet cascade. /*! Takes ownership of \a cascade, and returns the original cascade. */ Cascade *Document::replaceCascade(Cascade *sheets) { Cascade *old = iCascade; iCascade = sheets; return old; } //! Check all symbolic attributes in the document. /*! This function verifies that all symbolic attributes in the document are defined in the style sheet. It appends to \a seq all symbolic attributes (in no particular order, but without duplicates) that are NOT defined. Returns \c true if there are no undefined symbolic attributes in the document. */ bool Document::checkStyle(AttributeSeq &seq) const { for (int i = 0; i < countPages(); ++i) { for (int j = 0; j < page(i)->count(); ++j) { page(i)->object(j)->checkStyle(cascade(), seq); } } return (seq.size() == 0); } //! Update the PDF resources (after running latex). /*! Takes ownership. */ void Document::setResources(PdfResources *resources) { delete iResources; iResources = resources; } #if 0 //! Load a style sheet and add at top of cascade. bool Document::addStyleSheet(DataSource &source) { ImlParser parser(source); StyleSheet *sheet = parser.parseStyleSheet(); if (sheet) { sheet->setCascade(iCascade); setStyleSheet(sheet); return true; } else return false; } #endif //! Return total number of views in all pages. int Document::countTotalViews() const { int views = 0; for (int i = 0; i < countPages(); ++i) { int nviews = page(i)->countViews(); views += (nviews > 0) ? nviews : 1; } return views; } //! Return page index given a section title or page number. /*! Input page numbers are 1-based strings. Returns -1 if page not found. */ int Document::findPage(String s) const { if (s.empty()) return -1; if ('0' <= s[0] && s[0] <= '9') { int no = Lex(s).getInt(); if (no <= 0 || no > countPages()) return -1; return no - 1; } for (int i = 0; i < countPages(); ++i) { if (s == page(i)->section(0)) return i; } return -1; } //! Insert a new page. /*! The page is inserted at index \a no. */ void Document::insert(int no, Page *page) { iPages.insert(iPages.begin() + no, page); } //! Append a new page. void Document::push_back(Page *page) { iPages.push_back(page); } //! Replace page. /*! Returns the original page. */ Page *Document::set(int no, Page *page) { Page *p = iPages[no]; iPages[no] = page; return p; } //! Remove a page. /*! Returns the page that has been removed. */ Page *Document::remove(int no) { Page *p = iPages[no]; iPages.erase(iPages.begin() + no); return p; } // -------------------------------------------------------------------- //! Run PdfLatex or Xelatex int Document::runLatex(String docname, String &texLog) { texLog = ""; Latex converter(cascade(), iProperties.iTexEngine); AttributeSeq seq; cascade()->allNames(ESymbol, seq); for (AttributeSeq::iterator it = seq.begin(); it != seq.end(); ++it) { const Symbol *sym = cascade()->findSymbol(*it); if (sym) converter.scanObject(sym->iObject); } int count = 0; for (int i = 0; i < countPages(); ++i) count = converter.scanPage(page(i)); if (count == 0) return ErrNoText; if (iProperties.iNumberPages) { for (int i = 0; i < countPages(); ++i) { int nviews = page(i)->countViews(); for (int j = 0; j < nviews; ++j) converter.addPageNumber(i, j, countPages(), nviews); } } // First we need a directory String latexDir = Platform::latexDirectory(); if (latexDir.empty()) return ErrNoDir; String texFile = latexDir + "ipetemp.tex"; String pdfFile = latexDir + "ipetemp.pdf"; String logFile = latexDir + "ipetemp.log"; std::remove(logFile.z()); std::FILE *file = Platform::fopen(texFile.z(), "wb"); if (!file) return ErrWritingSource; FileStream stream(file); int err = converter.createLatexSource(stream, properties().iPreamble); std::fclose(file); if (err < 0) return ErrWritingSource; int result = Platform::runLatex(latexDir, iProperties.iTexEngine, docname); if (result != 0 && result != 1) return ErrRunLatex; // Check log file for Pdflatex version and errors texLog = Platform::readFile(logFile); if (texLog.left(14) != "This is pdfTeX" && texLog.left(15) != "This is pdfeTeX" && texLog.left(13) != "This is XeTeX" && texLog.left(14) != "This is LuaTeX" && texLog.left(22) != "entering extended mode") return ErrRunLatex; int i = texLog.find('\n'); if (i < 0) return ErrRunLatex; String version = texLog.substr(8, i); ipeDebug("%s", version.z()); // Check for error if (texLog.find("\n!") >= 0) return ErrLatex; std::FILE *pdfF = Platform::fopen(pdfFile.z(), "rb"); if (!pdfF) return ErrLatex; FileSource source(pdfF); bool okay = (converter.readPdf(source) && converter.updateTextObjects()); std::fclose(pdfF); if (okay) { setResources(converter.takeResources()); // resources()->show(); return ErrNone; } else return ErrLatexOutput; } //! Run Pdflatex (suitable for console applications) /*! Success/error is reported on stderr. */ int Document::runLatex(String docname) { String logFile; switch (runLatex(docname, logFile)) { case ErrNoText: fprintf(stderr, "No text objects in document, no need to run Pdflatex.\n"); return 0; case ErrNoDir: fprintf(stderr, "Directory '%s' does not exist and cannot be created.\n", "latexdir"); return 1; case ErrWritingSource: fprintf(stderr, "Error writing Latex source.\n"); return 1; case ErrOldPdfLatex: fprintf(stderr, "Your installed version of Pdflatex is too old.\n"); return 1; case ErrRunLatex: fprintf(stderr, "There was an error trying to run Pdflatex.\n"); return 1; case ErrLatex: fprintf(stderr, "There were Latex errors.\n"); return 1; case ErrLatexOutput: fprintf(stderr, "There was an error reading the Pdflatex output.\n"); return 1; case ErrNone: default: fprintf(stderr, "Pdflatex was run sucessfully.\n"); return 0; } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipesnap.cpp0000644000175000017500000002731613561570220016443 0ustar otfriedotfried// -------------------------------------------------------------------- // Snapping // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipesnap.h" #include "ipepage.h" #include "ipegroup.h" #include "ipereference.h" #include "ipepath.h" using namespace ipe; /*! \defgroup high Ipe Utilities \brief Classes to manage Ipe documents and objects. This module contains classes used in the implementation of the Ipe program itself. The only classes from this module you may be interested in are Visitor (which is essential to traverse an Ipe object structure), and perhaps Snap (if you are writing an Ipelet whose behavior depends on the current snap setting in the Ipe program). */ /*! \class ipe::Snap \ingroup high \brief Performs snapping operations, and stores snapping state. */ // -------------------------------------------------------------------- class CollectSegs : public Visitor { public: CollectSegs(const Vector &mouse, double snapDist, const Page *page, int view); virtual void visitGroup(const Group *obj); virtual void visitPath(const Path *obj); public: std::vector iSegs; std::vector iBeziers; std::vector iBeziersCont; // true if continuation of previous bezier std::vector iArcs; private: std::vector iMatrices; Vector iMouse; double iDist; int iView; }; CollectSegs::CollectSegs(const Vector &mouse, double snapDist, const Page *page, int view) : iMouse(mouse), iDist(snapDist), iView(view) { iMatrices.push_back(Matrix()); // identity matrix for (int i = 0; i < page->count(); ++i) { if (page->objSnapsInView(i, iView)) page->object(i)->accept(*this); } } void CollectSegs::visitGroup(const Group *obj) { iMatrices.push_back(iMatrices.back() * obj->matrix()); for (Group::const_iterator it = obj->begin(); it != obj->end(); ++it) (*it)->accept(*this); iMatrices.pop_back(); } // TODO: use bounding boxes for subsegs/beziers to speed up ? void CollectSegs::visitPath(const Path *obj) { Bezier b; Arc arc; Matrix m = iMatrices.back() * obj->matrix(); for (int i = 0; i < obj->shape().countSubPaths(); ++i) { const SubPath *sp = obj->shape().subPath(i); switch (sp->type()) { case SubPath::EEllipse: if (sp->distance(iMouse, m, iDist) < iDist) iArcs.push_back(m * Arc(sp->asEllipse()->matrix())); break; case SubPath::EClosedSpline: { std::vector bez; bool cont = false; sp->asClosedSpline()->beziers(bez); for (const Bezier & bz : bez) { b = m * bz; if (b.distance(iMouse, iDist) < iDist) { iBeziers.push_back(b); iBeziersCont.push_back(cont); cont = true; } else cont = false; } break; } case SubPath::ECurve: { const Curve *ssp = sp->asCurve(); int ns = ssp->closed() ? -1 : 0; Vector u[2]; for (int j = ns; j < ssp->countSegments(); ++j) { CurveSegment seg = j < 0 ? ssp->closingSegment(u) : ssp->segment(j); switch (seg.type()) { case CurveSegment::ESegment: if (seg.distance(iMouse, m, iDist) < iDist) iSegs.push_back(Segment(m * seg.cp(0), m * seg.cp(1))); break; case CurveSegment::EArc: arc = m * seg.arc(); if (arc.distance(iMouse, iDist) < iDist) iArcs.push_back(arc); break; case CurveSegment::EOldSpline: case CurveSegment::ESpline: { std::vector bez; seg.beziers(bez); bool cont = false; for (const Bezier & bz : bez) { b = m * bz; if (b.distance(iMouse, iDist) < iDist) { iBeziers.push_back(b); iBeziersCont.push_back(cont); cont = true; } else cont = false; } break; } } } break; } } } } // -------------------------------------------------------------------- /*! Find line through \a base with slope determined by angular snap size and direction. */ Line Snap::getLine(const Vector &mouse, const Vector &base) const noexcept { Angle alpha = iDir; Vector d = mouse - base; if (d.len() > 2.0) { alpha = d.angle() - iDir; alpha.normalize(0.0); alpha = iAngleSize * int(alpha / iAngleSize + 0.5) + iDir; } return Line(base, Vector(alpha)); } //! Perform intersection snapping. void Snap::intersectionSnap(const Vector &pos, Vector &fifi, const Page *page, int view, double &snapDist) const noexcept { CollectSegs segs(pos, snapDist, page, view); Vector v; std::vector pts; // 1. seg-seg intersections for (int i = 0; i < size(segs.iSegs); ++i) { for (int j = i + 1; j < size(segs.iSegs); ++j) { if (segs.iSegs[i].intersects(segs.iSegs[j], v)) pts.push_back(v); } } // 2. bezier-bezier and bezier-seg intersections for (int i = 0; i < size(segs.iBeziers); ++i) { for (int j = i + 1; j < size(segs.iBeziers); ++j) { if (j > i+1 || !segs.iBeziersCont[j]) segs.iBeziers[i].intersect(segs.iBeziers[j], pts); } for (int j = 0; j < size(segs.iSegs); ++j) segs.iBeziers[i].intersect(segs.iSegs[j], pts); } // 3. arc-arc, arc-bezier, and arc-segment intersections for (int i = 0; i < size(segs.iArcs); ++i) { for (int j = i+1; j < size(segs.iArcs); ++j) segs.iArcs[i].intersect(segs.iArcs[j], pts); for (int j = 0; j < size(segs.iBeziers); ++j) segs.iArcs[i].intersect(segs.iBeziers[j], pts); for (int j = 0; j < size(segs.iSegs); ++j) segs.iArcs[i].intersect(segs.iSegs[j], pts); } double d = snapDist; Vector pos1 = pos; double d1; for (const auto & pt : pts) { if ((d1 = (pos - pt).len()) < d) { d = d1; pos1 = pt; } } if (d < snapDist) { fifi = pos1; snapDist = d; } } //! Perform snapping to intersection of angular line and pos. bool Snap::snapAngularIntersection(Vector &pos, const Line &l, const Page *page, int view, double snapDist) const noexcept { CollectSegs segs(pos, snapDist, page, view); std::vector pts; Vector v; for (std::vector::const_iterator it = segs.iSegs.begin(); it != segs.iSegs.end(); ++it) { if (it->intersects(l, v)) pts.push_back(v); } for (std::vector::const_iterator it = segs.iArcs.begin(); it != segs.iArcs.end(); ++it) { it->intersect(l, pts); } for (std::vector::const_iterator it = segs.iBeziers.begin(); it != segs.iBeziers.end(); ++it) { it->intersect(l, pts); } double d = snapDist; Vector pos1 = pos; double d1; for (const auto & pt : pts) { if ((d1 = (pos - pt).len()) < d) { d = d1; pos1 = pt; } } if (d < snapDist) { pos = pos1; return true; } return false; } //! Tries vertex, intersection, boundary, and grid snapping. /*! If snapping occurred, \a pos is set to the new user space position. */ Snap::TSnapModes Snap::simpleSnap(Vector &pos, const Page *page, int view, double snapDist, Tool *tool) const noexcept { double d = snapDist; Vector fifi = pos; // highest priority: vertex snapping if (iSnap & ESnapVtx) { for (int i = 0; i < page->count(); ++i) { if (page->objSnapsInView(i, view)) page->snapVtx(i, pos, fifi, d); } if (tool) tool->snapVtx(pos, fifi, d, false); } double dvtx = d; Vector fifiCtl = pos; if (iSnap & ESnapCtl) { for (int i = 0; i < page->count(); ++i) { if (page->objSnapsInView(i, view)) page->snapCtl(i, pos, fifiCtl, d); } if (tool) tool->snapVtx(pos, fifiCtl, d, true); } double dctl = d; Vector fifiX = pos; if (iSnap & ESnapInt) intersectionSnap(pos, fifiX, page, view, d); // Return if snapping has occurred if (d < dctl) { pos = fifiX; return ESnapInt; } else if (d < dvtx) { pos = fifiCtl; return ESnapCtl; } else if (d < snapDist) { pos = fifi; return ESnapVtx; } // boundary snapping if (iSnap & ESnapBd) { for (int i = 0; i < page->count(); ++i) { if (page->objSnapsInView(i, view)) page->snapBnd(i, pos, fifi, d); } if (d < snapDist) { pos = fifi; return ESnapBd; } } // grid snapping: always occurs if (iSnap & ESnapGrid) { int grid = iGridSize; fifi.x = grid * int(pos.x / grid + (pos.x > 0 ? 0.5 : -0.5)); fifi.y = grid * int(pos.y / grid + (pos.y > 0 ? 0.5 : -0.5)); pos = fifi; return ESnapGrid; } return ESnapNone; } //! Performs snapping of position \a pos. /*! Returns \c true if snapping occurred. In that case \a pos is set to the new user space position. Automatic angular snapping occurs if \a autoOrg is not null --- the value is then used as the origin for automatic angular snapping. */ Snap::TSnapModes Snap::snap(Vector &pos, const Page *page, int view, double snapDist, Tool *tool, Vector *autoOrg) const noexcept { // automatic angular snapping and angular snapping both on? if (autoOrg && (iSnap & ESnapAuto) && (iSnap & ESnapAngle)) { // only one possible point! Line angular = getLine(pos, iOrigin); Line automat = getLine(pos, *autoOrg); Vector v; if (angular.intersects(automat, v) && v.sqLen() < 1e10) { pos = v; return ESnapAngle; } // if the two lines do not intersect, use following case } // case of only one angular snapping mode if ((iSnap & ESnapAngle) || (autoOrg && (iSnap & ESnapAuto))) { Vector org; if (iSnap & ESnapAngle) org = iOrigin; else org = *autoOrg; Line l = getLine(pos, org); pos = l.project(pos); if (iSnap & ESnapBd) snapAngularIntersection(pos, l, page, view, snapDist); return ESnapAngle; } // we are not in any angular snapping mode return simpleSnap(pos, page, view, snapDist, tool); } //! Set axis origin and direction from edge near mouse. /*! Returns \c true if successful. */ bool Snap::setEdge(const Vector &pos, const Page *page, int view) noexcept { // bound cannot be too small, as distance to Bezier // is computed based on an approximation of precision 1.0 CollectSegs segs(pos, 2.0, page, view); if (!segs.iSegs.empty()) { Segment seg = segs.iSegs.back(); Line l = seg.line(); iOrigin = l.project(pos); Vector dir = l.dir(); if ((iOrigin - seg.iP).len() > (iOrigin - seg.iQ).len()) dir = -dir; iDir = dir.angle(); return true; } else if (!segs.iArcs.empty()) { Arc arc = segs.iArcs.back(); Angle alpha; (void) arc.distance(pos, 3.0, iOrigin, alpha); iDir = (arc.iM.linear() * Vector(Angle(alpha + IpeHalfPi))).angle(); return true; } else if (!segs.iBeziers.empty()) { Bezier bez = segs.iBeziers.back(); double t; double bound = 2.0; if (!bez.snap(pos, t, iOrigin, bound)) return false; iDir = bez.tangent(t).angle(); return true; } return false; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipepage.cpp0000644000175000017500000005014413561570220016411 0ustar otfriedotfried// -------------------------------------------------------------------- // A page of a document. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepage.h" #include "ipegroup.h" #include "ipereference.h" #include "ipepainter.h" #include "ipeiml.h" #include "ipeutils.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::Page \ingroup doc \brief An Ipe document page. Its main ingredients are a sequence of Objects (with selection state, layer, and a cached bounding box), a set of Layers, and a sequence of Views. Each object on a Page belongs to one of the layers of the page. Layers are orthogonal to the back-to-front ordering of objects (in particular, they are not "layered" - the word is a misnomer). The "layer" is really just another attribute of the object. - Layers are either editable or locked. Objects in a locked layer cannot be selected, and a locked layer cannot be made active in the UI. This more or less means that the contents of such a layer cannot be modified---but that's a consequence of the UI, Ipelib contains no special handling of locked layers. - A layer may have snapping on or off---objects will behave magnetically only if their layer has snapping on. A Page is presented in a number of \e views. Each view presents some of the layers of the page. In addition, each view has an active layer (where objects are added when this view is shown in the UI), and possibly a transition effect (Acrobat Reader eye candy). A Page can be copied and assigned. The operation takes time linear in the number of top-level object on the page. */ //! The default constructor creates a new empty page. /*! This page still needs a layer and a view to be usable! */ Page::Page() : iTitle() { iUseTitle[0] = iUseTitle[1] = false; iMarked = true; } //! Create a new empty page with standard settings. /*! This is an empty page with layer 'alpha' and a single view. */ Page *Page::basic() { // Create one empty page Page *page = new Page; page->addLayer("alpha"); page->insertView(0, "alpha"); page->setVisible(0, "alpha", true); return page; } // -------------------------------------------------------------------- //! save page in XML format. void Page::saveAsXml(Stream &stream) const { stream << "\n"; if (!iNotes.empty()) { stream << ""; stream.putXmlString(iNotes); stream << "\n"; } for (int i = 0; i < countLayers(); ++i) { stream << "\n"; } for (int i = 0; i < countViews(); ++i) { stream << "\n"; } int currentLayer = -1; for (ObjSeq::const_iterator it = iObjects.begin(); it != iObjects.end(); ++it) { String l; if (it->iLayer != currentLayer) { currentLayer = it->iLayer; l = layer(currentLayer); } it->iObject->saveAsXml(stream, l); } stream << "\n"; } // -------------------------------------------------------------------- Page::SLayer::SLayer(String name) { iName = name; iFlags = 0; } //! Set locking of layer \a i. void Page::setLocked(int i, bool flag) { iLayers[i].iFlags &= ~ELocked; if (flag) iLayers[i].iFlags |= ELocked; } //! Set snapping of layer \a i. void Page::setSnapping(int i, bool flag) { iLayers[i].iFlags &= ~ENoSnapping; if (!flag) iLayers[i].iFlags |= ENoSnapping; } //! Add a new layer. void Page::addLayer(String name) { iLayers.push_back(SLayer(name)); iLayers.back().iVisible.resize(countViews()); for (int i = 0; i < countViews(); ++i) iLayers.back().iVisible[i] = false; } //! Find layer with given name. /*! Returns -1 if not found. */ int Page::findLayer(String name) const { for (int i = 0; i < countLayers(); ++i) if (layer(i) == name) return i; return -1; } const char * const layerNames[] = { "alpha", "beta", "gamma", "delta", "epsilon", "zeta", "eta", "theta", "iota", "kappa", "lambda", "mu", "nu", "xi", "omicron", "pi", "rho", "sigma", "tau", "upsilon", "phi", "chi", "psi", "omega" }; //! Add a new layer with unique name. void Page::addLayer() { for (int i = 0; i < int(sizeof(layerNames)/sizeof(const char *)); ++i) { if (findLayer(layerNames[i]) < 0) { addLayer(layerNames[i]); return; } } char name[20]; int i = 1; for (;;) { std::sprintf(name, "alpha%d", i); if (findLayer(name) < 0) { addLayer(name); return; } i++; } } //! Moves the position of a layer in the layer list. void Page::moveLayer(int index, int newIndex) { assert(0 <= index && index < int(iLayers.size()) && 0 <= newIndex && newIndex < int(iLayers.size())); SLayer layer = iLayers[index]; iLayers.erase(iLayers.begin() + index); iLayers.insert(iLayers.begin() + newIndex, layer); // Layer of object needs to be decreased by one if > index // Then increase by one if >= newIndex // If == index, then replace by newIndex for (ObjSeq::iterator it = iObjects.begin(); it != iObjects.end(); ++it) { int k = it->iLayer; if (k == index) { k = newIndex; } else { if (k > index) k -= 1; if (k >= newIndex) k += 1; } it->iLayer = k; } } //! Removes an empty layer from the page. /*! All objects are adjusted. Panics if there are objects in the deleted layer, of if it is the only layer. */ void Page::removeLayer(String name) { int index = findLayer(name); assert(iLayers.size() > 1 && index >= 0); for (ObjSeq::iterator it = iObjects.begin(); it != iObjects.end(); ++it) { int k = it->iLayer; assert(k != index); if (k > index) it->iLayer = k-1; } iLayers.erase(iLayers.begin() + index); } //! Return number of objects in each layer void Page::objectsPerLayer(std::vector &objcounts) const { objcounts.clear(); for (int i = 0; i < countLayers(); ++i) objcounts.push_back(0); for (const auto & obj : iObjects) objcounts[obj.iLayer] += 1; } //! Rename a layer. void Page::renameLayer(String oldName, String newName) { int l = findLayer(oldName); if (l < 0) return; iLayers[l].iName = newName; } //! Returns a precise bounding box for the artwork on the page. /*! This is meant to be used as the bounding box in PDF output. It is computed by rendering all objects on the page that are visible in at least one view, plus all objects in a layer named "BBOX" (even if that is not visible), using a BBoxPainter. */ Rect Page::pageBBox(const Cascade *sheet) const { // make table with all layers to be rendered std::vector layers; for (int l = 0; l < countLayers(); ++l) { bool vis = false; if (layer(l) == "BBOX") vis = true; else for (int vno = 0; !vis && vno < countViews(); ++vno) vis = visible(vno, l); layers.push_back(vis); } BBoxPainter bboxPainter(sheet); for (int i = 0; i < count(); ++i) { if (layers[layerOf(i)]) object(i)->draw(bboxPainter); } return bboxPainter.bbox(); } //! Returns a precise bounding box for the artwork in the view. /*! This is meant to be used as the bounding box in PDF and EPS output. It is computed by rendering all objects in the page using a BBoxPainter. */ Rect Page::viewBBox(const Cascade *sheet, int view) const { BBoxPainter bboxPainter(sheet); for (int i = 0; i < count(); ++i) { if (objectVisible(view, i)) object(i)->draw(bboxPainter); } return bboxPainter.bbox(); } //! Snapping occurs if the layer is visible and has snapping enabled. bool Page::objSnapsInView(int objNo, int view) const noexcept { int layer = layerOf(objNo); return hasSnapping(layer) && visible(view, layer); } // -------------------------------------------------------------------- //! Set effect of view. /*! Panics if \a sym is not symbolic. */ void Page::setEffect(int index, Attribute sym) { assert(sym.isSymbolic()); iViews[index].iEffect = sym; } //! Set active layer of view. void Page::setActive(int index, String layer) { assert(findLayer(layer) >= 0); iViews[index].iActive = layer; } //! Set visibility of layer \a layer in view \a view. void Page::setVisible(int view, String layer, bool vis) { int index = findLayer(layer); assert(index >= 0); iLayers[index].iVisible[view] = vis; } //! Insert a new view at index \a i. void Page::insertView(int i, String active) { iViews.insert(iViews.begin() + i, SView()); iViews[i].iActive = active; iViews[i].iMarked = false; for (int l = 0; l < countLayers(); ++l) iLayers[l].iVisible.insert(iLayers[l].iVisible.begin() + i, false); } //! Remove the view at index \a i. void Page::removeView(int i) { iViews.erase(iViews.begin() + i); for (int l = 0; l < countLayers(); ++l) iLayers[l].iVisible.erase(iLayers[l].iVisible.begin() + i); } //! Remove all views of this page. void Page::clearViews() { iViews.clear(); for (LayerSeq::iterator it = iLayers.begin(); it != iLayers.end(); ++it) it->iVisible.clear(); } void Page::setMarkedView(int index, bool marked) { iViews[index].iMarked = marked; } int Page::countMarkedViews() const { int count = 0; for (int i = 0; i < countViews(); ++i) { if (markedView(i)) ++count; } return (count == 0) ? 1 : count; } //! Return index of view with given number or name. /*! Input numbers are one-based. Returns -1 if no such view exists. */ int Page::findView(String s) const { if (s.empty()) return -1; if ('0' <= s[0] && s[0] <= '9') { int no = Lex(s).getInt(); if (no <= 0 || no > countViews()) return -1; return no - 1; } for (int i = 0; i < countViews(); ++i) { if (s == viewName(i)) return i; } return -1; } // -------------------------------------------------------------------- Page::SObject::SObject() { iObject = nullptr; iLayer = 0; iSelect = ENotSelected; } Page::SObject::SObject(const SObject &rhs) : iSelect(rhs.iSelect), iLayer(rhs.iLayer) { if (rhs.iObject) iObject = rhs.iObject->clone(); else iObject = nullptr; } Page::SObject &Page::SObject::operator=(const SObject &rhs) { if (this != &rhs) { delete iObject; iSelect = rhs.iSelect; iLayer = rhs.iLayer; if (rhs.iObject) iObject = rhs.iObject->clone(); else iObject = nullptr; iBBox.clear(); // invalidate } return *this; } Page::SObject::~SObject() { delete iObject; } // -------------------------------------------------------------------- //! Insert a new object at index \a i. /*! Takes ownership of the object. */ void Page::insert(int i, TSelect select, int layer, Object *obj) { iObjects.insert(iObjects.begin() + i, SObject()); SObject &s = iObjects[i]; s.iSelect = select; s.iLayer = layer; s.iObject = obj; } //! Append a new object. /*! Takes ownership of the object. */ void Page::append(TSelect select, int layer, Object *obj) { iObjects.push_back(SObject()); SObject &s = iObjects.back(); s.iSelect = select; s.iLayer = layer; s.iObject = obj; } //! Remove the object at index \a i. void Page::remove(int i) { iObjects.erase(iObjects.begin() + i); } //! Replace the object at index \a i. /*! Takes ownership of \a obj. */ void Page::replace(int i, Object *obj) { delete iObjects[i].iObject; iObjects[i].iObject = obj; invalidateBBox(i); } //! Return distance between object at index \a i and \a v. /*! But may just return \a bound if the distance is larger. This function uses the cached bounded box, and is faster than calling Object::distance directly. */ double Page::distance(int i, const Vector &v, double bound) const { if (bbox(i).certainClearance(v, bound)) return bound; return object(i)->distance(v, Matrix(), bound); } //! Transform the object at index \a i. /*! Use this function instead of calling Object::setMatrix directly, as the latter doesn't invalidate the cached bounding box. */ void Page::transform(int i, const Matrix &m) { invalidateBBox(i); object(i)->setMatrix(m * object(i)->matrix()); } //! Invalidate the bounding box at index \a i (the object is somehow changed). void Page::invalidateBBox(int i) const { iObjects[i].iBBox.clear(); } //! Return a bounding box for the object at index \a i. /*! This is a bounding box including the control points of the object. If you need a tight bounding box, you'll need to use the Object directly. The Page caches the box the first time it is computed. Make sure you call Page::transform instead of Object::setMatrix, as the latter would not invalidate the bounding box. */ Rect Page::bbox(int i) const { if (iObjects[i].iBBox.isEmpty()) iObjects[i].iObject->addToBBox(iObjects[i].iBBox, Matrix(), true); return iObjects[i].iBBox; } //! Compute possible vertex snapping position for object at index \a i. /*! Looks only for positions closer than \a bound. If successful, modifies \a pos and \a bound. */ void Page::snapVtx(int i, const Vector &mouse, Vector &pos, double &bound) const { if (bbox(i).certainClearance(mouse, bound)) return; object(i)->snapVtx(mouse, Matrix(), pos, bound); } //! Compute possible control point snapping position for object at index \a i. /*! Looks only for positions closer than \a bound. If successful, modifies \a pos and \a bound. */ void Page::snapCtl(int i, const Vector &mouse, Vector &pos, double &bound) const { if (bbox(i).certainClearance(mouse, bound)) return; object(i)->snapCtl(mouse, Matrix(), pos, bound); } //! Compute possible boundary snapping position for object at index \a i. /*! Looks only for positions closer than \a bound. If successful, modifies \a pos and \a bound. */ void Page::snapBnd(int i, const Vector &mouse, Vector &pos, double &bound) const { if (bbox(i).certainClearance(mouse, bound)) return; object(i)->snapBnd(mouse, Matrix(), pos, bound); } //! Set attribute \a prop of object at index \a i to \a value. /*! This method automatically invalidates the bounding box if a ETextSize property is actually changed. */ bool Page::setAttribute(int i, Property prop, Attribute value) { bool changed = object(i)->setAttribute(prop, value); if (changed && (prop == EPropTextSize || prop == EPropTransformations)) invalidateBBox(i); return changed; } // -------------------------------------------------------------------- //! Return section title at \a level. /*! Level 0 is the section, level 1 the subsection. */ String Page::section(int level) const { if (iUseTitle[level]) return title(); else return iSection[level]; } //! Set the section title at \a level. /*! Level 0 is the section, level 1 the subsection. If \a useTitle is \c true, then \a name is ignored, and the section title will be copied from the page title (and further changes to the page title are automatically reflected). */ void Page::setSection(int level, bool useTitle, String name) { iUseTitle[level] = useTitle; iSection[level] = useTitle ? String() : name; } //! Set the title of this page. /*! An empty title is not displayed. */ void Page::setTitle(String title) { iTitle = title; iTitleObject.setText(String("\\PageTitle{") + title + "}"); } //! Return title of this page. String Page::title() const { return iTitle; } //! Set the notes of this page. void Page::setNotes(String notes) { iNotes = notes; } //! Set if page is marked for printing. void Page::setMarked(bool marked) { iMarked = marked; } //! Return Text object representing the title text. /*! Return 0 if no title is set. Ownership of object remains with Page. */ const Text *Page::titleText() const { if (title().empty()) return nullptr; return &iTitleObject; } //! Apply styling to title text object. void Page::applyTitleStyle(const Cascade *sheet) { if (title().empty()) return; const StyleSheet::TitleStyle *ts = sheet->findTitleStyle(); if (!ts) return; iTitleObject.setMatrix(Matrix(ts->iPos)); iTitleObject.setSize(ts->iSize); iTitleObject.setStroke(ts->iColor); iTitleObject.setHorizontalAlignment(ts->iHorizontalAlignment); iTitleObject.setVerticalAlignment(ts->iVerticalAlignment); } // -------------------------------------------------------------------- //! Return index of primary selection. /*! Returns -1 if there is no primary selection. */ int Page::primarySelection() const { for (int i = 0; i < count(); ++i) if (select(i) == EPrimarySelected) return i; return -1; } //! Returns true iff any object on the page is selected. bool Page::hasSelection() const { for (int i = 0; i < count(); ++i) if (select(i)) return true; return false; } //! Deselect all objects. void Page::deselectAll() { for (int i = 0; i < count(); ++i) setSelect(i, ENotSelected); } /*! If no object is the primary selection, make the topmost secondary selection the primary one. */ void Page::ensurePrimarySelection() { for (int i = 0; i < count(); ++i) if (select(i) == EPrimarySelected) return; for (int i = count() - 1; i >= 0; --i) { if (select(i) == ESecondarySelected) { setSelect(i, EPrimarySelected); return; } } } //! Copy whole page with bitmaps as into the stream. void Page::saveAsIpePage(Stream &stream) const { BitmapFinder bmFinder; bmFinder.scanPage(this); stream << "\n"; int id = 1; for (std::vector::const_iterator it = bmFinder.iBitmaps.begin(); it != bmFinder.iBitmaps.end(); ++it) { Bitmap bm = *it; bm.saveAsXml(stream, id); bm.setObjNum(id); ++id; } saveAsXml(stream); stream << "\n"; } //! Copy selected objects as into the stream. void Page::saveSelection(Stream &stream) const { BitmapFinder bmFinder; for (int i = 0; i < count(); ++i) { if (select(i)) object(i)->accept(bmFinder); } stream << "\n"; int id = 1; for (std::vector::const_iterator it = bmFinder.iBitmaps.begin(); it != bmFinder.iBitmaps.end(); ++it) { Bitmap bm = *it; bm.saveAsXml(stream, id); bm.setObjNum(id); ++id; } for (int i = 0; i < count(); ++i) { if (select(i)) object(i)->saveAsXml(stream, String()); } stream << "\n"; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/iperesources.cpp0000644000175000017500000001543013561570220017506 0ustar otfriedotfried// -------------------------------------------------------------------- // PDF Resources // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "iperesources.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::PdfResourceBase * \ingroup base * \brief Base class providing access to PDF objects. */ PdfResourceBase::PdfResourceBase() : iPageResources(new PdfDict) { // nothing } PdfResourceBase::~PdfResourceBase() { // nothing } const PdfObj *PdfResourceBase::getDeep(const PdfDict *d, String key) const noexcept { if (!d) return nullptr; const PdfObj *obj = d->get(key, nullptr); if (obj && obj->ref()) obj = object(obj->ref()->value()); return obj; } const PdfDict *PdfResourceBase::getDict(const PdfDict *d, String key) const noexcept { const PdfObj *obj = getDeep(d, key); if (obj) return obj->dict(); return nullptr; } const PdfDict *PdfResourceBase::resourcesOfKind(String kind) const noexcept { const PdfObj *obj = iPageResources->get(kind, nullptr); if (!obj) return nullptr; else return obj->dict(); } const PdfDict *PdfResourceBase::findResource(String kind, String name) const noexcept { return getDict(resourcesOfKind(kind), name); } const PdfDict *PdfResourceBase::findResource(const PdfDict *xf, String kind, String name) const noexcept { const PdfDict *res = getDict(xf, "Resources"); const PdfDict *kindd = getDict(res, kind); return getDict(kindd, name); } // -------------------------------------------------------------------- /*! \class ipe::PdfFileResource * \ingroup base * \brief PDF resources directly from a PdfFile. */ PdfFileResources::PdfFileResources(const PdfFile *file) : iPdf(file) { // nothing } const PdfObj *PdfFileResources::object(int num) const noexcept { return iPdf->object(num); } // -------------------------------------------------------------------- /*! \class ipe::PdfResources * \ingroup base * \brief All the resources needed by the text objects in the document. */ PdfResources::PdfResources() { // nothing } void PdfResources::add(int num, PdfFile *file) { if (object(num)) // already present return; std::unique_ptr obj = file->take(num); if (!obj) return; // no such object const PdfObj *q = obj.get(); iObjects[num] = std::move(obj); addIndirect(q, file); iEmbedSequence.push_back(num); // after all its dependencies! } void PdfResources::addIndirect(const PdfObj *q, PdfFile *file) { if (q->array()) { const PdfArray *arr = q->array(); for (int i = 0; i < arr->count(); ++i) addIndirect(arr->obj(i, nullptr), file); } else if (q->dict()) { const PdfDict *dict = q->dict(); for (int i = 0; i < dict->count(); ++i) addIndirect(dict->value(i), file); } else if (q->ref()) add(q->ref()->value(), file); } const PdfObj *PdfResources::object(int num) const noexcept { auto got = iObjects.find(num); if (got != iObjects.end()) return got->second.get(); else return nullptr; } const PdfDict *PdfResources::baseResources() const noexcept { return iPageResources.get(); } //! Collect (recursively) all the given resources (of the one latex page). //! Takes ownership of all the scanned objects. bool PdfResources::collect(const PdfDict *resd, PdfFile *file) { /* A resource is a dictionary, like this: /Font << /F8 9 0 R /F10 18 0 R >> /ProcSet [ /PDF /Text ] */ for (int i = 0; i < resd->count(); ++i) { String key = resd->key(i); if (key == "Ipe" || key == "ProcSet") continue; const PdfObj *obj = resd->get(key, file); const PdfDict *rd = obj->dict(); if (!rd) { ipeDebug("Resource %s is not a dictionary", key.z()); return false; } PdfDict *d = new PdfDict; for (int j = 0; j < rd->count(); ++j) { if (!addToResource(d, rd->key(j), rd->value(j), file)) return false; } iPageResources->add(key, d); } return true; } bool PdfResources::addToResource(PdfDict *d, String key, const PdfObj *el, PdfFile *file) { if (el->name()) d->add(key, new PdfName(el->name()->value())); else if (el->number()) d->add(key, new PdfNumber(el->number()->value())); else if (el->ref()) { int ref = el->ref()->value(); d->add(key, new PdfRef(ref)); add(ref, file); // take all dependencies from file } else if (el->array()) { PdfArray *a = new PdfArray; for (int i = 0; i < el->array()->count(); ++i) { const PdfObj *al = el->array()->obj(i, nullptr); if (al->name()) a->append(new PdfName(al->name()->value())); else if (al->number()) a->append(new PdfNumber(al->number()->value())); else { ipeDebug("Surprising type in resource: %s", el->repr().z()); return false; } } d->add(key, a); } else if (el->dict()) { const PdfDict *eld = el->dict(); PdfDict *d1 = new PdfDict; for (int i = 0; i < eld->count(); ++i) { if (!addToResource(d1, eld->key(i), eld->value(i), file)) return false; } d->add(key, d1); } return true; } void PdfResources::show() const noexcept { ipeDebug("Resources:\n%s", iPageResources->repr().z()); } // -------------------------------------------------------------------- void PdfResources::addPageNumber(SPageNumber &pn) noexcept { iPageNumbers.emplace_back(std::move(pn)); } const Text *PdfResources::pageNumber(int page, int view) const noexcept { auto it = std::find_if(iPageNumbers.begin(), iPageNumbers.end(), [page, view](const SPageNumber &pn) { return pn.page == page && pn.view == view; } ); if (it == iPageNumbers.end()) return nullptr; else return it->text.get(); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipeattributes.cpp0000644000175000017500000003524413561570220017667 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Ipe object attributes // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeattributes.h" // -------------------------------------------------------------------- /*! \defgroup attr Ipe Attributes \brief Attributes for Ipe objects. Ipe objects have attributes such as color, line width, dash pattern, etc. Most attributes can be symbolic (the need to be looked up in a style sheet before rendering) or absolute. The Color class represents absolute values of colors. The class Attribute encapsulates all attributes that can be either symbolic or absolute. The Lua bindings for attributes are described \ref luaobj "here". */ // -------------------------------------------------------------------- namespace ipe { const char *const kind_names[] = { "pen", "symbolsize", "arrowsize", "color", "dashstyle", "textsize", "textstretch", "textstyle", "labelstyle", "gridsize", "anglesize", "opacity", "tiling", "symbol", "gradient", "effect", nullptr }; const char *const property_names[] = { "pen", "symbolsize", "farrow", "rarrow", "farrowsize", "rarrowsize", "farrowshape", "rarrowshape", "stroke", "fill", "markshape", "pathmode", "dashstyle", "textsize", "textstyle", "labelstyle", "opacity", "strokeopacity", "tiling", "gradient", "horizontalalignment", "verticalalignment", "linejoin", "linecap", "fillrule", "pinned", "transformations", "transformabletext", "minipage", "width", "decoration", nullptr }; } using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::Color \ingroup attr \brief An absolute RGB color. */ //! Construct a color. /*! Arguments \a red, \a green, \a blue range from 0 to 1000. */ Color::Color(int red, int green, int blue) { iRed = Fixed::fromInternal(red); iGreen = Fixed::fromInternal(green); iBlue = Fixed::fromInternal(blue); } //! Save to stream. void Color::save(Stream &stream) const { if (isGray()) stream << iRed; else stream << iRed << " " << iGreen << " " << iBlue; } //! Save to stream in long format. /*! The RGB components are saved separately even for gray colors. */ void Color::saveRGB(Stream &stream) const { stream << iRed << " " << iGreen << " " << iBlue; } //! is it an absolute gray value? bool Color::isGray() const { return (iRed == iGreen && iRed == iBlue); } bool Color::operator==(const Color &rhs) const { return (iRed == rhs.iRed) && (iGreen == rhs.iGreen) && (iBlue == rhs.iBlue); } // -------------------------------------------------------------------- /*! \class ipe::Effect \ingroup attr \brief Effect that Acrobat Reader will show on page change. Acrobat Reader and other PDF viewers can show a special effect when a new page of the document is shown. This class describes such an effect. */ //! Construct default effect. Effect::Effect() { iEffect = ENormal; iDuration = 0; iTransitionTime = 1; } //! Write part of page dictionary. /*! Write part of page dictionary indicating effect, including the two keys /Dur and /Trans. */ void Effect::pageDictionary(Stream &stream) const { if (iDuration > 0) stream << "/Dur " << iDuration << "\n"; if (iEffect != ENormal) { stream << "/Trans << /D " << iTransitionTime << " /S "; switch (iEffect) { case ESplitHI: stream << "/Split /Dm /H /M /I"; break; case ESplitHO: stream << "/Split /Dm /H /M /O"; break; case ESplitVI: stream << "/Split /Dm /V /M /I"; break; case ESplitVO: stream << "/Split /Dm /V /M /O"; break; case EBlindsH: stream << "/Blinds /Dm /H"; break; case EBlindsV: stream << "/Blinds /Dm /V"; break; case EBoxI: stream << "/Box /M /I"; break; case EBoxO: stream << "/Box /M /O"; break; case EWipeLR: stream << "/Wipe /Di 0"; break; case EWipeBT: stream << "/Wipe /Di 90"; break; case EWipeRL: stream << "/Wipe /Di 180"; break; case EWipeTB: stream << "/Wipe /Di 270"; break; case EDissolve: stream << "/Dissolve"; break; case EGlitterLR: stream << "/Glitter /Di 0"; break; case EGlitterTB: stream << "/Glitter /Di 270"; break; case EGlitterD: stream << "/Glitter /Di 315"; break; case ENormal: break; // to satisfy compiler } stream << " >>\n"; } } // -------------------------------------------------------------------- /*! \class ipe::Repository \ingroup attr \brief Repository of strings. Ipe documents can use symbolic attributes, such as 'normal', 'fat', or 'thin' for line thickness, or 'red', 'navy', 'turquoise' for color, as well as absolute attributes such as "[3 1] 0" for a dash pattern. To avoid storing these common strings hundreds of times, Repository keeps a repository of strings. Inside an Object, strings are replaced by indices into the repository. The Repository is a singleton object. It is created the first time it is used. You obtain access to the repository using get(). */ // pointer to singleton object Repository *Repository::singleton = nullptr; //! Constructor. Repository::Repository() { // put certain strings at index 0 .. iStrings.push_back("normal"); iStrings.push_back("undefined"); iStrings.push_back("Background"); iStrings.push_back("sym-stroke"); iStrings.push_back("sym-fill"); iStrings.push_back("sym-pen"); iStrings.push_back("arrow/normal(spx)"); iStrings.push_back("opaque"); iStrings.push_back("arrow/arc(spx)"); iStrings.push_back("arrow/farc(spx)"); iStrings.push_back("arrow/ptarc(spx)"); iStrings.push_back("arrow/fptarc(spx)"); } //! Get pointer to singleton Repository. Repository *Repository::get() { if (!singleton) { singleton = new Repository(); } return singleton; } //! Return string with given index. String Repository::toString(int index) const { return iStrings[index]; } //! Return index of given string. /*! The string is added to the repository if it doesn't exist yet. */ int Repository::toIndex(String str) { assert(!str.empty()); std::vector::const_iterator it = std::find(iStrings.begin(), iStrings.end(), str); if (it != iStrings.end()) return (it - iStrings.begin()); iStrings.push_back(str); return iStrings.size() - 1; } //! Destroy repository object. void Repository::cleanup() { delete singleton; singleton = nullptr; } // -------------------------------------------------------------------- /*! \class ipe::Attribute \ingroup attr \brief An attribute of an Ipe Object. An attribute is either an absolute value or a symbolic name that has to be looked up in a StyleSheet. All string values are replaced by indices into a Repository (that applies both to symbolic names and to absolute values that are strings). All other values are stored directly inside the attribute, either as a Fixed or a Color. There are five different kinds of Attribute objects: - if isSymbolic() is true, index() returns the index into the repository, and string() returns the symbolic name. - if isColor() is true, color() returns an absolute RGB color. - if isNumeric() is true, number() returns an absolute scalar value. - if isEnum() is true, the attribute represents an enumeration value. - otherwise, isString() is true, and index() returns the index into the repository (for a string expressing the absolute value of the attribute), and string() returns the string itself. */ /* if (n & 0xc000.0000) == 0x0000.0000 -> color in 0x3fff.ffff if (n & 0xc000.0000) == 0x4000.0000 -> fixed in 0x3fff.ffff if (n & 0xe000.0000) == 0x8000.0000 -> symbolic string in 0x1fffffff if (n & 0xe000.0000) == 0xc000.0000 -> absolute string in 0x1fffffff if (n & 0xe000.0000) == 0xe000.0000 -> enum in 0x1fff.ffff */ //! Create an attribute with absolute color. Attribute::Attribute(Color color) { iName = (color.iRed.internal() << 20) + (color.iGreen.internal() << 10) + (color.iBlue.internal()); } //! Create an attribute with string value. Attribute::Attribute(bool symbolic, int index) { iName = index | (symbolic ? ESymbolic : EAbsolute); } //! Create an absolute numeric attribute. Attribute::Attribute(Fixed value) { iName = EFixed | value.internal(); } //! Create an attribute with string value. Attribute::Attribute(bool symbolic, String name) { int index = Repository::get()->toIndex(name); iName = index | (symbolic ? ESymbolic : EAbsolute); } static const char * const enumeration_name[] = { "false", "true", // bool "left", "right", "hcenter", // halign "bottom", "baseline", "top", "vcenter", // valign "normal", "miter", "round", "bevel", // linejoin "normal", "butt", "round", "square", // linecap "normal", "wind", "evenodd", // fillrule "none", "horizontal", "vertical", "fixed", // pinned "translations", "rigid", "affine", // transformations "stroked", "strokedfilled", "filled", // pathmode }; //! Return string representing the attribute. String Attribute::string() const { if (isSymbolic() || isString()) return Repository::get()->toString(index()); String str; StringStream stream(str); if (isNumber()) { stream << number(); } else if (isColor()) { stream << color(); } else { // is enumeration value stream << enumeration_name[index()]; } return str; } //! Return value of absolute numeric attribute. Fixed Attribute::number() const { assert(isNumber()); return Fixed::fromInternal(iName & EFixedMask); } //! Return absolute color. Color Attribute::color() const { assert(isColor()); Color col; col.iRed = Fixed::fromInternal(iName >> 20); col.iGreen = Fixed::fromInternal((iName >> 10) & 0x3ff); col.iBlue = Fixed::fromInternal(iName & 0x3ff); return col; } //! Construct a color from a string. /*! If only a single number is given, this is a gray value, otherwise red, green, and blue components must be given. */ Color::Color(String str) { Lex st(str); st >> iRed >> iGreen; if (st.eos()) iGreen = iBlue = iRed; else st >> iBlue; } //! Make a color attribute. /*! If the string starts with a letter, make a symbolic attribute. Otherwise, it's either a single gray value (0.0 to 1.0), or the three red, green, and blue components, separated by spaces. If it's an empty string, return \a deflt. */ Attribute Attribute::makeColor(String str, Attribute deflt) { if (str.empty()) return deflt; else if (('a' <= str[0] && str[0] <= 'z') || ('A' <= str[0] && str[0] <= 'Z')) return Attribute(true, str); else return Attribute(Color(str)); } //! Make a scalar attribute. /*! If \a str is empty, simply return \a deflt. If \a str starts with a letter, make a symbolic attribute. Otherwise, must be a number. */ Attribute Attribute::makeScalar(String str, Attribute deflt) { if (str.empty()) { return deflt; } else if (('a' <= str[0] && str[0] <= 'z') || ('A' <= str[0] && str[0] <= 'Z')) { return Attribute(true, str); } else { return Attribute(Lex(str).getFixed()); } } //! Construct dash style attribute from string. /*! Strings starting with '[' create an absolute dash style. The empty string is equivalent to 'normal'. Any other string creates a symbolic dash style. */ Attribute Attribute::makeDashStyle(String str) { if (str.empty()) return Attribute::NORMAL(); else if (str[0] == '[') return Attribute(false, str); else return Attribute(true, str); } //! Construct text size attribute from string. /*! String starting with digit creates a numeric absolute value, string starting with letter creates symbolic text size, anything else creates absolute (string) text size. The empty string is treated like "normal". */ Attribute Attribute::makeTextSize(String str) { if (str.empty()) return Attribute::NORMAL(); else if ('0' <= str[0] && str[0] <= '9') return Attribute(Lex(str).getFixed()); else if (('a' <= str[0] && str[0] <= 'z') || ('A' <= str[0] && str[0] <= 'Z')) return Attribute(true, str); else return Attribute(false, str); } //! Return a standard value for attribute of \a kind. /*! The value is used if the stylesheet doesn't define a symbolic attribute used in the document. */ Attribute Attribute::normal(Kind kind) { switch (kind) { case EPen: case EArrowSize: case ESymbolSize: case ETextSize: case ETextStyle: case EDashStyle: default: return Attribute::NORMAL(); case ETextStretch: case EOpacity: return Attribute::ONE(); case EColor: return Attribute::BLACK(); case EGridSize: return Attribute(Fixed(8)); case EAngleSize: return Attribute(Fixed(45)); } } // -------------------------------------------------------------------- /*! \class ipe::AllAttributes \ingroup attr \brief Collection of all object attributes. */ //! Constructor sets default values. AllAttributes::AllAttributes() { iStroke = iFill = Attribute::BLACK(); iPathMode = EStrokedOnly; iDashStyle = Attribute::NORMAL(); iPen = iFArrowSize = iRArrowSize = Attribute::NORMAL(); iFArrowShape = iRArrowShape = Attribute::ARROW_NORMAL(); iFArrow = iRArrow = false; iSymbolSize = iTextSize = iTextStyle = iLabelStyle = Attribute::NORMAL(); iTransformableText = false; iVerticalAlignment = EAlignBaseline; iHorizontalAlignment = EAlignLeft; iPinned = ENoPin; iTransformations = ETransformationsAffine; iLineJoin = EDefaultJoin; iLineCap = EDefaultCap; iFillRule = EDefaultRule; iOpacity = Attribute::OPAQUE(); iStrokeOpacity = Attribute::OPAQUE(); iTiling = Attribute::NORMAL(); iGradient = Attribute::NORMAL(); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipeiml.cpp0000644000175000017500000005023213561570220016254 0ustar otfriedotfried// -------------------------------------------------------------------- // IpeImlParser // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeiml.h" #include "ipeobject.h" #include "ipegroup.h" #include "ipepage.h" #include "ipefactory.h" #include "ipestyle.h" #include "ipereference.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::ImlParser \ingroup high \brief XML Parser for Ipe documents and style sheets. A recursive descent parser for the XML streams. After experimenting with various XML parsing frameworks, this turned out to work best for Ipe. */ ImlParser::ImlParser(DataSource &source) : XmlParser(source) { // nothing } //! XML contents can refer to data in PDF. /*! If the XML stream is embedded in a PDF file, XML contents can refer to PDF objects. A derived parser must implement this method to access PDF data. It is assumed that PDF object \a objNum is a stream. Its contents (uncompressed!) is returned in a buffer. */ Buffer ImlParser::pdfStream(int /* objNum */) { return Buffer(); } //! Read a complete document from IML stream. /*! Returns an error code. */ int ImlParser::parseDocument(Document &doc) { Document::SProperties properties = doc.properties(); String tag = parseToTag(); if (tag == "?xml") { XmlAttributes attr; if (!parseAttributes(attr, true)) return ESyntaxError; tag = parseToTag(); } if (tag != "ipe") return ESyntaxError; XmlAttributes attr; if (!parseAttributes(attr)) return ESyntaxError; Lex versLex(attr["version"]); int version; versLex >> version; if (version < OLDEST_FILE_FORMAT) return EVersionTooOld; if (version > IPELIB_VERSION) return EVersionTooRecent; attr.has("creator", properties.iCreator); tag = parseToTag(); if (tag == "info") { XmlAttributes att; if (!parseAttributes(att)) return ESyntaxError; properties.iTitle = att["title"]; properties.iAuthor = att["author"]; properties.iSubject = att["subject"]; properties.iKeywords = att["keywords"]; properties.iFullScreen = (att["pagemode"] == "fullscreen"); properties.iNumberPages = (att["numberpages"] == "yes"); properties.iCreated = att["created"]; properties.iModified = att["modified"]; String tex = att["tex"]; if (tex == "pdftex") properties.iTexEngine = LatexType::Pdftex; else if (tex == "xetex") properties.iTexEngine = LatexType::Xetex; else if (tex == "luatex") properties.iTexEngine = LatexType::Luatex; tag = parseToTag(); } if (tag == "preamble") { XmlAttributes att; if (!parseAttributes(att)) return ESyntaxError; if (!parsePCDATA("preamble", properties.iPreamble)) return ESyntaxError; tag = parseToTag(); } // document created by default constructor already has standard stylesheet Cascade *cascade = doc.cascade(); while (tag == "ipestyle" || tag == "bitmap") { if (tag == "ipestyle") { StyleSheet *sheet = new StyleSheet(); if (!parseStyle(*sheet)) { delete sheet; return ESyntaxError; } cascade->insert(0, sheet); } else { // tag == "bitmap" if (!parseBitmap()) return ESyntaxError; } tag = parseToTag(); } while (tag == "page") { // read one page Page *page = new Page; doc.push_back(page); if (!parsePage(*page)) return ESyntaxError; tag = parseToTag(); } doc.setProperties(properties); if (tag != "/ipe") return ESyntaxError; return ESuccess; } //! Parse an Bitmap. /*! On calling, stream must be just past \c bitmap. */ bool ImlParser::parseBitmap() { XmlAttributes att; if (!parseAttributes(att)) return false; String objNumStr; if (att.slash() && att.has("pdfObject", objNumStr)) { Lex lex(objNumStr); Buffer data = pdfStream(lex.getInt()); Buffer alpha; lex.skipWhitespace(); if (!lex.eos()) alpha = pdfStream(lex.getInt()); Bitmap bitmap(att, data, alpha); iBitmaps.push_back(bitmap); } else { String bits; if (!parsePCDATA("bitmap", bits)) return false; Bitmap bitmap(att, bits); iBitmaps.push_back(bitmap); } return true; } //! Parse an Page. /*! On calling, stream must be just past \c page. */ bool ImlParser::parsePage(Page &page) { XmlAttributes att; if (!parseAttributes(att)) return false; String str; if (att.has("title", str)) page.setTitle(str); if (att.has("section", str)) page.setSection(0, str.empty(), str); else page.setSection(0, false, String()); if (att.has("subsection", str)) page.setSection(1, str.empty(), str); else page.setSection(1, false, String()); if (att["marked"] == "no") page.setMarked(false); String tag = parseToTag(); if (tag == "notes") { XmlAttributes att; if (!parseAttributes(att)) return false; if (!parsePCDATA("notes", str)) return false; page.setNotes(str); tag = parseToTag(); } while (tag == "layer") { XmlAttributes att; if (!parseAttributes(att)) return false; page.addLayer(att["name"]); if (att["edit"] == "no") page.setLocked(page.countLayers() - 1, true); tag = parseToTag(); } // default layer: 'alpha' if (page.countLayers() == 0) page.addLayer("alpha"); while (tag == "view") { XmlAttributes att; if (!parseAttributes(att)) return false; page.insertView(page.countViews(), att["active"]); String str; if (att.has("effect", str)) page.setEffect(page.countViews() - 1, Attribute(true, str)); Lex st(att["layers"]); st.skipWhitespace(); String last; while (!st.eos()) { last = st.nextToken(); page.setVisible(page.countViews() - 1, last, true); st.skipWhitespace(); } if (!att.has("active", str)) { // if no layer visible must have active attribute if (last.empty()) return false; page.setActive(page.countViews() - 1, last); } if (att["marked"] == "yes") page.setMarkedView(page.countViews() - 1, true); if (att.has("name", str)) page.setViewName(page.countViews() - 1, str); tag = parseToTag(); } // default view: include all layers if (page.countViews() == 0) { int al = 0; while (al < page.countLayers() && page.isLocked(al)) ++al; if (al == page.countLayers()) return false; // no unlocked layer // need to synthesize a view page.insertView(0, page.layer(al)); for (int i = 0; i < page.countLayers(); ++i) page.setVisible(0, page.layer(i), true); } int currentLayer = 0; String layerName; for (;;) { if (tag == "/page") { return true; } if (tag.empty()) return false; Object *obj = parseObject(tag, &page, ¤tLayer); if (!obj) return false; page.insert(page.count(), ENotSelected, currentLayer, obj); tag = parseToTag(); } } //! parse an \c element (used on clipboard). Page *ImlParser::parsePageSelection() { String tag = parseToTag(); if (tag != "ipepage") return nullptr; XmlAttributes attr; if (!parseAttributes(attr)) return nullptr; tag = parseToTag(); while (tag == "bitmap") { if (!parseBitmap()) return nullptr; tag = parseToTag(); } if (tag != "page") return nullptr; std::unique_ptr page(new Page); if (!parsePage(*page)) return nullptr; tag = parseToTag(); if (tag != "/ipepage") return nullptr; return page.release(); } #if 0 //! parse an \c element. /*! An PgObjectSeq is used to own the objects, but selection mode and layer are not set. */ bool ImlParser::parseSelection(PageObjectSeq &seq) { String tag = parseToTag(); if (tag != "ipeselection") return false; XmlAttributes attr; if (!parseAttributes(attr)) return nullptr; tag = parseToTag(); while (tag == "bitmap") { if (!parseBitmap()) return false; tag = parseToTag(); } for (;;) { if (tag == "/ipeselection") return true; Object *obj = parseObject(tag); if (!obj) return false; seq.push_back(PageObject(ENotSelected, 0, obj)); tag = parseToTag(); } } #endif //! parse an Object. /*! On calling, stream must be just past the tag. */ Object *ImlParser::parseObject(String tag, Page *page, int *currentLayer) { if (tag[0] == '/') return nullptr; XmlAttributes attr; if (!parseAttributes(attr)) return nullptr; String layer; if (page && currentLayer && attr.has("layer", layer)) { for (int i = 0; i < page->countLayers(); ++i) { if (page->layer(i) == layer) { *currentLayer = i; break; } } } if (tag == "group") { Group group(attr); for (;;) { String tag = parseToTag(); if (tag == "/group") { return new Group(group); } Object *obj = parseObject(tag); if (!obj) return nullptr; group.push_back(obj); } } String pcdata; if (!attr.slash() && !parsePCDATA(tag, pcdata)) return nullptr; String bitmapId; if (tag == "image" && attr.has("bitmap", bitmapId)) { int objNum = Lex(bitmapId).getInt(); Bitmap bitmap; for (std::vector::const_iterator it = iBitmaps.begin(); it != iBitmaps.end(); ++it) { if (it->objNum() == objNum) { bitmap = *it; break; } } assert(!bitmap.isNull()); return ObjectFactory::createImage(tag, attr, bitmap); } else return ObjectFactory::createObject(tag, attr, pcdata); } static inline bool symbolName(String s) { return (!s.empty() && (('a' <= s[0] && s[0] <= 'z') || ('A' <= s[0] && s[0] <= 'Z'))); } //! Parse a style sheet. /*! On calling, stream must be just past the style tag. */ bool ImlParser::parseStyle(StyleSheet &sheet) { XmlAttributes att; if (!parseAttributes(att)) return false; String name; if (att.has("name", name)) sheet.setName(name); if (att.slash()) return true; String tag = parseToTag(); while (tag != "/ipestyle") { if (tag == "bitmap") { if (!parseBitmap()) return false; } else if (tag == "symbol") { if (!parseAttributes(att)) return false; String tag1 = parseToTag(); Object *obj = parseObject(tag1); if (!obj) return false; Symbol symbol(obj); String name = att["name"]; if (!symbolName(name)) return false; if (att["transformations"] == "rigid") symbol.iTransformations = ETransformationsRigidMotions; else if (att["transformations"] == "translations") symbol.iTransformations = ETransformationsTranslations; if (att["xform"] == "yes") { uint32_t flags = Reference::flagsFromName(name); if ((flags & (Reference::EHasStroke| Reference::EHasFill| Reference::EHasPen| Reference::EHasSize)) == 0) { symbol.iXForm = true; symbol.iTransformations = ETransformationsTranslations; } } Lex snaplex(att["snap"]); while (!snaplex.eos()) { Vector pos; snaplex >> pos.x >> pos.y; snaplex.skipWhitespace(); symbol.iSnap.push_back(pos); } sheet.addSymbol(Attribute(true, name), symbol); if (parseToTag() != "/symbol") return false; } else if (tag == "layout") { if (!parseAttributes(att) || !att.slash()) return false; Layout layout; Lex lex1(att["paper"]); lex1 >> layout.iPaperSize.x >> layout.iPaperSize.y; Lex lex2(att["origin"]); lex2 >> layout.iOrigin.x >> layout.iOrigin.y; Lex lex3(att["frame"]); lex3 >> layout.iFrameSize.x >> layout.iFrameSize.y; layout.iParagraphSkip = Lex(att["skip"]).getDouble(); layout.iCrop = !(att["crop"] == "no"); sheet.setLayout(layout); } else if (tag == "textpad") { if (!parseAttributes(att) || !att.slash()) return false; TextPadding pad; pad.iLeft = Lex(att["left"]).getDouble(); pad.iRight = Lex(att["right"]).getDouble(); pad.iTop = Lex(att["top"]).getDouble(); pad.iBottom = Lex(att["bottom"]).getDouble(); sheet.setTextPadding(pad); } else if (tag == "titlestyle") { if (!parseAttributes(att) || !att.slash()) return false; StyleSheet::TitleStyle ts; ts.iDefined = true; Lex lex1(att["pos"]); lex1 >> ts.iPos.x >> ts.iPos.y; ts.iSize = Attribute::makeScalar(att["size"], Attribute::NORMAL()); ts.iColor = Attribute::makeColor(att["color"], Attribute::BLACK()); ts.iHorizontalAlignment = Text::makeHAlign(att["halign"], EAlignLeft); ts.iVerticalAlignment = Text::makeVAlign(att["valign"], EAlignBaseline); sheet.setTitleStyle(ts); } else if (tag == "pagenumberstyle") { if (!parseAttributes(att)) return false; StyleSheet::PageNumberStyle pns; pns.iDefined = true; Lex lex1(att["pos"]); lex1 >> pns.iPos.x >> pns.iPos.y; pns.iSize = Attribute::makeTextSize(att["size"]); pns.iColor = Attribute::makeColor(att["color"], Attribute::BLACK()); pns.iVerticalAlignment = Text::makeVAlign(att["valign"], EAlignBaseline); pns.iHorizontalAlignment = Text::makeHAlign(att["halign"], EAlignLeft); if (!att.slash() && !parsePCDATA(tag, pns.iText)) return false; sheet.setPageNumberStyle(pns); } else if (tag == "preamble") { if (!parseAttributes(att)) return false; String pcdata; if (!att.slash() && !parsePCDATA(tag, pcdata)) return false; sheet.setPreamble(pcdata); } else if (tag == "pathstyle") { if (!parseAttributes(att) || !att.slash()) return false; String str; if (att.has("cap", str)) sheet.setLineCap(TLineCap(Lex(str).getInt() + 1)); if (att.has("join", str)) sheet.setLineJoin(TLineJoin(Lex(str).getInt() + 1)); if (att.has("fillrule", str)) { if (str == "wind") sheet.setFillRule(EWindRule); else if (str == "eofill") sheet.setFillRule(EEvenOddRule); } } else if (tag == "color") { if (!parseAttributes(att) || !att.slash()) return false; String name = att["name"]; Attribute col = Attribute::makeColor(att["value"], Attribute::NORMAL()); if (!symbolName(name) || !col.isColor()) return false; sheet.add(EColor, Attribute(true, name), col); } else if (tag == "dashstyle") { if (!parseAttributes(att) || !att.slash()) return false; String name = att["name"]; Attribute dash = Attribute::makeDashStyle(att["value"]); if (!symbolName(name) || dash.isSymbolic()) return false; sheet.add(EDashStyle, Attribute(true, name), dash); } else if (tag == "textsize") { if (!parseAttributes(att) || !att.slash()) return false; String name = att["name"]; Attribute value = Attribute::makeTextSize(att["value"]); if (!symbolName(name) || value.isSymbolic()) return false; sheet.add(ETextSize, Attribute(true, name), value); } else if (tag == "textstretch") { if (!parseAttributes(att) || !att.slash()) return false; String name = att["name"]; Attribute value = Attribute::makeScalar(att["value"], Attribute::NORMAL()); if (!symbolName(name) || value.isSymbolic()) return false; sheet.add(ETextStretch, Attribute(true, name), value); } else if (tag == "gradient") { if (!parseAttributes(att) || att.slash()) return false; String name = att["name"]; if (!symbolName(name)) return false; Gradient s; s.iType = (att["type"] == "radial") ? Gradient::ERadial : Gradient::EAxial; Lex lex(att["coords"]); if (s.iType == Gradient::ERadial) lex >> s.iV[0].x >> s.iV[0].y >> s.iRadius[0] >> s.iV[1].x >> s.iV[1].y >> s.iRadius[1]; else lex >> s.iV[0].x >> s.iV[0].y >> s.iV[1].x >> s.iV[1].y; String str; s.iExtend = (att.has("extend",str) && str == "yes"); if (att.has("matrix", str)) s.iMatrix = Matrix(str); tag = parseToTag(); while (tag == "stop") { if (!parseAttributes(att) || !att.slash()) return false; Gradient::Stop st; st.color = Color(att["color"]); st.offset = Lex(att["offset"]).getDouble(); s.iStops.push_back(st); tag = parseToTag(); } if (s.iStops.size() < 2) return false; if (s.iStops.front().offset != 0.0) { s.iStops.insert(s.iStops.begin(), s.iStops.front()); s.iStops.front().offset = 0.0; } if (s.iStops.back().offset != 1.0) { s.iStops.push_back(s.iStops.back()); s.iStops.back().offset = 1.0; } if (s.iStops.front().offset < 0.0 || s.iStops.front().offset > 1.0) return false; for (int i = 1; i < size(s.iStops); ++i) { if (s.iStops[i].offset < s.iStops[i-1].offset) return false; } if (tag != "/gradient") return false; sheet.addGradient(Attribute(true, name), s); } else if (tag == "tiling") { if (!parseAttributes(att) || !att.slash()) return false; String name = att["name"]; if (!symbolName(name)) return false; Tiling s; s.iAngle = Angle::Degrees(Lex(att["angle"]).getDouble()); s.iStep = Lex(att["step"]).getDouble(); s.iWidth = Lex(att["width"]).getDouble(); sheet.addTiling(Attribute(true, name), s); } else if (tag == "effect") { if (!parseAttributes(att) || !att.slash()) return false; String name = att["name"]; if (!symbolName(name)) return false; Effect s; String str; if (att.has("duration", str)) s.iDuration = Lex(str).getInt(); if (att.has("transition", str)) s.iTransitionTime = Lex(str).getInt(); if (att.has("effect", str)) s.iEffect = Effect::TEffect(Lex(str).getInt()); sheet.addEffect(Attribute(true, name), s); } else if (tag == "textstyle") { if (!parseAttributes(att) || !att.slash()) return false; String name = att["name"]; if (!symbolName(name)) return false; String value = att["begin"]; value += '\0'; value += att["end"]; Kind k = (att["type"] == "label") ? ELabelStyle : ETextStyle; sheet.add(k, Attribute(true, name), Attribute(false, value)); } else { Kind kind; if (tag == "pen") kind = EPen; else if (tag == "symbolsize") kind = ESymbolSize; else if (tag == "arrowsize") kind = EArrowSize; else if (tag == "gridsize") kind = EGridSize; else if (tag == "anglesize") kind = EAngleSize; else if (tag == "opacity") kind = EOpacity; else return false; // error if (!parseAttributes(att) || !att.slash()) return false; String name = att["name"]; Attribute value = Attribute::makeScalar(att["value"], Attribute::NORMAL()); if (name.empty() || value.isSymbolic()) return false; if (kind == EGridSize && (!value.isNumber() || !value.number().isInteger())) return false; // refuse non-integer gridsize sheet.add(kind, Attribute(true, name), value); } tag = parseToTag(); } return true; } //! parse a complete style sheet. /*! On calling, stream must be before the 'ipestyle' tag. A tag is allowed. */ StyleSheet *ImlParser::parseStyleSheet() { String tag = parseToTag(); if (tag == "?xml") { XmlAttributes attr; if (!parseAttributes(attr, true)) return nullptr; tag = parseToTag(); } if (tag != "ipestyle") return nullptr; StyleSheet *sheet = new StyleSheet(); if (parseStyle(*sheet)) return sheet; delete sheet; return nullptr; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipepainter.cpp0000644000175000017500000004036513561570220017143 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Ipe drawing interface // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepainter.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::Painter * \ingroup base * \brief Interface for drawing. Painter-derived classes are used for drawing to the screen and for generating PDF and Postscript output. The Painter maintains a stack of graphics states, which includes stroke and fill color, line width, dash style, miter limit, line cap and line join. It also maintains a separate stack of transformation matrices. The Painter class takes care of maintaining the stacks, and setting of the attributes in the current graphics state. Setting an attribute with a symbolic value is resolved immediately using the stylesheet Cascade attached to the Painter, so calling the stroke() or fill() methods of Painter will return the current absolute color. It's okay to set symbolic attributes that the stylesheet does not define - they are set to a default absolute value (black, solid, etc.). The painter is either in "general" or in "path construction" mode. The newPath() member starts path construction mode. In this mode, only the path construction operators (moveTo, lineTo, curveTo, rect, drawArc, closePath), the transformation operators (transform, untransform, translate), and the matrix stack operators (pushMatrix, popMatrix) are admissible. The path is drawn using drawPath, this ends path construction mode. Path construction operators cannot be used in general mode. The graphics state for a path must be set before starting path construction mode, that is, before calling newPath(). Derived classes need to implement the doXXX functions for drawing paths, images, and texts. The transformation matrix has already been applied to the coordinates passed to the doXXX functions. */ //! Constructor takes a (cascaded) style sheet, which is not owned. /*! The initial graphics state contains all default attributes. */ Painter::Painter(const Cascade *style) { iCascade = style; State state; state.iStroke = Color(0,0,0); state.iFill = Color(1000, 1000, 1000); state.iPen = iCascade->find(EPen, Attribute::NORMAL()).number(); state.iDashStyle = "[]0"; // solid state.iLineCap = style->lineCap(); state.iLineJoin = style->lineJoin(); state.iFillRule = style->fillRule(); state.iSymStroke = Color(0, 0, 0); state.iSymFill = Color(1000, 1000, 1000); state.iSymPen = Fixed(1); state.iOpacity = Fixed(1); state.iStrokeOpacity = Fixed(1); state.iTiling = Attribute::NORMAL(); state.iGradient = Attribute::NORMAL(); iState.push_back(state); iMatrix.push_back(Matrix()); // identity iInPath = 0; } //! Virtual destructor. Painter::~Painter() { // nothing } //! Concatenate a matrix to current transformation matrix. void Painter::transform(const Matrix &m) { iMatrix.back() = matrix() * m; } //! Reset transformation to original one, but with different origin/direction. /*! This changes the current transformation matrix to the one set before the first push operation, but maintaining the current origin. Only the operations allowed in \a allowed are applied. */ void Painter::untransform(TTransformations trans) { if (trans == ETransformationsAffine) return; Matrix m = matrix(); Vector org = m.translation(); Vector dx = Vector(m.a[0], m.a[1]); // Vector dy = Vector(m.a[2], m.a[3]); Linear m1(iMatrix.front().linear()); if (trans == ETransformationsRigidMotions) { // compute what direction is transformed to dx by original matrix Angle alpha = (m1.inverse() * dx).angle(); // ensure that (1,0) is rotated into this orientation m1 = m1 * Linear(alpha); } iMatrix.back() = Matrix(m1, org); } //! Concatenate a translation to current transformation matrix. void Painter::translate(const Vector &v) { Matrix m; m.a[4] = v.x; m.a[5] = v.y; iMatrix.back() = matrix() * m; } //! Enter path construction mode. void Painter::newPath() { assert(!iInPath); iInPath = iState.size(); // save current nesting level doNewPath(); } //! Start a new subpath. void Painter::moveTo(const Vector &v) { assert(iInPath > 0); doMoveTo(matrix() * v); } //! Add line segment to current subpath. void Painter::lineTo(const Vector &v) { assert(iInPath > 0); doLineTo(matrix() * v); } //! Add a Bezier segment to current subpath. void Painter::curveTo(const Vector &v1, const Vector &v2, const Vector &v3) { assert(iInPath > 0); doCurveTo(matrix() * v1, matrix() * v2, matrix() * v3); } //! Add an elliptic arc to current path. /*! Assumes the current point is \a arc.beginp(). */ void Painter::drawArc(const Arc &arc) { assert(iInPath > 0); doDrawArc(arc); } //! Add a rectangle subpath to the path. /*! This is implemented in terms of moveTo() and lineTo(). */ void Painter::rect(const Rect &re) { moveTo(re.bottomLeft()); lineTo(re.bottomRight()); lineTo(re.topRight()); lineTo(re.topLeft()); closePath(); } //! Close the current subpath. void Painter::closePath() { assert(iInPath > 0); doClosePath(); } //! Save current graphics state. /*! Cannot be called in path construction mode. */ void Painter::push() { assert(!iInPath); State state = iState.back(); iState.push_back(state); doPush(); } //! Restore previous graphics state. /*! Cannot be called in path construction mode. */ void Painter::pop() { assert(!iInPath); iState.pop_back(); doPop(); } //! Save current transformation matrix. void Painter::pushMatrix() { iMatrix.push_back(matrix()); } //! Restore previous transformation matrix. void Painter::popMatrix() { iMatrix.pop_back(); } //! Fill and/or stroke a path. /*! As in PDF, a "path" can consist of several subpaths. Whether it is filled or stroked depends on \a mode. */ void Painter::drawPath(TPathMode mode) { assert(iInPath > 0); doDrawPath(mode); iInPath = 0; } //! Render a bitmap. /*! Assumes the transformation matrix has been set up to map the unit square to the image area on the paper. */ void Painter::drawBitmap(Bitmap bitmap) { assert(!iInPath); doDrawBitmap(bitmap); } //! Render a text object. /*! Stroke color is already set, and the origin is the lower-left corner of the text box (not the reference point!). */ void Painter::drawText(const Text *text) { assert(!iInPath); doDrawText(text); } //! Render a symbol. /*! The current coordinate system is already the symbol coordinate system. If the symbol is parameterized, then sym-stroke, sym-fill, and sym-pen are already set. */ void Painter::drawSymbol(Attribute symbol) { assert(!iInPath); doDrawSymbol(symbol); } //! Add current path as clip path. void Painter::addClipPath() { assert(iInPath > 0); doAddClipPath(); iInPath = 0; } // -------------------------------------------------------------------- //! Set stroke color, resolving symbolic color and "sym-x" colors void Painter::setStroke(Attribute color) { assert(!iInPath); if (color == Attribute::SYM_STROKE()) iState.back().iStroke = iState.back().iSymStroke; else if (color == Attribute::SYM_FILL()) iState.back().iStroke = iState.back().iSymFill; else iState.back().iStroke = iCascade->find(EColor, color).color(); } //! Set fill color, resolving symbolic color. void Painter::setFill(Attribute color) { assert(!iInPath); if (color == Attribute::SYM_STROKE()) iState.back().iFill = iState.back().iSymStroke; else if (color == Attribute::SYM_FILL()) iState.back().iFill = iState.back().iSymFill; else iState.back().iFill = iCascade->find(EColor, color).color(); } //! Set pen, resolving symbolic value. void Painter::setPen(Attribute pen) { assert(!iInPath); if (pen == Attribute::SYM_PEN()) iState.back().iPen = iState.back().iSymPen; else iState.back().iPen = iCascade->find(EPen, pen).number(); } //! Set dash style, resolving symbolic value. void Painter::setDashStyle(Attribute dash) { assert(!iInPath); iState.back().iDashStyle = iCascade->find(EDashStyle, dash).string(); } //! Return dashstyle as a double sequence. void Painter::dashStyle(std::vector &dashes, double &offset) const { dashes.clear(); offset = 0.0; String s = dashStyle(); int i = s.find("["); int j = s.find("]"); if (i < 0 || j < 0) return; Lex lex(s.substr(i+1, j - i - 1)); while (!lex.eos()) dashes.push_back(lex.getDouble()); offset = Lex(s.substr(j+1)).getDouble(); } //! Set line cap. /*! If \a cap is EDefaultCap, the current setting remains unchanged. */ void Painter::setLineCap(TLineCap cap) { assert(!iInPath); if (cap != EDefaultCap) iState.back().iLineCap = cap; } //! Set line join. /*! If \a join is EDefaultJoin, the current setting remains unchanged. */ void Painter::setLineJoin(TLineJoin join) { assert(!iInPath); if (join != EDefaultJoin) iState.back().iLineJoin = join; } //! Set fill rule (wind or even-odd). /*! If the rule is EDefaultRule, the current setting remains unchanged. */ void Painter::setFillRule(TFillRule rule) { assert(!iInPath); if (rule != EDefaultRule) iState.back().iFillRule = rule; } //! Set opacity. void Painter::setOpacity(Attribute opaq) { assert(!iInPath); iState.back().iOpacity = iCascade->find(EOpacity, opaq).number(); } //! Set stroke opacity. void Painter::setStrokeOpacity(Attribute opaq) { assert(!iInPath); iState.back().iStrokeOpacity = iCascade->find(EOpacity, opaq).number(); } //! Set tiling pattern. /*! If \a tiling is not \c normal, resets the gradient pattern. */ void Painter::setTiling(Attribute tiling) { assert(!iInPath); iState.back().iTiling = tiling; if (!tiling.isNormal()) iState.back().iGradient = Attribute::NORMAL(); } //! Set gradient fill. /*! If \a grad is not \c normal, resets the tiling pattern. */ void Painter::setGradient(Attribute grad) { assert(!iInPath); iState.back().iGradient = grad; if (!grad.isNormal()) iState.back().iTiling = Attribute::NORMAL(); } //! Set symbol stroke color, resolving symbolic color. void Painter::setSymStroke(Attribute color) { assert(!iInPath); if (color == Attribute::SYM_STROKE()) iState.back().iSymStroke = (++iState.rbegin())->iSymStroke; else if (color == Attribute::SYM_FILL()) iState.back().iSymStroke = (++iState.rbegin())->iSymFill; else iState.back().iSymStroke = iCascade->find(EColor, color).color(); } //! Set symbol fill color, resolving symbolic color. void Painter::setSymFill(Attribute color) { assert(!iInPath); if (color == Attribute::SYM_STROKE()) iState.back().iSymFill = (++iState.rbegin())->iSymStroke; else if (color == Attribute::SYM_FILL()) iState.back().iSymFill = (++iState.rbegin())->iSymFill; else iState.back().iSymFill = iCascade->find(EColor, color).color(); } //! Set symbol pen, resolving symbolic pen. void Painter::setSymPen(Attribute pen) { assert(!iInPath); if (pen == Attribute::SYM_PEN()) iState.back().iSymPen = (++iState.rbegin())->iSymPen; else iState.back().iSymPen = iCascade->find(EPen, pen).number(); } //! Set full graphics state at once. void Painter::setState(const State &state) { iState.back() = state; } // -------------------------------------------------------------------- // Coordinate for bezier approximation for quarter circle. const double BETA = 0.55228474983079334; const double PI15 = IpePi + IpeHalfPi; //! Draw an arc of the unit circle of length \a alpha. /*! PDF does not have an "arc" or "circle" primitive, so to draw an arc, circle, or ellipse, Ipe has to translate it into a sequence of Bezier curves. The approximation is based on the following: The unit circle arc from (1,0) to (cos a, sin a) be approximated by a Bezier spline with control points (1, 0), (1, beta) and their mirror images along the line with slope a/2, where beta = 4.0 * (1.0 - cos(a/2)) / (3 * sin(a/2)) Ipe draws circles by drawing four Bezier curves for the quadrants, and arcs by patching together quarter circle approximations with a piece computed from the formula above. \a alpha is normalized to [0, 2 pi], and applied starting from the point (1,0). The function generates a sequence of Bezier splines as calls to curveTo. It is assumed that the caller has already executed a moveTo to the beginning of the arc at (1,0). This function may modify the transformation matrix. */ void Painter::drawArcAsBezier(double alpha) { // Vector p0(1.0, 0.0); Vector p1(1.0, BETA); Vector p2(BETA, 1.0); Vector p3(0.0, 1.0); Vector q1(-BETA, 1.0); Vector q2(-1.0, BETA); Vector q3(-1.0, 0.0); double begAngle = 0.0; if (alpha > IpeHalfPi) { curveTo(p1, p2, p3); begAngle = IpeHalfPi; } if (alpha > IpePi) { curveTo(q1, q2, q3); begAngle = IpePi; } if (alpha > PI15) { curveTo(-p1, -p2, -p3); begAngle = PI15; } if (alpha >= IpeTwoPi) { curveTo(-q1, -q2, -q3); } else { alpha -= begAngle; double alpha2 = alpha / 2.0; double divi = 3.0 * sin(alpha2); if (divi == 0.0) return; // alpha2 is close to zero double beta = 4.0 * (1.0 - cos(alpha2)) / divi; Linear m = Linear(Angle(begAngle)); Vector pp1(1.0, beta); Vector pp2 = Linear(Angle(alpha)) * Vector(1.0, -beta); Vector pp3 = Vector(Angle(alpha)); curveTo(m * pp1, m * pp2, m * pp3); } } // -------------------------------------------------------------------- //! Perform graphics state push on output medium. void Painter::doPush() { // nothing } //! Perform graphics state pop on output medium. void Painter::doPop() { // nothing } //! Perform new path operator. void Painter::doNewPath() { // nothing } //! Perform moveto operator. /*! The transformation matrix has already been applied. */ void Painter::doMoveTo(const Vector &) { // nothing } //! Perform lineto operator. /*! The transformation matrix has already been applied. */ void Painter::doLineTo(const Vector &) { // nothing } //! Perform curveto operator. /*! The transformation matrix has already been applied. */ void Painter::doCurveTo(const Vector &, const Vector &, const Vector &) { // nothing } //! Draw an elliptic arc. /*! The default implementations calls drawArcAsBezier(). The transformation matrix has not yet been applied to \a arc. */ void Painter::doDrawArc(const Arc &arc) { pushMatrix(); transform(arc.iM); if (arc.isEllipse()) { moveTo(Vector(1,0)); drawArcAsBezier(IpeTwoPi); } else { transform(Linear(arc.iAlpha)); double alpha = Angle(arc.iBeta - arc.iAlpha).normalize(0.0); drawArcAsBezier(alpha); } popMatrix(); } //! Perform closepath operator. void Painter::doClosePath() { // nothing } //! Actually draw the path. void Painter::doDrawPath(TPathMode) { // nothing } //! Draw a bitmap. void Painter::doDrawBitmap(Bitmap) { // nothing } //! Draw a text object. void Painter::doDrawText(const Text *) { // nothing } //! Draw a symbol. /*! The default implementation calls the draw method of the object. Only PDF drawing overrides this to reuse a PDF XForm. */ void Painter::doDrawSymbol(Attribute symbol) { const Symbol *sym = cascade()->findSymbol(symbol); if (sym) sym->iObject->draw(*this); } //! Add a clip path void Painter::doAddClipPath() { // nothing } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipebitmap_unix.cpp0000644000175000017500000002020013561570220020002 0ustar otfriedotfried// ipebitmap_unix.cpp // Code dependent on libjpeg and libpng /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebitmap.h" #include "ipeutils.h" #include #ifdef __APPLE__ #include #else #include #include #endif using namespace ipe; // -------------------------------------------------------------------- #ifdef __APPLE__ bool dctDecode(Buffer dctData, Buffer pixelData) { CGDataProviderRef source = CGDataProviderCreateWithData(nullptr, dctData.data(), dctData.size(), nullptr); CGImageRef bitmap = CGImageCreateWithJPEGDataProvider(source, nullptr, false, kCGRenderingIntentDefault); if (CGImageGetBitsPerComponent(bitmap) != 8) return false; int w = CGImageGetWidth(bitmap); int h = CGImageGetHeight(bitmap); int bits = CGImageGetBitsPerPixel(bitmap); int stride = CGImageGetBytesPerRow(bitmap); if (bits != 8 && bits != 24 && bits != 32) return false; int bytes = bits / 8; CGBitmapInfo info = CGImageGetBitmapInfo(bitmap); // Do we need to check for alpha channel, float pixel values, and byte order? ipeDebug("dctDecode: %d x %d x %d, stride %d, info %x", w, h, bytes, stride, info); CFDataRef pixels = CGDataProviderCopyData(CGImageGetDataProvider(bitmap)); const uint8_t *inRow = CFDataGetBytePtr(pixels); uint32_t *q = (uint32_t *) pixelData.data(); if (bits != 8) { for (int y = 0; y < h; ++y) { const uint8_t *p = inRow; for (int x = 0; x < w; ++x) { *q++ = 0xff000000 | (p[0] << 16) | (p[1] << 8) | p[2]; p += bytes; } inRow += stride; } } else { for (int y = 0; y < h; ++y) { const uint8_t *p = inRow; for (int x = 0; x < w; ++x) *q++ = 0xff000000 | (*p << 16) | (*p << 8) | *p; inRow += stride; } } CFRelease(pixels); CGImageRelease(bitmap); CGDataProviderRelease(source); return true; } #else // Decode jpeg image using libjpeg API with error handling // Code contributed by Michael Thon, 2015. // The following is error-handling code for decompressing jpeg using the // standard libjpeg API. Taken from the example.c and stackoverflow. struct jpegErrorManager { struct jpeg_error_mgr pub; jmp_buf setjmp_buffer; }; static char jpegLastErrorMsg[JMSG_LENGTH_MAX]; static void jpegErrorExit (j_common_ptr cinfo) { jpegErrorManager *myerr = (jpegErrorManager*) cinfo->err; (*(cinfo->err->format_message)) (cinfo, jpegLastErrorMsg); longjmp(myerr->setjmp_buffer, 1); } bool dctDecode(Buffer dctData, Buffer pixelData) { struct jpeg_decompress_struct cinfo; // Error handling: struct jpegErrorManager jerr; cinfo.err = jpeg_std_error(&jerr.pub); jerr.pub.error_exit = jpegErrorExit; if (setjmp(jerr.setjmp_buffer)) { ipeDebug("jpeg decompression failed: %s", jpegLastErrorMsg); jpeg_destroy_decompress(&cinfo); return false; } // Decompression: jpeg_create_decompress(&cinfo); jpeg_mem_src(&cinfo, (unsigned char *) dctData.data(), dctData.size()); jpeg_read_header(&cinfo, 1); cinfo.out_color_space = JCS_RGB; jpeg_start_decompress(&cinfo); uint32_t *p = (uint32_t *) pixelData.data(); Buffer row(cinfo.output_width * cinfo.output_components); uint8_t *buffer[1]; uint8_t *fin = (uint8_t *) row.data() + row.size(); while (cinfo.output_scanline < cinfo.output_height) { buffer[0] = (uint8_t *) row.data(); jpeg_read_scanlines(&cinfo, buffer, 1); uint32_t pixel; uint8_t *q = (uint8_t *) row.data(); while (q < fin) { pixel = 0xff000000 | (*q++ << 16); pixel |= (*q++ << 8); *p++ = pixel | *q++; } } jpeg_finish_decompress(&cinfo); jpeg_destroy_decompress(&cinfo); return true; } #endif // -------------------------------------------------------------------- //! Read PNG image from file. /*! Returns the image as a Bitmap. It will be compressed if \a deflate is set. Sets \a dotsPerInch if the image file contains a resolution, otherwise sets it to (0,0). If reading the file fails, returns a null Bitmap, and sets the error message \a errmsg. */ Bitmap Bitmap::readPNG(const char *fname, Vector &dotsPerInch, const char * &errmsg) { FILE *fp = Platform::fopen(fname, "rb"); if (!fp) { errmsg = "Error opening file"; return Bitmap(); } static const char pngerr[] = "PNG library error"; uint8_t header[8]; if (fread(header, 1, 8, fp) != 8 || png_sig_cmp(header, 0, 8)) { errmsg = "The file does not appear to be a PNG image"; fclose(fp); return Bitmap(); } png_structp png_ptr = png_create_read_struct(PNG_LIBPNG_VER_STRING, (png_voidp) nullptr, nullptr, nullptr); if (!png_ptr) { errmsg = pngerr; fclose(fp); return Bitmap(); } png_infop info_ptr = png_create_info_struct(png_ptr); if (!info_ptr) { png_destroy_read_struct(&png_ptr, (png_infopp) nullptr, (png_infopp) nullptr); errmsg = pngerr; return Bitmap(); } if (setjmp(png_jmpbuf(png_ptr))) { png_destroy_read_struct(&png_ptr, &info_ptr, (png_infopp) nullptr); errmsg = pngerr; fclose(fp); return Bitmap(); } #if PNG_LIBPNG_VER >= 10504 png_set_alpha_mode(png_ptr, PNG_ALPHA_PNG, PNG_GAMMA_LINEAR); #endif png_init_io(png_ptr, fp); png_set_sig_bytes(png_ptr, 8); png_read_info(png_ptr, info_ptr); int width = png_get_image_width(png_ptr, info_ptr); int height = png_get_image_height(png_ptr, info_ptr); int color_type = png_get_color_type(png_ptr, info_ptr); if (color_type == PNG_COLOR_TYPE_PALETTE) { png_set_palette_to_rgb(png_ptr); if (png_get_valid(png_ptr, info_ptr, PNG_INFO_tRNS)) { png_set_tRNS_to_alpha(png_ptr); png_set_swap_alpha(png_ptr); } else png_set_add_alpha(png_ptr, 0xff, PNG_FILLER_BEFORE); } else { if (color_type == PNG_COLOR_TYPE_GRAY && png_get_bit_depth(png_ptr, info_ptr) < 8) png_set_expand_gray_1_2_4_to_8(png_ptr); if (color_type == PNG_COLOR_TYPE_GRAY || color_type == PNG_COLOR_TYPE_GRAY_ALPHA) png_set_gray_to_rgb(png_ptr); if (color_type & PNG_COLOR_MASK_ALPHA) png_set_swap_alpha(png_ptr); else png_set_add_alpha(png_ptr, 0xff, PNG_FILLER_BEFORE); } if (png_get_bit_depth(png_ptr, info_ptr) == 16) #if PNG_LIBPNG_VER >= 10504 png_set_scale_16(png_ptr); #else png_set_strip_16(png_ptr); #endif png_read_update_info(png_ptr, info_ptr); if (png_get_bit_depth(png_ptr, info_ptr) != 8) { png_destroy_read_struct(&png_ptr, &info_ptr, (png_infopp) nullptr); errmsg = "Depth of PNG image is not eight bits."; fclose(fp); return Bitmap(); } const double mpi = 25.4/1000.0; dotsPerInch = Vector(mpi * png_get_x_pixels_per_meter(png_ptr, info_ptr), mpi * png_get_y_pixels_per_meter(png_ptr, info_ptr)); Buffer pixels(4 * width * height); png_bytep row[height]; for (int y = 0; y < height; ++y) row[y] = (png_bytep) pixels.data() + 4 * width * y; png_read_image(png_ptr, row); png_read_end(png_ptr, (png_infop) nullptr); png_destroy_read_struct(&png_ptr, &info_ptr, (png_infopp) nullptr); fclose(fp); Bitmap bm(width, height, Bitmap::ERGB|Bitmap::EAlpha, pixels); return bm; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipeimage.cpp0000644000175000017500000001241213561570220016553 0ustar otfriedotfried// -------------------------------------------------------------------- // The image object. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeimage.h" #include "ipepainter.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::Image \ingroup obj \brief The image object. */ //! Create a new image Image::Image(const Rect &rect, Bitmap bitmap) : Object() { iRect = rect; iBitmap = bitmap; iOpacity = Attribute::OPAQUE(); assert(!iBitmap.isNull()); } //! Create from XML stream. Image::Image(const XmlAttributes &attr, String data) : Object(attr) { init(attr); iBitmap = Bitmap(attr, data); } //! Create from XML stream with given bitmap. Image::Image(const XmlAttributes &attr, Bitmap bitmap) : Object(attr), iBitmap(bitmap) { init(attr); } void Image::init(const XmlAttributes &attr) { String str; if (attr.has("opacity", str)) iOpacity = Attribute(true, str); else iOpacity = Attribute::OPAQUE(); // parse rect Lex st(attr["rect"]); Vector v; st >> v.x >> v.y; iRect.addPoint(v); st >> v.x >> v.y; iRect.addPoint(v); } //! Clone object Object *Image::clone() const { return new Image(*this); } //! Return pointer to this object. Image *Image::asImage() { return this; } Object::Type Image::type() const { return EImage; } //! Call VisitImage of visitor. void Image::accept(Visitor &visitor) const { visitor.visitImage(this); } //! Save image in XML stream. void Image::saveAsXml(Stream &stream, String layer) const { stream << "\n"; } //! Draw image. void Image::draw(Painter &painter) const { Matrix m(iRect.width(), 0, 0, iRect.height(), iRect.bottomLeft().x, iRect.bottomLeft().y); painter.pushMatrix(); painter.transform(matrix()); painter.untransform(transformations()); painter.transform(m); painter.push(); painter.setOpacity(iOpacity); painter.drawBitmap(iBitmap); painter.pop(); painter.popMatrix(); } void Image::drawSimple(Painter &painter) const { painter.pushMatrix(); painter.transform(matrix()); painter.untransform(transformations()); painter.newPath(); painter.rect(iRect); painter.drawPath(EStrokedOnly); painter.popMatrix(); } double Image::distance(const Vector &v, const Matrix &m, double bound) const { Matrix m1 = m * matrix(); Vector u[5]; u[0] = m1 * iRect.bottomLeft(); u[1] = m1 * iRect.bottomRight(); u[2] = m1 * iRect.topRight(); u[3] = m1 * iRect.topLeft(); u[4] = u[0]; Rect box; for (int i = 0; i < 4; ++i) box.addPoint(u[i]); if (box.certainClearance(v, bound)) return bound; double d = bound; double d1; for (int i = 0; i < 4; ++i) { if ((d1 = Segment(u[i], u[i+1]).distance(v, d)) < d) d = d1; } return d; } void Image::addToBBox(Rect &box, const Matrix &m, bool) const { Matrix m1 = m * matrix(); box.addPoint(m1 * iRect.bottomLeft()); box.addPoint(m1 * iRect.bottomRight()); box.addPoint(m1 * iRect.topRight()); box.addPoint(m1 * iRect.topLeft()); } void Image::snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { Matrix m1 = m * matrix(); (m1 * iRect.bottomLeft()).snap(mouse, pos, bound); (m1 * iRect.bottomRight()).snap(mouse, pos, bound); (m1 * iRect.topRight()).snap(mouse, pos, bound); (m1 * iRect.topLeft()).snap(mouse, pos, bound); } //! Set opacity of the object. void Image::setOpacity(Attribute opaq) { iOpacity = opaq; } bool Image::setAttribute(Property prop, Attribute value) { switch (prop) { case EPropOpacity: if (value != opacity()) { setOpacity(value); return true; } break; default: return Object::setAttribute(prop, value); } return false; } Attribute Image::getAttribute(Property prop) const noexcept { switch (prop) { case EPropOpacity: return opacity(); default: return Object::getAttribute(prop); } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipereference.cpp0000644000175000017500000002654013561570220017436 0ustar otfriedotfried// -------------------------------------------------------------------- // The reference object. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipereference.h" #include "ipestyle.h" #include "ipepainter.h" using namespace ipe; /*! \class ipe::Reference \ingroup obj \brief The reference object. A Reference uses a symbol, that is, an object defined in an Ipe StyleSheet. The object is defined as a named symbol in the style sheet, and can be reused arbitrarily often in the document. This can, for instance, be used for backgrounds on multi-page documents. It is admissible to refer to an undefined object (that is, the current style sheet cascade does not define a symbol with the given name). Nothing will be drawn in this case. The Reference has a stroke, fill, and pen attribute. When drawing a symbol, these attributes are made available to the symbol through the names "sym-stroke", "sym-fill", and "sym-pen". These are not defined by the style sheet, but resolved by the Painter when the symbol sets its attributes. Note that it is not possible to determine \e whether a symbol is filled from the Reference object. The size attribute is of type ESymbolSize, and indicates a magnification factor applied to the symbol. This magnification is applied after the untransformation indicated in the Reference and in the Symbol has been performed, so that symbols are magnified even if they specify ETransformationsTranslations. The size is meant for symbols such as marks, that can be shown in different sizes. Another application of symbols is for backgrounds and logos. Their size should not be changed when the user changes the symbolsize for the entire page. For such symbols, the size attribute of the Reference should be set to the absolute value zero. This means that no magnification is applied to the object, and it also \e stops setAttribute() from modifying the size. (The size can still be changed using setSize(), but this is not available from Lua.) */ //! Create a reference to the named object in stylesheet. Reference::Reference(const AllAttributes &attr, Attribute name, Vector pos) : Object() { assert(name.isSymbolic()); iName = name; iPos = pos; iPen = Attribute::NORMAL(); iSize = Attribute::ONE(); iStroke = Attribute::BLACK(); iFill = Attribute::WHITE(); iFlags = flagsFromName(name.string()); if (iFlags & EHasPen) iPen = attr.iPen; if (iFlags & EHasSize) iSize = attr.iSymbolSize; if (iFlags & EHasStroke) iStroke = attr.iStroke; if (iFlags & EHasFill) iFill = attr.iFill; } //! Create from XML stream. Reference::Reference(const XmlAttributes &attr, String /* data */) : Object(attr) { iName = Attribute(true, attr["name"]); String str; if (attr.has("pos", str)) { Lex st(str); st >> iPos.x >> iPos.y; } else iPos = Vector::ZERO; iPen = Attribute::makeScalar(attr["pen"], Attribute::NORMAL()); iSize = Attribute::makeScalar(attr["size"], Attribute::ONE()); iStroke = Attribute::makeColor(attr["stroke"], Attribute::BLACK()); iFill = Attribute::makeColor(attr["fill"], Attribute::WHITE()); iFlags = flagsFromName(iName.string()); } //! Clone object Object *Reference::clone() const { return new Reference(*this); } //! Return pointer to this object. Reference *Reference::asReference() { return this; } Object::Type Reference::type() const { return EReference; } //! Call visitReference of visitor. void Reference::accept(Visitor &visitor) const { visitor.visitReference(this); } //! Save in XML format. void Reference::saveAsXml(Stream &stream, String layer) const { stream << "\n"; } //! Draw reference. /*! If the symbolic attribute is not defined in the current style sheet, nothing is drawn at all. */ void Reference::draw(Painter &painter) const { const Symbol *symbol = painter.cascade()->findSymbol(iName); if (symbol) { iSnap = symbol->iSnap; // cache snap point information Attribute si = painter.cascade()->find(ESymbolSize, iSize); double s = si.number().toDouble(); painter.pushMatrix(); painter.transform(matrix()); painter.translate(iPos); painter.untransform(transformations()); painter.untransform(symbol->iTransformations); if (iFlags & EHasSize) { Matrix m(s, 0, 0, s, 0, 0); painter.transform(m); } painter.push(); if (iFlags & EHasStroke) painter.setSymStroke(iStroke); if (iFlags & EHasFill) painter.setSymFill(iFill); if (iFlags & EHasPen) painter.setSymPen(iPen); painter.drawSymbol(iName); painter.pop(); painter.popMatrix(); } } void Reference::drawSimple(Painter &painter) const { painter.pushMatrix(); painter.transform(matrix()); painter.translate(iPos); if (iSnap.size() > 0) { const Symbol *symbol = painter.cascade()->findSymbol(iName); if (symbol) { painter.untransform(symbol->iTransformations); if (iFlags & EHasSize) { Attribute si = painter.cascade()->find(ESymbolSize, iSize); double s = si.number().toDouble(); Matrix m(s, 0, 0, s, 0, 0); painter.transform(m); } painter.push(); symbol->iObject->drawSimple(painter); painter.pop(); painter.popMatrix(); return; } } painter.untransform(ETransformationsTranslations); const int size = 10; painter.newPath(); painter.moveTo(Vector(-size, 0)); painter.lineTo(Vector(size, 0)); painter.moveTo(Vector(0, -size)); painter.lineTo(Vector(0, size)); painter.drawPath(EStrokedOnly); painter.popMatrix(); } /*! \copydoc Object::addToBBox This only adds the position (or the snap positions) to the \a box. */ void Reference::addToBBox(Rect &box, const Matrix &m, bool cp) const { if (iSnap.size() > 0) { for (const Vector & pos : iSnap) box.addPoint((m * matrix()) * (iPos + pos)); } else box.addPoint((m * matrix()) * iPos); } void Reference::checkStyle(const Cascade *sheet, AttributeSeq &seq) const { const Symbol *symbol = sheet->findSymbol(iName); if (!symbol) { if (std::find(seq.begin(), seq.end(), iName) == seq.end()) seq.push_back(iName); } else { iSnap = symbol->iSnap; // cache snap positions } if (iFlags & EHasStroke) checkSymbol(EColor, iStroke, sheet, seq); if (iFlags & EHasFill) checkSymbol(EColor, iFill, sheet, seq); if (iFlags & EHasPen) checkSymbol(EPen, iPen, sheet, seq); if (iFlags & EHasSize) checkSymbol(ESymbolSize, iSize, sheet, seq); } double Reference::distance(const Vector &v, const Matrix &m, double bound) const { if (iSnap.size() > 0) { double d = bound; for (const Vector & snapPos : iSnap) { double d1 = (v - (m * (matrix() * (iPos + snapPos)))).len(); if (d1 < d) d = d1; } return d; } else return (v - (m * (matrix() * iPos))).len(); } void Reference::snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { if (iSnap.size() > 0) { for (const Vector & snapPos : iSnap) (m * (matrix() * (iPos + snapPos))).snap(mouse, pos, bound); } else (m * (matrix() * iPos)).snap(mouse, pos, bound); } void Reference::snapBnd(const Vector &, const Matrix &, Vector &, double &) const { // nothing } //! Set name of symbol referenced. void Reference::setName(Attribute name) { iName = name; iFlags = flagsFromName(name.string()); } //! Set pen. void Reference::setPen(Attribute pen) { iPen = pen; } //! Set stroke color. void Reference::setStroke(Attribute color) { iStroke = color; } //! Set fill color. void Reference::setFill(Attribute color) { iFill = color; } //! Set size (magnification) of symbol. void Reference::setSize(Attribute size) { iSize = size; } //! \copydoc Object::setAttribute bool Reference::setAttribute(Property prop, Attribute value) { switch (prop) { case EPropPen: if ((iFlags & EHasPen) && value != pen()) { setPen(value); return true; } break; case EPropStrokeColor: if ((iFlags & EHasStroke) && value != stroke()) { setStroke(value); return true; } break; case EPropFillColor: if ((iFlags & EHasFill) && value != fill()) { setFill(value); return true; } break; case EPropSymbolSize: if ((iFlags & EHasSize) && value != size()) { setSize(value); return true; } break; case EPropMarkShape: if ((iFlags & EIsMark) && value != name()) { setName(value); return true; } break; default: return Object::setAttribute(prop, value); } return false; } Attribute Reference::getAttribute(Property prop) const noexcept { switch (prop) { case EPropPen: if (iFlags & EHasPen) return pen(); break; case EPropStrokeColor: if (iFlags & EHasStroke) return stroke(); break; case EPropFillColor: if (iFlags & EHasFill) return fill(); break; case EPropSymbolSize: if (iFlags & EHasSize) return size(); break; case EPropMarkShape: if (iFlags & EIsMark) return name(); break; default: break; } return Object::getAttribute(prop); } // -------------------------------------------------------------------- uint32_t Reference::flagsFromName(String name) { uint32_t flags = 0; if (name.left(5) == "mark/") flags |= EIsMark; if (name.left(6) == "arrow/") flags |= EIsArrow; int i = name.rfind('('); if (i < 0 || name[name.size() - 1] != ')') return flags; String letters = name.substr(i+1, name.size() - i - 2); if (letters.find('x') >= 0) flags |= EHasSize; if (letters.find('s') >= 0) flags |= EHasStroke; if (letters.find('f') >= 0) flags |= EHasFill; if (letters.find('p') >= 0) flags |= EHasPen; return flags; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipestdstyles.cpp0000644000175000017500000000663313561570220017537 0ustar otfriedotfried// -------------------------------------------------------------------- // Standard Ipe style (embedded in Ipelib) // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebase.h" #include "ipestyle.h" #include "ipeiml.h" using namespace ipe; static const char *styleStandard[] = { "", "", "", "", "", "", "", "", "", "", "", "0 0 m -1.0 0.333 l -1.0 -0.333 l h", "", "\n", "", "", "", "", "", "", "", "", nullptr }; class StandardStyleSource : public DataSource { public: StandardStyleSource(const char **lines) : iLine(lines), iChar(lines[0]) { /* nothing */ } int getChar(); private: const char **iLine; const char *iChar; }; int StandardStyleSource::getChar() { if (!*iLine) return EOF; // not yet at end of data if (!*iChar) { iLine++; iChar = *iLine; return '\n'; // important: iChar may be 0 now! } return *iChar++; } //! Create standard built-in style sheet. StyleSheet *StyleSheet::standard() { // ipeDebug("creating standard stylesheet"); StandardStyleSource source(styleStandard); ImlParser parser(source); StyleSheet *sheet = parser.parseStyleSheet(); assert(sheet); sheet->iStandard = true; sheet->iName = "standard"; return sheet; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipebitmap.cpp0000644000175000017500000005361513561570220016757 0ustar otfriedotfried// -------------------------------------------------------------------- // Bitmaps // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebitmap.h" #include "ipeutils.h" #include using namespace ipe; extern bool dctDecode(Buffer dctData, Buffer pixelData); // -------------------------------------------------------------------- /*! \class ipe::Bitmap \ingroup base \brief A bitmap. Bitmaps are explicitely shared using reference-counting. Copying is cheap, so Bitmap objects are meant to be passed by value. The bitmap provides a slot for short-term storage of an "object number". The PDF embedder, for instance, sets it to the PDF object number when embedding the bitmap, and can reuse it when "drawing" the bitmap. */ //! Default constructor constructs null bitmap. Bitmap::Bitmap() { iImp = nullptr; } //! Create from XML stream. Bitmap::Bitmap(const XmlAttributes &attr, String pcdata) { auto lengths = init(attr); int length = lengths.first; if (length == 0) length = height() * width() * (isGray() ? 1 : 3); int alphaLength = lengths.second; // decode data iImp->iData = Buffer(length); char *p = iImp->iData.data(); Buffer alpha; char *q = nullptr; if (alphaLength > 0) { alpha = Buffer(alphaLength); q = alpha.data(); } if (attr["encoding"] == "base64") { Buffer dbuffer(pcdata.data(), pcdata.size()); BufferSource source(dbuffer); Base64Source b64source(source); while (length-- > 0) *p++ = b64source.getChar(); while (alphaLength-- > 0) *q++ = b64source.getChar(); } else { Lex datalex(pcdata); while (length-- > 0) *p++ = char(datalex.getHexByte()); while (alphaLength-- > 0) *q++ = char(datalex.getHexByte()); } unpack(alpha); computeChecksum(); analyze(); } //! Create from XML using external raw data Bitmap::Bitmap(const XmlAttributes &attr, Buffer data, Buffer alpha) { init(attr); iImp->iData = data; unpack(alpha); computeChecksum(); analyze(); } std::pair Bitmap::init(const XmlAttributes &attr) { iImp = new Imp; iImp->iRefCount = 1; iImp->iFlags = 0; iImp->iColorKey = -1; iImp->iPixelsComputed = false; iImp->iObjNum = Lex(attr["id"]).getInt(); iImp->iWidth = Lex(attr["width"]).getInt(); iImp->iHeight = Lex(attr["height"]).getInt(); int length = Lex(attr["length"]).getInt(); int alphaLength = Lex(attr["alphaLength"]).getInt(); assert(iImp->iWidth > 0 && iImp->iHeight > 0); String cs = attr["ColorSpace"]; if (cs.right(5) =="Alpha") { iImp->iFlags |= EAlpha; cs = cs.left(cs.size() - 5); } if (cs == "DeviceRGB") iImp->iFlags |= ERGB; String fi = attr["Filter"]; if (fi == "DCTDecode") iImp->iFlags |= EDCT; else if (fi == "FlateDecode") iImp->iFlags |= EInflate; String cc; if (!isJpeg() && attr.has("ColorKey", cc)) iImp->iColorKey = Lex(cc).getHexNumber(); return std::make_pair(length, alphaLength); } //! Create a new image from given image data. /*! If you already have data in native-endian ARGB32 without premultiplication, pass it with flag ENative. Otherwise pass a byte stream and set ERGB and EAlpha correctly: EAlpha: each pixel starts with one byte of alpha channel, ERGB: each pixel has three bytes of R, G, B, in this order, otherwise each pixel has one byte of gray value. */ Bitmap::Bitmap(int width, int height, uint32_t flags, Buffer data) { iImp = new Imp; iImp->iRefCount = 1; iImp->iFlags = flags; iImp->iColorKey = -1; iImp->iObjNum = -1; iImp->iWidth = width; iImp->iHeight = height; iImp->iData = data; iImp->iPixelsComputed = false; assert(iImp->iWidth > 0 && iImp->iHeight > 0); unpack(Buffer()); computeChecksum(); analyze(); } //! Take care of inflating, converting grayscale to rgb, and merging the alpha channel void Bitmap::unpack(Buffer alphaChannel) { if (isJpeg() || iImp->iFlags & ENative) return; int npixels = width() * height(); if (iImp->iFlags & EInflate) { // inflate data int components = isGray() ? 1 : 3; if (hasAlpha() && alphaChannel.size() == 0) components += 1; uLongf inflatedSize = npixels * components; Buffer inflated(inflatedSize); assert(uncompress((Bytef *) inflated.data(), &inflatedSize, (const Bytef *) iImp->iData.data(), iImp->iData.size()) == Z_OK); iImp->iData = inflated; if (alphaChannel.size() > 0) { inflatedSize = npixels; Buffer inflatedAlpha(inflatedSize); assert(uncompress((Bytef *) inflatedAlpha.data(), &inflatedSize, (const Bytef *) alphaChannel.data(), alphaChannel.size()) == Z_OK); alphaChannel = inflatedAlpha; } } // convert data to ARGB32 format bool alphaInMain = hasAlpha() && alphaChannel.size() == 0; Buffer pixels(npixels * sizeof(uint32_t)); const char *p = iImp->iData.data(); uint32_t *q = (uint32_t *) pixels.data(); uint32_t *fin = q + npixels; if (!isGray()) { while (q < fin) { uint8_t alpha = (alphaInMain ? uint8_t(*p++) : 0xff); uint8_t r = uint8_t(*p++); uint8_t g = uint8_t(*p++); uint8_t b = uint8_t(*p++); uint32_t pixel = (alpha << 24) | (r << 16) | (g << 8) | b; *q++ = pixel; } } else { while (q < fin) { uint8_t alpha = (alphaInMain ? uint8_t(*p++) : 0xff); uint8_t r = uint8_t(*p++); *q++ = (alpha << 24) | (r << 16) | (r << 8) | r; } } // merge separate alpha channel if (hasAlpha() && alphaChannel.size() > 0) { q = (uint32_t *) pixels.data(); p = alphaChannel.data(); uint32_t pixel; while (q < fin) { pixel = *q; pixel = (pixel & 0x00ffffff) | (*p++ << 24); *q++ = pixel; } } if (iImp->iColorKey >= 0) { uint32_t colorKey = (iImp->iColorKey | 0xff000000); q = (uint32_t *) pixels.data(); while (q < fin) { if (*q == colorKey) *q = iImp->iColorKey; ++q; } } iImp->iData = pixels; } //! Determine if bitmap has alpha channel, colorkey, rgb values (does nothing for JPG). void Bitmap::analyze() { iImp->iColorKey = -1; iImp->iFlags &= EDCT|ERGB; // clear all other flags, we recompute them if (isJpeg()) return; iImp->iFlags &= EDCT; // ERGB will also be recomputed const uint32_t *q = (const uint32_t *) iImp->iData.data(); const uint32_t *fin = q + width() * height(); uint32_t pixel, gray; while (q < fin) { pixel = *q++ & 0x00ffffff; gray = (pixel & 0xff); gray |= (gray << 8) | (gray << 16); if (pixel != gray) { iImp->iFlags |= ERGB; break; } } int candidate = -1, color; uint32_t alpha; q = (const uint32_t *) iImp->iData.data(); while (q < fin) { pixel = *q++; alpha = pixel & 0xff000000; color = pixel & 0x00ffffff; if (alpha != 0 && alpha != 0xff000000) { iImp->iFlags |= EAlpha; return; } if (alpha == 0) { // transparent color found if (candidate < 0) candidate = color; else if (candidate != color) { // two different transparent colors iImp->iFlags |= EAlpha; return; } } else if (color == candidate) { // opaque copy of candidate found iImp->iFlags |= EAlpha; return; } } iImp->iColorKey = candidate; } //! Copy constructor. /*! Since Bitmaps are reference counted, this is very fast. */ Bitmap::Bitmap(const Bitmap &rhs) { iImp = rhs.iImp; if (iImp) iImp->iRefCount++; } //! Destructor. Bitmap::~Bitmap() { if (iImp && --iImp->iRefCount == 0) { delete iImp; } } //! Assignment operator (takes care of reference counting). /*! Very fast. */ Bitmap &Bitmap::operator=(const Bitmap &rhs) { if (this != &rhs) { if (iImp && --iImp->iRefCount == 0) delete iImp; iImp = rhs.iImp; if (iImp) iImp->iRefCount++; } return *this; } //! Save bitmap in XML stream. void Bitmap::saveAsXml(Stream &stream, int id, int pdfObjNum) const { assert(iImp); stream << "= 0) { char buf[10]; sprintf(buf, "%x", colorKey()); stream << " ColorKey=\"" << buf << "\""; } if (pdfObjNum >= 0) { stream << " pdfObject=\"" << pdfObjNum; if (hasAlpha()) stream << " " << pdfObjNum-1; stream << "\"/>\n"; } else { // save data auto data = embed(); stream << " length=\"" << data.first.size() << "\""; if (hasAlpha()) stream << " alphaLength=\"" << data.second.size() << "\""; stream << " encoding=\"base64\">\n"; Base64Stream b64(stream); for (const auto & buffer : { data.first, data.second } ) { const char *p = buffer.data(); const char *fin = p + buffer.size(); while (p != fin) b64.putChar(*p++); } b64.close(); stream << "\n"; } } bool Bitmap::equal(Bitmap rhs) const { if (iImp == rhs.iImp) return true; if (!iImp || !rhs.iImp) return false; if (iImp->iFlags != rhs.iImp->iFlags || iImp->iWidth != rhs.iImp->iWidth || iImp->iHeight != rhs.iImp->iHeight || iImp->iChecksum != rhs.iImp->iChecksum || iImp->iData.size() != rhs.iImp->iData.size()) return false; // check actual data int len = iImp->iData.size(); char *p = iImp->iData.data(); char *q = rhs.iImp->iData.data(); while (len--) { if (*p++ != *q++) return false; } return true; } void Bitmap::computeChecksum() { int s = 0; int len = iImp->iData.size(); char *p = iImp->iData.data(); while (len--) { s = (s & 0x0fffffff) << 3; s += *p++; } iImp->iChecksum = s; } //! Create the data to be embedded in an XML or PDF file. /*! For Jpeg images, this is simply the bitmap data. For other images, rgb/grayscale data and alpha channel are split and deflated separately. */ std::pair Bitmap::embed() const { if (isJpeg()) return std::make_pair(iImp->iData, Buffer()); int npixels = width() * height(); uint32_t *src = (uint32_t *) iImp->iData.data(); uint32_t *fin = src + npixels; uint32_t pixel; Buffer rgb(npixels * (isGray() ? 1 : 3)); char *p = rgb.data(); while (src < fin) { pixel = *src++; if (isGray()) { *p++ = pixel & 0xff; } else { *p++ = (pixel & 0xff0000) >> 16; *p++ = (pixel & 0x00ff00) >> 8; *p++ = (pixel & 0x0000ff); } } int deflatedSize; Buffer deflated = DeflateStream::deflate(rgb.data(), rgb.size(), deflatedSize, 9); rgb = Buffer(deflated.data(), deflatedSize); Buffer alpha; if (hasAlpha()) { alpha = Buffer(npixels); src = (uint32_t *) iImp->iData.data(); p = alpha.data(); while (src < fin) *p++ = (*src++ & 0xff000000) >> 24; deflated = DeflateStream::deflate(alpha.data(), alpha.size(), deflatedSize, 9); alpha = Buffer(deflated.data(), deflatedSize); } return std::make_pair(rgb, alpha); } // -------------------------------------------------------------------- void Bitmap::savePixels(const char *fname) { FILE *file = Platform::fopen(fname, "wb"); if (!file) return; if (isJpeg()) { fwrite(iImp->iData.data(), 1, iImp->iData.size(), file); } else { fprintf(file, "PyRGBA\n%d %d\n255\n", width(), height()); Buffer pixels = Buffer(iImp->iData.size()); uint32_t *p = (uint32_t *) iImp->iData.data(); uint8_t *q = (uint8_t *) pixels.data(); uint32_t *fin = p + width() * height(); while (p < fin) { uint32_t pixel = *p++; *q++ = (pixel & 0x00ff0000) >> 16; *q++ = (pixel & 0x0000ff00) >> 8; *q++ = (pixel & 0x000000ff); *q++ = (pixel & 0xff000000) >> 24; } fwrite(pixels.data(), 1, iImp->iData.size(), file); } fclose(file); } // -------------------------------------------------------------------- //! Return pixels for rendering. /*! Returns empty buffer if it cannot decode the bitmap information. Otherwise, returns a buffer of size width() * height() uint32_t's. The data is in cairo ARGB32 format, that is native-endian uint32_t's with premultiplied alpha. */ Buffer Bitmap::pixelData() { if (!iImp->iPixelsComputed) { iImp->iPixelsComputed = true; if (isJpeg()) { Buffer stream = iImp->iData; Buffer pixels; pixels = Buffer(4 * width() * height()); if (!dctDecode(stream, pixels)) return Buffer(); iImp->iPixelData = pixels; } else { if (hasAlpha() || colorKey() >= 0) { // premultiply RGB data iImp->iPixelData = Buffer(iImp->iData.size()); uint32_t *p = (uint32_t *) iImp->iData.data(); uint32_t *q = (uint32_t *) iImp->iPixelData.data(); uint32_t *fin = p + width() * height(); uint32_t pixel, alpha, alphaM, r, g, b; while (p < fin) { pixel = *p++; alpha = (pixel & 0xff000000); alphaM = alpha >> 24; r = alphaM * (pixel & 0xff0000) / 255; g = alphaM * (pixel & 0x00ff00) / 255; b = alphaM * (pixel & 0x0000ff) / 255; *q++ = alpha | (r & 0xff0000) | (g & 0x00ff00) | (b & 0x0000ff); } } else iImp->iPixelData = iImp->iData; } } return iImp->iPixelData; } // -------------------------------------------------------------------- /* JPG reading code Copyright (c) 1996-2002 Han The Thanh, This code is part of pdfTeX. pdfTeX is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. */ #define JPG_GRAY 1 /* Gray color space, use /DeviceGray */ #define JPG_RGB 3 /* RGB color space, use /DeviceRGB */ #define JPG_CMYK 4 /* CMYK color space, use /DeviceCMYK */ enum JPEG_MARKER { /* JPEG marker codes */ M_SOF0 = 0xc0, /* baseline DCT */ M_SOF1 = 0xc1, /* extended sequential DCT */ M_SOF2 = 0xc2, /* progressive DCT */ M_SOF3 = 0xc3, /* lossless (sequential) */ M_SOF5 = 0xc5, /* differential sequential DCT */ M_SOF6 = 0xc6, /* differential progressive DCT */ M_SOF7 = 0xc7, /* differential lossless */ M_JPG = 0xc8, /* JPEG extensions */ M_SOF9 = 0xc9, /* extended sequential DCT */ M_SOF10 = 0xca, /* progressive DCT */ M_SOF11 = 0xcb, /* lossless (sequential) */ M_SOF13 = 0xcd, /* differential sequential DCT */ M_SOF14 = 0xce, /* differential progressive DCT */ M_SOF15 = 0xcf, /* differential lossless */ M_DHT = 0xc4, /* define Huffman tables */ M_DAC = 0xcc, /* define arithmetic conditioning table */ M_RST0 = 0xd0, /* restart */ M_RST1 = 0xd1, /* restart */ M_RST2 = 0xd2, /* restart */ M_RST3 = 0xd3, /* restart */ M_RST4 = 0xd4, /* restart */ M_RST5 = 0xd5, /* restart */ M_RST6 = 0xd6, /* restart */ M_RST7 = 0xd7, /* restart */ M_SOI = 0xd8, /* start of image */ M_EOI = 0xd9, /* end of image */ M_SOS = 0xda, /* start of scan */ M_DQT = 0xdb, /* define quantization tables */ M_DNL = 0xdc, /* define number of lines */ M_DRI = 0xdd, /* define restart interval */ M_DHP = 0xde, /* define hierarchical progression */ M_EXP = 0xdf, /* expand reference image(s) */ M_APP0 = 0xe0, /* application marker, used for JFIF */ M_APP1 = 0xe1, /* application marker */ M_APP2 = 0xe2, /* application marker */ M_APP3 = 0xe3, /* application marker */ M_APP4 = 0xe4, /* application marker */ M_APP5 = 0xe5, /* application marker */ M_APP6 = 0xe6, /* application marker */ M_APP7 = 0xe7, /* application marker */ M_APP8 = 0xe8, /* application marker */ M_APP9 = 0xe9, /* application marker */ M_APP10 = 0xea, /* application marker */ M_APP11 = 0xeb, /* application marker */ M_APP12 = 0xec, /* application marker */ M_APP13 = 0xed, /* application marker */ M_APP14 = 0xee, /* application marker, used by Adobe */ M_APP15 = 0xef, /* application marker */ M_JPG0 = 0xf0, /* reserved for JPEG extensions */ M_JPG13 = 0xfd, /* reserved for JPEG extensions */ M_COM = 0xfe, /* comment */ M_TEM = 0x01, /* temporary use */ }; inline int read2bytes(FILE *f) { uint8_t c1 = fgetc(f); uint8_t c2 = fgetc(f); return (c1 << 8) + c2; } // -------------------------------------------------------------------- //! Read information about JPEG image from file. /*! Returns NULL on success, an error message otherwise. Sets flags to EDCT and possibly ERGB. */ const char *Bitmap::readJpegInfo(FILE *file, int &width, int &height, Vector &dotsPerInch, uint32_t &flags) { static char jpg_id[] = "JFIF"; bool app0_seen = false; dotsPerInch = Vector(0, 0); flags = EDCT; if (read2bytes(file) != 0xFFD8) { return "The file does not appear to be a JPEG image"; } for (;;) { int ch = fgetc(file); if (ch != 0xff) return "Reading JPEG image failed"; do { ch = fgetc(file); } while (ch == 0xff); ipeDebug("JPEG tag %x", ch & 0xff); int fpos = ftell(file); switch (ch & 0xff) { case M_SOF5: case M_SOF6: case M_SOF7: case M_SOF9: case M_SOF10: case M_SOF11: case M_SOF13: case M_SOF14: case M_SOF15: return "Unsupported type of JPEG compression"; case M_SOF0: case M_SOF1: case M_SOF2: // progressive DCT allowed since PDF-1.3 case M_SOF3: read2bytes(file); /* read segment length */ ch = fgetc(file); if (ch != 8) return "Unsupported bit width of pixels in JPEG image"; height = read2bytes(file); width = read2bytes(file); ch = fgetc(file); switch (ch & 0xff) { case JPG_GRAY: break; case JPG_RGB: flags |= ERGB; break; default: return "Unsupported color space in JPEG image"; } fseek(file, 0, SEEK_SET); return nullptr; // success! case M_APP0: { int len = read2bytes(file); if (app0_seen) { fseek(file, fpos + len, SEEK_SET); break; } for (int i = 0; i < 5; i++) { ch = fgetc(file); if (ch != jpg_id[i]) { return "Reading JPEG image failed"; } } read2bytes(file); // JFIF version char units = fgetc(file); int xres = read2bytes(file); int yres = read2bytes(file); if (xres != 0 && yres != 0) { switch (units) { case 1: /* pixels per inch */ dotsPerInch = Vector(xres, yres); break; case 2: /* pixels per cm */ dotsPerInch = Vector(xres * 2.54, yres * 2.54); break; default: // 0: aspect ratio only break; } } app0_seen = true; fseek(file, fpos + len, SEEK_SET); break; } case M_SOI: // ignore markers without parameters case M_EOI: case M_TEM: case M_RST0: case M_RST1: case M_RST2: case M_RST3: case M_RST4: case M_RST5: case M_RST6: case M_RST7: break; default: // skip variable length markers fseek(file, fpos + read2bytes(file), SEEK_SET); break; } } } //! Read JPEG image from file. /*! Returns the image as a DCT-encoded Bitmap. Sets \a dotsPerInch if the image file contains a resolution, otherwise sets it to (0,0). If reading the file fails, returns a null Bitmap, and sets the error message \a errmsg. */ Bitmap Bitmap::readJpeg(const char *fname, Vector &dotsPerInch, const char * &errmsg) { FILE *file = Platform::fopen(fname, "rb"); if (!file) { errmsg = "Error opening file"; return Bitmap(); } int width, height; uint32_t flags; errmsg = Bitmap::readJpegInfo(file, width, height, dotsPerInch, flags); fclose(file); if (errmsg) return Bitmap(); String a = Platform::readFile(fname); return Bitmap(width, height, flags, Buffer(a.data(), a.size())); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipelatex.cpp0000644000175000017500000003423013561570220016610 0ustar otfriedotfried// -------------------------------------------------------------------- // Interface with Pdflatex // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipestyle.h" #include "ipegroup.h" #include "ipereference.h" #include "ipelatex.h" #include using namespace ipe; /*! \class ipe::Latex \brief Object that converts latex source to PDF format. This object is responsible for creating the PDF representation of text objects. */ //! Create a converter object. Latex::Latex(const Cascade *sheet, LatexType latexType) { iCascade = sheet; iResources = new PdfResources; iLatexType = latexType; iXetex = (latexType == LatexType::Xetex); } //! Destructor. Latex::~Latex() { for (auto &it : iXForms) delete it; delete iResources; } // -------------------------------------------------------------------- //! Return the newly created PdfResources and pass ownership to caller. PdfResources *Latex::takeResources() { PdfResources *r = iResources; iResources = nullptr; return r; } // -------------------------------------------------------------------- class ipe::TextCollectingVisitor : public Visitor { public: TextCollectingVisitor(Latex::TextList *list); virtual void visitText(const Text *obj); virtual void visitGroup(const Group *obj); virtual void visitReference(const Reference *obj); public: bool iTextFound; private: Latex::TextList *iList; }; TextCollectingVisitor::TextCollectingVisitor(Latex::TextList *list) : iList(list) { // nothing } void TextCollectingVisitor::visitText(const Text *obj) { Latex::SText s; s.iText = obj; s.iSize = obj->size(); iList->push_back(s); iTextFound = true; } void TextCollectingVisitor::visitGroup(const Group *obj) { for (Group::const_iterator it = obj->begin(); it != obj->end(); ++it) (*it)->accept(*this); } void TextCollectingVisitor::visitReference(const Reference *) { // need to figure out what to do for symbols } // -------------------------------------------------------------------- /*! Scan an object and insert all text objects into Latex's list. Returns total number of text objects found so far. */ int Latex::scanObject(const Object *obj) { TextCollectingVisitor visitor(&iTextObjects); obj->accept(visitor); return iTextObjects.size(); } /*! Scan a page and insert all text objects into Latex's list. Returns total number of text objects found so far. */ int Latex::scanPage(Page *page) { page->applyTitleStyle(iCascade); TextCollectingVisitor visitor(&iTextObjects); const Text *title = page->titleText(); if (title) title->accept(visitor); for (int i = 0; i < page->count(); ++i) { visitor.iTextFound = false; page->object(i)->accept(visitor); if (visitor.iTextFound) page->invalidateBBox(i); } return iTextObjects.size(); } //! Create Text object to represent the page number of this view. void Latex::addPageNumber(int pno, int vno, int npages, int nviews) { const StyleSheet::PageNumberStyle *pns = iCascade->findPageNumberStyle(); AllAttributes attr; attr.iStroke = pns->iColor; attr.iTextSize = pns->iSize; attr.iHorizontalAlignment = pns->iHorizontalAlignment; attr.iVerticalAlignment = pns->iVerticalAlignment; char latex[256]; sprintf(latex, "\\def\\ipeNumber#1#2{#%d}" "\\setcounter{ipePage}{%d}\\setcounter{ipeView}{%d}" "\\setcounter{ipePages}{%d}\\setcounter{ipeViews}{%d}", (nviews > 1 ? 2 : 1), pno + 1, vno + 1, npages, nviews); String data = pns->iText.empty() ? "\\ipeNumber{\\arabic{ipePage}}{\\arabic{ipePage} - \\arabic{ipeView}}" : pns->iText; Text *t = new Text(attr, String(latex) + data, pns->iPos, Text::ELabel); SText s; s.iText = t; s.iSize = t->size(); iTextObjects.push_back(s); PdfResources::SPageNumber pn; pn.page = pno; pn.view = vno; pn.text.reset(t); iResources->addPageNumber(pn); } /*! Create a Latex source file with all the text objects collected before. The client should have prepared a directory for the Pdflatex run, and pass the name of the Latex source file to be written by Latex. Returns the number of text objects that did not yet have an XForm, or a negative error code. */ int Latex::createLatexSource(Stream &stream, String preamble) { bool ancient = (getenv("IPEANCIENTPDFTEX") != nullptr); int count = 0; stream << "\\nonstopmode\n"; if (!iXetex) { stream << "\\expandafter\\ifx\\csname pdfobjcompresslevel\\endcsname" << "\\relax\\else\\pdfobjcompresslevel0\\fi\n"; if (!ancient && iLatexType != LatexType::Luatex) stream << "\\ifnum\\the\\pdftexversion<140" << "\\errmessage{Pdftex is too old. " << "Set IPEANCIENTPDFTEX environment variable!}\\fi\n"; if (iLatexType == LatexType::Luatex) // load luatex85 for new versions of Luatex stream << "\\expandafter\\ifx\\csname pdfcolorstack\\endcsname\\relax" << "\\RequirePackage{luatex85}\\fi\n"; } stream << "\\documentclass{article}\n" << "\\newdimen\\ipefs\n" << "\\newcounter{ipePage}\\newcounter{ipeView}\n" << "\\newcounter{ipePages}\\newcounter{ipeViews}\n" << "\\newcommand{\\PageTitle}[1]{#1}\n" << "\\newcommand{\\ipesymbol}[4]{$\\bullet$}\n"; stream << "\\def\\ipedefinecolors#1{\\ipecolorpreamble{#1}\\let\\ipecolorpreamble\\relax}\n" << "\\def\\ipecolorpreamble#1{\\usepackage[#1]{xcolor}\n"; AttributeSeq colors; iCascade->allNames(EColor, colors); for (AttributeSeq::const_iterator it = colors.begin(); it != colors.end(); ++it) { // only symbolic names (not black, white, void) String name = it->string(); Color value = iCascade->find(EColor, *it).color(); if (value.isGray()) stream << "\\definecolor{" << name << "}{gray}{" << value.iRed << "}\n"; else stream << "\\definecolor{" << name << "}{rgb}{" << value.iRed << "," << value.iGreen << "," << value.iBlue << "}\n"; } stream << "}\n"; if (iXetex) { stream << "\\def\\ipesetcolor#1#2#3{\\special{pdf:bc [#1 #2 #3]}}\n" << "\\def\\iperesetcolor{\\special{pdf:ec}}\n"; } else if (!ancient) { stream << "\\makeatletter\n" << "\\def\\ipesetcolor#1#2#3{\\def\\current@color{#1 #2 #3 rg #1 #2 #3 RG}" << "\\pdfcolorstack\\@pdfcolorstack push{\\current@color}}\n" << "\\def\\iperesetcolor{\\pdfcolorstack\\@pdfcolorstack pop}\n" << "\\makeatother\n"; } else { stream << "\\def\\ipesetcolor#1#2#3{\\color[rgb]{#1,#2,#3}}\n" << "\\def\\iperesetcolor{}\n"; } stream << iCascade->findPreamble() << "\n" << preamble << "\n" << "\\ipedefinecolors{}\n" << "\\pagestyle{empty}\n" << "\\newcount\\bigpoint\\dimen0=0.01bp\\bigpoint=\\dimen0\n" << "\\begin{document}\n" << "\\begin{picture}(500,500)\n"; int curnum = 1; if (iXetex) stream << "\\special{pdf:obj @ipeforms []}\n"; for (auto &it : iTextObjects) { const Text *text = it.iText; if (!text->getXForm()) count++; Attribute fsAttr = iCascade->find(ETextSize, it.iSize); // compute x-stretch factor from textstretch Fixed stretch(1); if (it.iSize.isSymbolic()) stretch = iCascade->find(ETextStretch, it.iSize).number(); stream << "\\setbox0=\\hbox{"; if (text->isMinipage()) { stream << "\\begin{minipage}{" << text->width()/stretch.toDouble() << "bp}"; } if (fsAttr.isNumber()) { Fixed fs = fsAttr.number(); stream << "\\fontsize{" << fs << "}" << "{" << fs.mult(6, 5) << "bp}\\selectfont\n"; } else stream << fsAttr.string() << "\n"; Color col = iCascade->find(EColor, text->stroke()).color(); stream << "\\ipesetcolor{" << col.iRed.toDouble() << "}{" << col.iGreen.toDouble() << "}{" << col.iBlue.toDouble() << "}%\n"; Attribute absStyle = iCascade->find(text->isMinipage() ? ETextStyle : ELabelStyle, text->style()); String style = absStyle.string(); int sp = 0; while (sp < style.size() && style[sp] != '\0') ++sp; stream << style.substr(0, sp); String txt = text->text(); stream << txt; if (text->isMinipage()) { if (!txt.empty() && txt[txt.size() - 1] != '\n') stream << "\n"; stream << style.substr(sp + 1); stream << "\\end{minipage}"; } else stream << style.substr(sp + 1) << "%\n"; stream << "\\iperesetcolor}\n" << "\\count0=\\dp0\\divide\\count0 by \\bigpoint\n"; if (iXetex) { stream << "\\special{ pdf:bxobj @ipeform" << curnum << "\n" << "width \\the\\wd0 \\space " << "height \\the\\ht0 \\space " << "depth \\the\\dp0}%\n" << "\\usebox0%\n" << "\\special{pdf:exobj}%\n" << "\\special{pdf:obj @ipeinfo" << curnum << " <<" << " /IpeId " << curnum << " /IpeStretch " << stretch.toDouble() << " /IpeDepth \\the\\count0" << " /IpeXForm @ipeform" << curnum << " >>}\n" << "\\special{pdf:close @ipeinfo" << curnum << "}\n" << "\\special{pdf:put @ipeforms @ipeinfo" << curnum << "}\n" << "\\put(0,0){\\special{pdf:uxobj @ipeform" << curnum << "}}\n"; } else { stream << "\\pdfxform attr{/IpeId " << curnum << " /IpeStretch " << stretch.toDouble() << " /IpeDepth \\the\\count0}" << "0\\put(0,0){\\pdfrefxform\\pdflastxform}\n"; } ++curnum; } stream << "\\end{picture}\n"; if (iXetex) stream << "\\special{pdf:close @ipeforms}\n" << "\\special{pdf:put @resources << /Ipe @ipeforms >>}\n"; stream << "\\end{document}\n"; return count; } bool Latex::getXForm(String key, const PdfDict *ipeInfo) { /* /Type /XObject /Subtype /Form /Id /abcd1234 /Depth 246 /Stretch [ 3 3 ] /BBox [0 0 4.639 4.289] /FormType 1 /Matrix [1 0 0 1 0 0] /Resources 11 0 R */ Text::XForm *xf = new Text::XForm; iXForms.push_back(xf); const PdfObj *xform = iXetex ? ipeInfo->get("IpeXForm", nullptr) : iResources->findResource("XObject", key); int xformNum = -1; if (xform && xform->ref()) { xformNum = xform->ref()->value(); xform = iResources->object(xformNum); } if (!xform || !xform->dict()) return false; const PdfDict *xformd = xform->dict(); if (iXetex) { // determine key const PdfDict *d = iResources->resourcesOfKind("XObject"); for (int i = 0; i < d->count(); ++i) { const PdfObj *obj = d->value(i); if (obj->ref() && obj->ref()->value() == xformNum) { xf->iName = d->key(i); break; } } if (xf->iName.empty()) return false; } else { xf->iName = key; ipeInfo = xformd; } double val; // Get id if (!ipeInfo->getNumber("IpeId", val, &iPdf)) return false; xf->iRefCount = val; // abusing refcount field if (!ipeInfo->getNumber("IpeDepth", val, &iPdf)) return false; xf->iDepth = int(val); if (!ipeInfo->getNumber("IpeStretch", val, &iPdf)) return false; xf->iStretch = val; // Get BBox std::vector a; if (!xformd->getNumberArray("BBox", &iPdf, a) || a.size() != 4) return false; xf->iBBox.addPoint(Vector(a[0], a[1])); xf->iBBox.addPoint(Vector(a[2], a[3])); if (!xformd->getNumberArray("Matrix", &iPdf, a) || a.size() != 6) return false; if (a[0] != 1.0 || a[1] != 0.0 || a[2] != 0.0 || a[3] != 1.0) { ipeDebug("PDF XObject has a non-trivial transformation"); return false; } xf->iTranslation = Vector(-a[4], -a[5]) - xf->iBBox.bottomLeft(); return true; } //! Read the PDF file created by Pdflatex. /*! Must have performed the call to Pdflatex, and pass the name of the resulting output file. */ bool Latex::readPdf(DataSource &source) { if (!iPdf.parse(source)) { warn("Ipe cannot parse the PDF file produced by Pdflatex."); return false; } const PdfDict *page1 = iPdf.page(); const PdfObj *res = page1->get("Resources", &iPdf); if (!res || !res->dict()) return false; if (!iResources->collect(res->dict(), &iPdf)) return false; if (iXetex) { const PdfObj *obj = res->dict()->get("Ipe", &iPdf); if (!obj || !obj->array()) { warn("Page 1 has no /Ipe link."); return false; } for (int i = 0; i < obj->array()->count(); i++) { const PdfObj *info = obj->array()->obj(i, &iPdf); if (!info || !info->dict()) return false; if (!getXForm(String(), info->dict())) return false; } } else { const PdfObj *obj = res->dict()->get("XObject", &iPdf); if (!obj || !obj->dict()) { warn("Page 1 has no XForms."); return false; } for (int i = 0; i < obj->dict()->count(); i++) { String key = obj->dict()->key(i); if (!getXForm(key, nullptr)) return false; } } return true; } //! Notify all text objects about their updated PDF code. /*! Returns true if successful. */ bool Latex::updateTextObjects() { int curnum = 1; for (auto &it : iTextObjects) { auto xf = std::find_if(iXForms.begin(), iXForms.end(), [curnum](Text::XForm *f) { return f->iRefCount == curnum; } ); if (xf == iXForms.end()) return false; Text::XForm *xform = *xf; iXForms.erase(xf); it.iText->setXForm(xform); ++curnum; } return true; } /*! Messages about the (mis)behaviour of Pdflatex, probably incomprehensible to the user. */ void Latex::warn(String msg) { ipeDebug(msg.z()); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipepdfparser.cpp0000644000175000017500000005717413561570220017475 0ustar otfriedotfried// -------------------------------------------------------------------- // PDF parsing // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepdfparser.h" #include "ipeutils.h" #include using namespace ipe; //------------------------------------------------------------------------ // A '1' in this array means the character is white space. // A '1' or '2' means the character ends a name or command. // '2' == () {} [] <> / % static char specialChars[256] = { 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 0, // 0x 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 1x 1, 0, 0, 0, 0, 2, 0, 0, 2, 2, 0, 0, 0, 0, 0, 2, // 2x 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 2, 0, // 3x 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 4x 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 2, 0, 0, // 5x 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 6x 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 2, 0, 0, // 7x 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 8x 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 9x 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // ax 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // bx 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // cx 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // dx 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // ex 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 // fx }; // -------------------------------------------------------------------- inline int toInt(String &s) { return std::strtol(s.z(), nullptr, 10); } // -------------------------------------------------------------------- /*! \class ipe::PdfObj * \ingroup base * \brief Abstract base class for PDF objects. */ //! Pure virtual destructor. PdfObj::~PdfObj() { // nothing } //! Return this object as PDF null object. const PdfNull *PdfObj::null() const noexcept { return nullptr; } //! Return this object as PDF bool object. const PdfBool *PdfObj::boolean() const noexcept { return nullptr; } //! Return this object as PDF number object. const PdfNumber *PdfObj::number() const noexcept { return nullptr; } //! Return this object as PDF string object. const PdfString *PdfObj::string() const noexcept { return nullptr; } //! Return this object as PDF name object. const PdfName *PdfObj::name() const noexcept { return nullptr; } //! Return this object as PDF reference object. const PdfRef *PdfObj::ref() const noexcept { return nullptr; } //! Return this object as PDF array object. const PdfArray *PdfObj::array() const noexcept { return nullptr; } //! Return this object as PDF dictionary object. const PdfDict *PdfObj::dict() const noexcept { return nullptr; } //! Return PDF representation of the object. String PdfObj::repr() const noexcept { String d; StringStream ss(d); write(ss); return d; } /*! \class ipe::PdfNull * \ingroup base * \brief The PDF null object. */ const PdfNull *PdfNull::null() const noexcept { return this; } void PdfNull::write(Stream &stream, const PdfRenumber *, bool infl) const noexcept { stream << "null"; } /*! \class ipe::PdfBool * \ingroup base * \brief The PDF bool object. */ const PdfBool *PdfBool::boolean() const noexcept { return this; } void PdfBool::write(Stream &stream, const PdfRenumber *, bool infl) const noexcept { stream << (iValue ? "true" : "false"); } /*! \class ipe::PdfNumber * \ingroup base * \brief The PDF number object. */ const PdfNumber *PdfNumber::number() const noexcept { return this; } void PdfNumber::write(Stream &stream, const PdfRenumber *, bool infl) const noexcept { stream << iValue; } /*! \class ipe::PdfString * \ingroup base * \brief The PDF string object. */ const PdfString *PdfString::string() const noexcept { return this; } void PdfString::write(Stream &stream, const PdfRenumber *, bool infl) const noexcept { if (iBinary) { stream << "<" << iValue << ">"; } else { char octbuf[5]; stream << "("; for (int i = 0; i < iValue.size(); ++i) { int ch = iValue[i]; if ((0 <= ch && ch < 0x20) || ch == '\\' || ch == '(' || ch == ')') { sprintf(octbuf, "\\%.3o", (ch & 0xff)); stream << octbuf; } else stream.putChar(ch); } stream << ")"; } } //! Return value of string after decoding binary strings. String PdfString::decode() const noexcept { if (!iBinary) return iValue; String result; Lex lex(iValue); while (!lex.eos()) result += char(lex.getHexByte()); return result; } /*! \class ipe::PdfName * \ingroup base * \brief The PDF name object. */ const PdfName *PdfName::name() const noexcept { return this; } void PdfName::write(Stream &stream, const PdfRenumber *, bool infl) const noexcept { stream << "/" << iValue; } /*! \class ipe::PdfRef * \ingroup base * \brief The PDF reference object (indirect object). */ const PdfRef *PdfRef::ref() const noexcept { return this; } void PdfRef::write(Stream &stream, const PdfRenumber *renumber, bool infl) const noexcept { if (renumber) { auto it = renumber->find(iValue); if (it != renumber->end()) { stream << it->second << " 0 R"; return; } } stream << iValue << " 0 R"; } /*! \class ipe::PdfArray * \ingroup base * \brief The PDF array object. */ const PdfArray *PdfArray::array() const noexcept { return this; } void PdfArray::write(Stream &stream, const PdfRenumber *renumber, bool infl) const noexcept { stream << "["; String sep = ""; for (int i = 0; i < count(); ++i) { stream << sep; sep = " "; obj(i, nullptr)->write(stream, renumber); } stream << "]"; } PdfArray::~PdfArray() { for (std::vector::iterator it = iObjects.begin(); it != iObjects.end(); ++it) { delete *it; *it = nullptr; } } //! Append an object to array. /*! Array takes ownership of the object. */ void PdfArray::append(const PdfObj *obj) { iObjects.push_back(obj); } //! Return object with \a index in array. /*! Indirect objects (references) are looked up if \a file is not nullptr, and the object referred to is returned (nullptr if it does not exist). Object remains owned by array. */ const PdfObj *PdfArray::obj(int index, const PdfFile *file) const noexcept { const PdfObj *obj = iObjects[index]; if (file && obj->ref()) { int n = obj->ref()->value(); return file->object(n); } return obj; } /*! \class ipe::PdfDict * \ingroup base * \brief The PDF dictionary and stream objects. A dictionary may or may not have attached stream data. */ const PdfDict *PdfDict::dict() const noexcept { return this; } //! Return PDF representation of the PdfDict without the stream. String PdfDict::dictRepr() const noexcept { String d; StringStream ss(d); dictWrite(ss, nullptr, false, iStream.size()); return d; } void PdfDict::dictWrite(Stream &stream, const PdfRenumber *renumber, bool infl, int length) const noexcept { stream << "<<"; for (std::vector::const_iterator it = iItems.begin(); it != iItems.end(); ++it) { if (it != iItems.begin()) stream << " "; if (infl && it->iKey == "Filter" && it->iVal->name() && it->iVal->name()->value() == "FlateDecode") continue; // remove filter and inflate stream stream << "/" << it->iKey << " "; if (it->iKey == "Length") stream << length; else it->iVal->write(stream, renumber); } stream << ">>"; } void PdfDict::write(Stream &stream, const PdfRenumber *renumber, bool infl) const noexcept { Buffer s = infl ? inflate() : iStream; dictWrite(stream, renumber, infl, s.size()); if (s.size() > 0) { stream << "\nstream\n"; for (int i = 0; i < s.size(); ++i) stream.putChar(s[i]); stream << "\nendstream"; } } PdfDict::~PdfDict() { for (std::vector::iterator it = iItems.begin(); it != iItems.end(); ++it) { delete it->iVal; it->iVal = nullptr; } } //! Add stream data to this dictionary. void PdfDict::setStream(const Buffer &stream) { iStream = stream; } //! Add a (key, value) pair to the dictionary. /*! Dictionary takes ownership of \a obj. */ void PdfDict::add(String key, const PdfObj *obj) { Item item; item.iKey = key; item.iVal = obj; iItems.push_back(item); } //! Look up key in dictionary. /*! Indirect objects (references) are looked up if \a file is not nullptr, and the object referred to is returned. Returns nullptr if key is not in dictionary. */ const PdfObj *PdfDict::get(String key, const PdfFile *file) const noexcept { for (std::vector::const_iterator it = iItems.begin(); it != iItems.end(); ++it) { if (it->iKey == key) { if (file && it->iVal->ref()) return file->object(it->iVal->ref()->value()); else return it->iVal; } } return nullptr; // not in dictionary } //! Retrieve a single number and stor in \a val. bool PdfDict::getNumber(String key, double &val, const PdfFile *file) const noexcept { const PdfObj *obj = get(key, file); if (!obj || !obj->number()) return false; val = obj->number()->value(); return true; } //! Retrieve an array of numbers and store in \a vals. bool PdfDict::getNumberArray(String key, const PdfFile *file, std::vector &vals) const noexcept { const PdfObj *obj = get(key, file); if (!obj || !obj->array()) return false; vals.clear(); for (int i = 0; i < obj->array()->count(); i++) { const PdfObj *a = obj->array()->obj(i, file); if (!a || !a->number()) return false; vals.push_back(a->number()->value()); } return true; } //! Is this stream compressed with flate compression? bool PdfDict::deflated() const noexcept { const PdfObj *f = get("Filter", nullptr); return !(!f || !f->name() || f->name()->value() != "FlateDecode"); } //! Return the (uncompressed) stream data. /*! This only handles the /Flate compression. */ Buffer PdfDict::inflate() const noexcept { if (iStream.size() == 0 || !deflated()) return iStream; String dest; BufferSource bsource(iStream); InflateSource source(bsource); int ch = source.getChar(); while (ch != EOF) { dest += char(ch); ch = source.getChar(); } return Buffer(dest.data(), dest.size()); } // -------------------------------------------------------------------- /*! \class ipe::PdfParser * \ingroup base * \brief PDF parser The parser understands the syntax of PDF files, but very little of its semantics. It is meant to be able to parse PDF documents created by Ipe for loading, and to extract information from PDF files created by Pdflatex or Xelatex. The parser reads a PDF file sequentially from front to back, ignores the contents of 'xref' sections, stores only generation 0 objects, and stops after reading the first 'trailer' section (so it cannot deal with files with incremental updates). It cannot handle stream objects whose /Length entry has been deferred (using an indirect object). */ //! Construct with a data source. PdfParser::PdfParser(DataSource &source) : iSource(source) { iPos = 0; getChar(); // init iCh getToken(); // init iTok } //! Skip white space and comments. void PdfParser::skipWhiteSpace() { while (!eos() && (specialChars[iCh] == 1 || iCh == '%')) { // handle comment if (iCh == '%') { while (!eos() && iCh != '\n' && iCh != '\r') getChar(); } getChar(); } } //! Read the next token from the input stream. void PdfParser::getToken() { iTok.iString.erase(); iTok.iType = PdfToken::EErr; skipWhiteSpace(); if (eos()) return; // Err // parse string if (iCh == '(') { int nest = 0; getChar(); while (iCh != ')' || nest > 0) { if (eos()) return; // Err if (iCh == '\\') { getChar(); if ('0' <= iCh && iCh <= '9') { // octal char code char buf[4]; int i = 0; buf[i++] = char(iCh); getChar(); if ('0' <= iCh && iCh <= '9') { buf[i++] = char(iCh); getChar(); } if ('0' <= iCh && iCh <= '9') { buf[i++] = char(iCh); getChar(); } buf[i] = '\0'; iTok.iString.append(char(std::strtol(buf, nullptr, 8))); } else { iTok.iString.append(char(iCh)); getChar(); } } else { if (iCh == '(') ++nest; else if (iCh == ')') --nest; iTok.iString.append(char(iCh)); getChar(); } } getChar(); // skip closing ')' iTok.iType = PdfToken::EString; return; } if (iCh == '<') { getChar(); // recognize dictionary separator "<<" if (iCh == '<') { getChar(); iTok.iType = PdfToken::EDictBg; return; } // otherwise it's a binary string while (iCh != '>') { if (eos()) return; // Err iTok.iString.append(char(iCh)); getChar(); } // We don't bother to decode it getChar(); // skip '>' iTok.iType = PdfToken::EStringBinary; return; } int ch = iCh; iTok.iString.append(char(iCh)); getChar(); // recognize array separators if (ch == '[') { iTok.iType = PdfToken::EArrayBg; return; } else if (ch == ']') { iTok.iType = PdfToken::EArrayEnd; return; } // recognize dictionary separator ">>" if (ch == '>') { if (iCh != '>') return; // Err getChar(); iTok.iType = PdfToken::EDictEnd; return; } // collect all characters up to white-space or separator while (!specialChars[iCh]) { if (eos()) return; // Err iTok.iString.append(char(iCh)); getChar(); } if (('0' <= ch && ch <= '9') || ch == '+' || ch == '-' || ch == '.') iTok.iType = PdfToken::ENumber; else if (ch == '/') iTok.iType = PdfToken::EName; else if (iTok.iString == "null") iTok.iType = PdfToken::ENull; else if (iTok.iString == "true") iTok.iType = PdfToken::ETrue; else if (iTok.iString == "false") iTok.iType = PdfToken::EFalse; else iTok.iType = PdfToken::EOp; } // -------------------------------------------------------------------- //! Parse elements of an array. PdfArray *PdfParser::makeArray() { std::unique_ptr arr(new PdfArray); for (;;) { if (iTok.iType == PdfToken::EArrayEnd) { // finish array getToken(); return arr.release(); } // check for reference object if (iTok.iType == PdfToken::ENumber) { PdfToken t1 = iTok; getToken(); if (iTok.iType == PdfToken::ENumber) { PdfToken t2 = iTok; getToken(); if (iTok.iType == PdfToken::EOp && iTok.iString == "R") { arr->append(new PdfRef(toInt(t1.iString))); getToken(); } else { arr->append(new PdfNumber(Platform::toDouble(t1.iString))); arr->append(new PdfNumber(Platform::toDouble(t2.iString))); } } else { arr->append(new PdfNumber(Platform::toDouble(t1.iString))); } } else { PdfObj *obj = getObject(); if (!obj) return nullptr; arr->append(obj); } } } PdfDict *PdfParser::makeDict() { std::unique_ptr dict(new PdfDict); for (;;) { if (iTok.iType == PdfToken::EDictEnd) { // finish getToken(); // check whether stream follows if (iTok.iType != PdfToken::EOp || iTok.iString != "stream") return dict.release(); // time to read the stream while (!eos() && iCh != '\n') getChar(); getChar(); // skip '\n' // now at beginning of stream const PdfObj *len = dict->get("Length", nullptr); if (len && len->ref()) { ipeDebug("/Length entry of dictionary is a reference."); return nullptr; } if (!len || !len->number()) return nullptr; int bytes = int(len->number()->value()); Buffer buf(bytes); char *p = buf.data(); while (bytes--) { *p++ = char(iCh); getChar(); } dict->setStream(buf); getToken(); if (iTok.iType != PdfToken::EOp || iTok.iString != "endstream") return nullptr; getToken(); return dict.release(); } // must read name if (iTok.iType != PdfToken::EName) return nullptr; String name = iTok.iString.substr(1); getToken(); // check for reference object if (iTok.iType == PdfToken::ENumber) { PdfToken t1 = iTok; getToken(); if (iTok.iType == PdfToken::ENumber) { PdfToken t2 = iTok; getToken(); if (iTok.iType == PdfToken::EOp && iTok.iString == "R") { dict->add(name, new PdfRef(toInt(t1.iString))); getToken(); } else return nullptr; // should be name or '>>' } else dict->add(name, new PdfNumber(Platform::toDouble(t1.iString))); } else { PdfObj *obj = getObject(); if (!obj) return nullptr; dict->add(name, obj); } } } //! Read one object from input stream. PdfObj *PdfParser::getObject() { PdfToken tok = iTok; getToken(); switch (tok.iType) { case PdfToken::ENumber: return new PdfNumber(Platform::toDouble(tok.iString)); case PdfToken::EString: return new PdfString(tok.iString); case PdfToken::EStringBinary: return new PdfString(tok.iString, true); case PdfToken::EName: return new PdfName(tok.iString.substr(1)); case PdfToken::ENull: return new PdfNull; case PdfToken::ETrue: return new PdfBool(true); case PdfToken::EFalse: return new PdfBool(false); case PdfToken::EArrayBg: return makeArray(); case PdfToken::EDictBg: return makeDict(); // anything else is an error case PdfToken::EErr: default: return nullptr; } } //! Parse an object definition (current token is object number). PdfObj *PdfParser::getObjectDef() { getToken(); if (iTok.iType != PdfToken::ENumber || iTok.iString != "0") return nullptr; getToken(); if (iTok.iType != PdfToken::EOp || iTok.iString != "obj") return nullptr; getToken(); PdfObj *obj = getObject(); if (!obj) return nullptr; if (iTok.iType != PdfToken::EOp || iTok.iString != "endobj") return nullptr; getToken(); return obj; } //! Skip xref table (current token is 'xref') void PdfParser::skipXRef() { getToken(); // first object number getToken(); // number of objects int k = toInt(iTok.iString); getToken(); while (k--) { getToken(); // obj num getToken(); // gen num getToken(); // n or f } } //! Parse trailer dictionary (current token is 'trailer') PdfDict *PdfParser::getTrailer() { getToken(); if (iTok.iType != PdfToken::EDictBg) return nullptr; getToken(); return makeDict(); } // -------------------------------------------------------------------- /*! \class ipe::PdfFile * \ingroup base * \brief All information obtained by parsing a PDF file. */ bool PdfFile::parseObjectStream(const PdfDict *d) { const PdfObj *objn = d->get("N", this); const PdfObj *objfirst = d->get("First", this); int n = objn->number() ? objn->number()->value() : -1; int first = objfirst->number() ? objfirst->number()->value() : -1; if (n < 0 || first < 0) return false; Buffer stream = d->inflate(); BufferSource source(stream); PdfParser parser(source); std::vector dir; for (int i = 0; i < 2 * n; ++i) { PdfToken t = parser.token(); if (t.iType != PdfToken::ENumber) return false; dir.push_back(toInt(t.iString)); parser.getToken(); } for (int i = 0; i < n; ++i) { int num = dir[2*i]; source.setPosition(first + dir[2*i+1]); parser.getChar(); parser.getToken(); PdfObj *obj = parser.getObject(); if (!obj) return false; // ipeDebug("Object: %s", obj->repr().z()); iObjects[num] = std::unique_ptr(obj); } return true; } //! Parse entire PDF stream, and store objects. bool PdfFile::parse(DataSource &source) { PdfParser parser(source); for (;;) { PdfToken t = parser.token(); if (t.iType == PdfToken::ENumber) { // 0 obj starts an object int num = toInt(t.iString); std::unique_ptr obj(parser.getObjectDef()); if (!obj) { ipeDebug("Failed to get object %d", num); return false; } const PdfDict *d = obj->dict(); const PdfObj *type = d ? d->get("Type", this) : nullptr; if (type && type->name() && type->name()->value() == "ObjStm") { if (!parseObjectStream(d)) return false; } else if (type && type->name() && type->name()->value() == "XRef") { iTrailer = std::unique_ptr(obj.release()->dict()); } else { // ipeDebug("Object: %s", obj->repr().z()); iObjects[num] = std::move(obj); } } else if (t.iType == PdfToken::EOp) { if (t.iString == "trailer") { iTrailer = std::unique_ptr(parser.getTrailer()); if (!iTrailer) { ipeDebug("Failed to get trailer"); return false; } return readPageTree(); } else if (t.iString == "xref") { parser.skipXRef(); } else if (t.iString == "startxref") { return readPageTree(); // this is the end } else { ipeDebug("Weird token: %s", t.iString.z()); // don't know what's happening return false; } } else { ipeDebug("Weird token type: %d %s", t.iType, t.iString.z()); // don't know what's happening return false; } } } //! Return object with number \a num. const PdfObj *PdfFile::object(int num) const noexcept { auto got = iObjects.find(num); if (got != iObjects.end()) return got->second.get(); else return nullptr; } //! Take ownership of object with number \a num, remove from PdfFile. std::unique_ptr PdfFile::take(int num) { auto got = iObjects.find(num); if (got != iObjects.end()) { std::unique_ptr obj = std::move(got->second); iObjects.erase(got); return obj; } else return std::unique_ptr(); } //! Return root catalog of PDF file. const PdfDict *PdfFile::catalog() const noexcept { const PdfObj *root = iTrailer->get("Root", this); assert(root && root->dict()); return root->dict(); } bool PdfFile::readPageTree(const PdfObj *ptn) { if (ptn == nullptr) ptn = catalog()->get("Pages", this); if (!ptn || !ptn->dict()) return false; const PdfObj *kids = ptn->dict()->get("Kids", this); if (!kids || !kids->array()) return false; for (int i = 0; i < kids->array()->count(); ++i) { const PdfObj *page = kids->array()->obj(i, this); if (!page || !page->dict()) return false; const PdfObj *type = page->dict()->get("Type", this); if (!type || !type->name()) return false; if (type->name()->value() == "Pages") readPageTree(page); else if (type->name()->value() == "Page") iPages.push_back(page->dict()); else return false; } return true; } //! Return a page of the document. const PdfDict *PdfFile::page(int pno) const noexcept { if (pno < 0 || pno >= countPages()) return nullptr; return iPages[pno]; } //! Return mediabox of a page. Rect PdfFile::mediaBox(const PdfDict *pg) const { Rect box; std::vector a; if (pg && pg->getNumberArray("MediaBox", this, a) && a.size() == 4) { box.addPoint(Vector(a[0], a[1])); box.addPoint(Vector(a[2], a[3])); } return box; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipebase.cpp0000644000175000017500000004640713561570220016416 0ustar otfriedotfried// -------------------------------------------------------------------- // Basic classes // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebase.h" #include #include #include using namespace ipe; // -------------------------------------------------------------------- /*! \defgroup base Ipe Base \brief Basic classes for Ipe. Some very basic type definitions, streams, lexical analysis, and XML parsing. All parts of Ipe make use of the STL. The C++ I/O streams library is not used, as Ipelib doesn't do much I/O. Ipe objects support internalization and externalization through an abstract interface based on ipe::Stream's. Clients of Ipelib can use any I/O library that implements this interface. Ipe simply uses \c cstdio. */ // -------------------------------------------------------------------- /*! \class ipe::String \ingroup base \brief Strings and buffers. String is is an implicitly shared byte string. It is designed to be efficient for strings of arbitrary length, and supposed to be passed by value (the size of String is a single pointer). Sharing is implicit---the string creates its own representation as soon as it is modified. String can be used for binary data. For text, it is usually assumed that the string is UTF-8 encoded, but only the unicode member function actually requires this. In particular, all indices into the string are byte indices, not Unicode character indices. */ String::Imp *String::theEmptyString = { nullptr }; String::Imp *String::emptyString() noexcept { if (theEmptyString == nullptr) { theEmptyString = new Imp; theEmptyString->iRefCount = 10; // always > 1 theEmptyString->iSize = 0; theEmptyString->iCapacity = 0; theEmptyString->iData = nullptr; } // increment every time it's requested to make sure it's never destroyed ++theEmptyString->iRefCount; return theEmptyString; } //! Construct an empty string. String::String() noexcept { iImp = emptyString(); } //! Construct a string by making copy of \a str. String::String(const char *str) noexcept { if (!str || !str[0]) { iImp = emptyString(); } else { int len = strlen(str); iImp = new Imp; iImp->iRefCount = 1; iImp->iSize = len; iImp->iCapacity = (len + 32) & ~15; iImp->iData = new char[iImp->iCapacity]; memcpy(iImp->iData, str, iImp->iSize); } } //! Construct string by taking ownership of given \a data. String String::withData(char *data, int len) noexcept { if (!len) len = strlen(data); String r; // empty string --r.iImp->iRefCount; r.iImp = new Imp; r.iImp->iRefCount = 1; r.iImp->iSize = len; r.iImp->iCapacity = len; r.iImp->iData = data; return r; } //! Construct string by making copy of \a str with given \a len. String::String(const char *str, int len) noexcept { if (!str || !len) iImp = emptyString(); else { iImp = new Imp; iImp->iRefCount = 1; iImp->iSize = len; iImp->iCapacity = (len + 32) & ~15; iImp->iData = new char[iImp->iCapacity]; memcpy(iImp->iData, str, iImp->iSize); } } //! Copy constructor. //! This only copies the reference and takes constant time. String::String(const String &rhs) noexcept { iImp = rhs.iImp; iImp->iRefCount++; } //! Construct a substring. /*! \a index must be >= 0. \a len can be negative or too large to return entire string. */ String::String(const String &rhs, int index, int len) noexcept { // actually available data int len1 = index < rhs.size() ? rhs.size() - index : 0; if (len < 0 || len1 < len) len = len1; if (!len) { iImp = emptyString(); } else { iImp = new Imp; iImp->iRefCount = 1; iImp->iSize = len; iImp->iCapacity = (len + 32) & ~15; iImp->iData = new char[iImp->iCapacity]; memcpy(iImp->iData, rhs.iImp->iData + index, len); } } //! Assignment takes constant time. String &String::operator=(const String &rhs) noexcept { if (iImp != rhs.iImp) { if (iImp->iRefCount == 1) { delete [] iImp->iData; delete iImp; } else iImp->iRefCount--; iImp = rhs.iImp; iImp->iRefCount++; } return *this; } //! Destruct string if reference count has reached zero. String::~String() noexcept { if (iImp->iRefCount == 1) { delete [] iImp->iData; delete iImp; } else iImp->iRefCount--; } //! Make a private copy of the string with \a n bytes to spare. /*! When a private copy has to be made an extra 32 bytes are ensured. */ void String::detach(int n) noexcept { if (iImp == theEmptyString) { iImp = new Imp; iImp->iRefCount = 1; iImp->iSize = 0; n = (n + 0x1f) & ~0x1f; iImp->iCapacity = (n >= 16) ? n : 16; iImp->iData = new char[iImp->iCapacity]; } else if (iImp->iRefCount > 1 || (iImp->iSize + n > iImp->iCapacity)) { Imp *imp = new Imp; imp->iRefCount = 1; imp->iSize = iImp->iSize; imp->iCapacity = iImp->iCapacity; while (imp->iSize + 32 + n > imp->iCapacity) imp->iCapacity *= 2; imp->iData = new char[imp->iCapacity]; memcpy(imp->iData, iImp->iData, imp->iSize); iImp->iRefCount--; if (iImp->iRefCount == 0) { delete [] iImp->iData; delete iImp; } iImp = imp; } } //! Return a C style string with final zero byte. const char *String::z() const noexcept { if (iImp == theEmptyString) return ""; String *This = const_cast(this); if (iImp->iSize == iImp->iCapacity) This->detach(1); This->iImp->iData[iImp->iSize] = '\0'; return data(); } //! Return index of first occurrence of ch. /*! Return -1 if character does not appear. */ int String::find(char ch) const noexcept { for (int i = 0; i < size(); ++i) if (iImp->iData[i] == ch) return i; return -1; } //! Return index of first occurrence of rhs. /*! Return -1 if not substring is not present. */ int String::find(const char *rhs) const noexcept { int s = strlen(rhs); for (int i = 0; i < size() - s; ++i) if (::strncmp(iImp->iData + i, rhs, s) == 0) return i; return -1; } //! Return line starting at position \a index. //! Index is updated to point to next line. String String::getLine(int &index) const noexcept { int i = index; while (i < size() && iImp->iData[i] != '\r' && iImp->iData[i] != '\n') ++i; String result = substr(index, i-index); if (i < size() && iImp->iData[i] == '\r') ++i; if (i < size() && iImp->iData[i] == '\n') ++i; index = i; return result; } //! Return index of last occurrence of ch. /*! Return -1 if character does not appear. */ int String::rfind(char ch) const noexcept { for (int i = size() - 1; i >= 0; --i) if (iImp->iData[i] == ch) return i; return -1; } //! Make string empty. void String::erase() noexcept { detach(0); iImp->iSize = 0; } //! Append \a rhs to this string. void String::append(const String &rhs) noexcept { int n = rhs.size(); detach(n); memcpy(iImp->iData + iImp->iSize, rhs.iImp->iData, n); iImp->iSize += n; } //! Append \a rhs to this string. void String::append(const char *rhs) noexcept { int n = strlen(rhs); if (n) { detach(n); memcpy(iImp->iData + iImp->iSize, rhs, n); iImp->iSize += n; } } //! Append \a ch to this string. void String::append(char ch) noexcept { detach(1); iImp->iData[iImp->iSize++] = ch; } //! Create substring at the right. /*! Returns the entire string if \a i is larger than its length. */ String String::right(int i) const noexcept { if (i < size()) return String(*this, size() - i, i); else return *this; } //! Does string start with this prefix? (bytewise comparison) bool String::hasPrefix(const char *rhs) const noexcept { int n = strlen(rhs); return (size() >= n && !strncmp(iImp->iData, rhs, n)); } //! Equality operator (bytewise comparison). bool String::operator==(const String &rhs) const noexcept { return (size() == rhs.size() && !strncmp(iImp->iData, rhs.iImp->iData, size())); } //! Equality operator (bytewise comparison). bool String::operator==(const char *rhs) const noexcept { int n = strlen(rhs); return (size() == n && !strncmp(iImp->iData, rhs, n)); } //! Inequality operator (bytewise comparison). bool String::operator<(const String &rhs) const noexcept { int n = size() < rhs.size() ? size() : rhs.size(); int cmp = ::strncmp(iImp->iData, rhs.iImp->iData, n); return (cmp < 0 || (cmp == 0 && size() < rhs.size())); } //! Concatenate this string with \a rhs. String String::operator+(const String &rhs) const noexcept { String s(*this); s.append(rhs); return s; } static const uint8_t bytesFromUTF8[256] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, 2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2, 3,3,3,3,3,3,3,3,4,4,4,4,5,5,5,5 }; static const uint8_t firstByteMark[7] = { 0x00, 0xC0, 0xE0, 0xF0, 0xF8, 0xFC, 0 }; //! Return Unicode value from UTF-8 string. /*! The \a index is incremented to the next UTF-8 character. This returns 0xfffd if there is any problem in parsing UTF-8. */ int String::unicode(int &index) const noexcept { int wch = uint8_t(iImp->iData[index++]); if ((wch & 0xc0) == 0x80) { // not on first byte of a UTF-8 sequence while (index < iImp->iSize && (iImp->iData[index] & 0xc0) == 0x80) index++; return 0xfffd; } int extraBytes = bytesFromUTF8[wch & 0xff]; wch -= firstByteMark[extraBytes]; while (extraBytes--) { if (index >= iImp->iSize) return 0xfffd; // UTF-8 sequence is incomplete if ((iImp->iData[index] & 0xc0) != 0x80) return 0xfffd; // UTF-8 sequence is incorrect wch <<= 6; wch |= (iImp->iData[index++] & 0x3f); } return wch; } // -------------------------------------------------------------------- /*! \class ipe::Fixed \ingroup base \brief Fixed point number with three (decimal) fractional digits */ //! Return value times (a/b) Fixed Fixed::mult(int a, int b) const { return Fixed::fromInternal(iValue * a / b); } Fixed Fixed::fromDouble(double val) { return Fixed::fromInternal(int(val * 1000 + 0.5)); } namespace ipe { /*! \relates Fixed */ Stream &operator<<(Stream &stream, const Fixed &f) { stream << (f.iValue / 1000); if (f.iValue % 1000) { stream << "." << ((f.iValue / 100) % 10); if (f.iValue % 100) { stream << ((f.iValue / 10) % 10); if (f.iValue % 10) stream << (f.iValue % 10); } } return stream; } } // -------------------------------------------------------------------- /*! \class ipe::Lex \ingroup base \brief Lexical analyser. Seeded with a string. */ //! Construct lexical analyzer from a string. Lex::Lex(String str) : iString(str), iPos(0) { // nothing } //! Return NextToken, but without extracting it. String Lex::token() { int pos = iPos; String str = nextToken(); iPos = pos; return str; } //! Extract next token. /*! Skips any whitespace before the token. Returns empty string if end of string is reached. */ String Lex::nextToken() { skipWhitespace(); int mark = iPos; while (!(eos() || uint8_t(iString[iPos]) <= ' ')) ++iPos; return iString.substr(mark, iPos - mark); } //! Extract integer token (skipping whitespace). int Lex::getInt() { String str = nextToken(); return std::strtol(str.z(), nullptr, 10); } inline int hexDigit(int ch) { if ('0' <= ch && ch <= '9') return ch - '0'; if ('a' <= ch && ch <= 'f') return ch - 'a' + 10; if ('A' <= ch && ch <= 'F') return ch - 'A' + 10; return 0; } //! Extract byte in hex (skipping whitespace). int Lex::getHexByte() { int ch1 = '0', ch2 = '0'; skipWhitespace(); if (!eos()) ch1 = iString[iPos++]; skipWhitespace(); if (!eos()) ch2 = iString[iPos++]; return (hexDigit(ch1) << 4) | hexDigit(ch2); } //! Extract hexadecimal token (skipping whitespace). unsigned long int Lex::getHexNumber() { String str = nextToken(); return std::strtoul(str.z(), nullptr, 16); } //! Extract Fixed token (skipping whitespace). Fixed Lex::getFixed() { String str = nextToken(); int i = 0; while (i < str.size() && str[i] != '.') ++i; int integral = std::strtol(str.substr(0, i).z(), nullptr, 10); int fractional = 0; if (i < str.size()) { String s = (str.substr(i+1) + "000").substr(0, 3); fractional = std::strtol(s.z(), nullptr, 10); } return Fixed::fromInternal(integral * 1000 + fractional); } //! Extract double token (skipping whitespace). double Lex::getDouble() { return Platform::toDouble(nextToken()); } //! Skip over whitespace. void Lex::skipWhitespace() { while (!eos() && uint8_t(iString[iPos]) <= ' ') ++iPos; } // -------------------------------------------------------------------- /*! \class ipe::Buffer \ingroup base \brief A memory buffer. Can be be copied in constant time, the actual data is shared. */ //! Create buffer of specified size. Buffer::Buffer(int size) { iData = std::shared_ptr>(new std::vector(size)); } //! Create buffer by copying the data. Buffer::Buffer(const char *data, int size) { iData = std::shared_ptr>(new std::vector(size)); std::memcpy(&(*iData)[0], data, size); } // -------------------------------------------------------------------- /*! \class ipe::Stream \ingroup base \brief Abstract base class for output streams. */ Stream::~Stream() { // empty implementation of pure virtual destructor } //! Close the stream. No more writing allowed! void Stream::close() { // nothing } //! Default implementation uses PutChar. void Stream::putString(String s) { for (int i = 0; i < s.size(); ++i) putChar(s[i]); } //! Default implementation uses PutChar. void Stream::putCString(const char *s) { while (*s) putChar(*s++); } //! Default implementation uses PutChar. void Stream::putRaw(const char *data, int size) { for (int i = 0; i < size; i++) putChar(data[i]); } //! Output integer. Stream &Stream::operator<<(int i) { char buf[30]; std::sprintf(buf, "%d", i); *this << buf; return *this; } //! Output double. Stream &Stream::operator<<(double d) { char buf[30]; if (d < 0.0) { putChar('-'); d = -d; } if (d >= 1e9) { // PDF will not be able to read this, but we have to write something. // Such large numbers should only happen if something is wrong. std::sprintf(buf, "%g", d); putCString(buf); } else if (d < 1e-8) { putChar('0'); } else { // Print six significant digits, but omit trailing zeros. // Probably I'll want to have adjustable precision later. int factor; if (d > 1000.0) factor = 100L; else if (d > 100.0) factor = 1000L; else if (d > 10.0) factor = 10000L; else if (d > 1.0) factor = 100000L; else if (d > 0.1) factor = 1000000L; else if (d > 0.01) factor = 10000000L; else factor = 100000000L; double dd = trunc(d); int intpart = int(dd + 0.5); // 10^9 < 2^31 int v = int(factor * (d - dd) + 0.5); if (v >= factor) { ++intpart; v -= factor; } std::sprintf(buf, "%d", intpart); putCString(buf); int mask = factor / 10; if (v != 0) { putChar('.'); while (v != 0) { putChar('0' + v / mask); v = (10 * v) % factor; } } } return *this; } //! Output byte in hexadecimal. void Stream::putHexByte(char b) { char buf[3]; std::sprintf(buf, "%02x", (b & 0xff)); *this << buf; } //! Save a string with XML escaping of &, >, <, ", '. void Stream::putXmlString(String s) { for (int i = 0; i < s.size(); ++i) { char ch = s[i]; switch (ch) { case '&': *this << "&"; break; case '<': *this << "<"; break; case '>': *this << ">"; break; case '"': *this << """; break; case '\'': *this << "'"; break; default: *this << ch; break; } } } // -------------------------------------------------------------------- /*! \class ipe::StringStream \ingroup base \brief Stream writing into an String. */ //! Construct with string reference. StringStream::StringStream(String &string) : iString(string) { // nothing } void StringStream::putChar(char ch) { iString += ch; } void StringStream::putString(String s) { iString += s; } void StringStream::putCString(const char *s) { iString += s; } void StringStream::putRaw(const char *data, int size) { for (int i = 0; i < size; i++) iString += data[i]; } long StringStream::tell() const { return iString.size(); } // -------------------------------------------------------------------- /*! \class ipe::FileStream \ingroup base \brief Stream writing into an open file. */ //! Constructor. FileStream::FileStream(std::FILE *file) : iFile(file) { // nothing } void FileStream::putChar(char ch) { std::fputc(ch, iFile); } void FileStream::putString(String s) { for (int i = 0; i < s.size(); ++i) std::fputc(s[i], iFile); } void FileStream::putCString(const char *s) { fputs(s, iFile); } void FileStream::putRaw(const char *data, int size) { for (int i = 0; i < size; i++) std::fputc(data[i], iFile); } long FileStream::tell() const { return std::ftell(iFile); } // -------------------------------------------------------------------- /*! \class ipe::DataSource * \ingroup base * \brief Interface for getting data for parsing. */ //! Pure virtual destructor. DataSource::~DataSource() { // nothing } // -------------------------------------------------------------------- /*! \class ipe::FileSource \ingroup base \brief Data source for parsing from a file. */ FileSource::FileSource(FILE *file) : iFile(file) { // nothing } int FileSource::getChar() { return std::fgetc(iFile); } /*! \class ipe::BufferSource \ingroup base \brief Data source for parsing from a buffer. */ BufferSource::BufferSource(const Buffer &buffer) : iBuffer(buffer) { iPos = 0; } void BufferSource::setPosition(int pos) { iPos = pos; } int BufferSource::getChar() { if (iPos >= iBuffer.size()) return EOF; return uint8_t(iBuffer[iPos++]); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipexml.cpp0000644000175000017500000001701113561570220016271 0ustar otfriedotfried// -------------------------------------------------------------------- // XML parsing // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipexml.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::XmlAttributes \ingroup base \brief Stores attributes of an XML tag. */ //! Constructor for an empty collection. XmlAttributes::XmlAttributes() { iSlash = false; } //! Remove all attributes. void XmlAttributes::clear() { iSlash = false; iMap.clear(); } //! Return attribute with given key. /*! Returns an empty string if no attribute with this key exists. */ String XmlAttributes::operator[](String str) const { std::map::const_iterator it = iMap.find(str); if (it == iMap.end()) return String(); else return it->second; } //! Add a new attribute. void XmlAttributes::add(String key, String val) { iMap[key] = val; } //! Check whether attribute exists, set \c val if so. bool XmlAttributes::has(String str, String &val) const { std::map::const_iterator it = iMap.find(str); if (it != iMap.end()) { val = it->second; return true; } return false; } //! Check whether attribute exists. bool XmlAttributes::has(String str) const { return (iMap.find(str) != iMap.end()); } // -------------------------------------------------------------------- /*! \class ipe::XmlParser * \ingroup base * \brief Base class for XML stream parsing. This is the base class for Ipe's XML parser. It only provides some utility functions for parsing tags and PCDATA. Derived classes implement the actual parsing using recursive descent parsers---after experimenting with various schemes for XML parsing, this seems to work best for Ipe. Tag names and attribute names must consist of ASCII letters only. Only entities for '&', '<', and '>' are recognized. */ //! Construct with a data source. XmlParser::XmlParser(DataSource &source) : iSource(source) { iPos = 0; getChar(); // init iCh } //! Virtual destructor, so one can destroy through pointer. XmlParser::~XmlParser() { // nothing } void XmlParser::skipWhitespace() { while (iCh <= ' ' && !eos()) getChar(); } //! Parse whitespace and the name of a tag. /*! If the tag is a closing tag, skips > and returns with stream after that. Otherwise, returns with stream just after the tag name. Comments and are skipped silently. */ String XmlParser::parseToTagX() { bool comment_found; do { skipWhitespace(); if (iCh != '<') return String(); getChar(); // // comment_found = (iCh == '!'); if (comment_found) { getChar(); if (iCh == '-') { int last[2] = { ' ', ' ' }; while (!eos() && (iCh != '>' || last[0] != '-' || last[1] != '-')) { last[0] = last[1]; last[1] = iCh; getChar(); } } else { // skip to end of tag while (!eos() && iCh != '>') getChar(); } getChar(); if (eos()) return String(); } } while (comment_found); String tagname; if (iCh == '?' || iCh == '/') { tagname += char(iCh); getChar(); } while (isTagChar(iCh)) { tagname += char(iCh); getChar(); } if (tagname[0] == '/') { skipWhitespace(); if (iCh != '>') return String(); getChar(); } // ipeDebug("<%s>", tagname.z()); return tagname; } //! Parse whitespace and the name of a tag. /*! Like ParseToTagX, but silently skips over all tags whose name starts with "x-" */ String XmlParser::parseToTag() { for (;;) { String s = parseToTagX(); if (s.size() < 3 || (s[0] != '/' && (s[0] != 'x' || s[1] != '-')) || (s[0] == '/' && (s[1] != 'x' || s[2] != '-'))) return s; if (s[0] != '/') { XmlAttributes attr; if (!parseAttributes(attr)) return String(); } } } static String fromXml(String source) { String s; for (int i = 0; i < source.size(); ) { if (source[i] == '&') { int j = i; while (j < source.size() && source[j] != ';') ++j; String ent(source, i + 1, j - i - 1); char ent1 = 0; if (ent == "amp") ent1 = '&'; else if (ent == "lt") ent1 = '<'; else if (ent == "gt") ent1 = '>'; else if (ent == "quot") ent1 = '"'; else if (ent == "apos") ent1 = '\''; if (ent1) { s += ent1; i = j+1; continue; } // entity not found: copy normally } s += source[i++]; } return s; } //! Parse XML attributes. /*! Returns with stream just after \>. Caller can check whether the tag ended with a / by checking attr.slash(). Set \a qm to true to allow a question mark just before the \>. */ bool XmlParser::parseAttributes(XmlAttributes &attr, bool qm) { // looking at char after tagname attr.clear(); skipWhitespace(); while (iCh != '>' && iCh != '/' && iCh != '?') { String attname; while (isTagChar(iCh)) { attname += char(iCh); getChar(); } // XML allows whitespace before and after the '=' skipWhitespace(); if (attname.empty() || iCh != '=') return false; getChar(); skipWhitespace(); // XML allows double or single quotes int quote = iCh; if (iCh != '\"' && iCh != '\'') return false; getChar(); String val; while (!eos() && iCh != quote) { val += char(iCh); getChar(); } if (iCh != quote) return false; getChar(); skipWhitespace(); attr.add(attname, fromXml(val)); } // looking at '/' or '>' (or '?' in tag) if (iCh == '/' || (qm && iCh == '?')) { attr.setSlash(); getChar(); skipWhitespace(); } // looking at '>' if (iCh != '>') return false; getChar(); return true; } //! Parse PCDATA. /*! Checks whether the data is terminated by \c \, and returns with stream past the \>. */ bool XmlParser::parsePCDATA(String tag, String &pcdata) { String s; bool haveEntity = false; for (;;) { if (eos()) return false; if (iCh == '<') { getChar(); if (iCh != '/') return false; getChar(); for (int i = 0; i < tag.size(); i++) { if (iCh != tag[i]) return false; getChar(); } skipWhitespace(); if (iCh != '>') return false; getChar(); if (haveEntity) pcdata = fromXml(s); else pcdata = s; return true; } else { if (iCh == '&') haveEntity = true; s += char(iCh); } getChar(); } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/Makefile0000644000175000017500000000335213561570220015732 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for Ipelib # -------------------------------------------------------------------- OBJDIR = $(BUILDDIR)/obj/ipelib include ../common.mak TARGET = $(call dll_target,ipe) MAKE_SYMLINKS = $(call dll_symlinks,ipe) SONAME = $(call soname,ipe) INSTALL_SYMLINKS = $(call install_symlinks,ipe) CPPFLAGS += -I../include ifdef IPEBUNDLE CPPFLAGS += -DIPEBUNDLE endif ifdef IPE_NO_IPELIB_VERSION_CHECK CPPFLAGS += -DIPE_NO_IPELIB_VERSION_CHECK endif CPPFLAGS += $(ZLIB_CFLAGS) $(JPEG_CFLAGS) $(PNG_CFLAGS) CXXFLAGS += $(DLL_CFLAGS) LIBS += $(JPEG_LIBS) $(ZLIB_LIBS) $(PNG_LIBS) all: $(TARGET) sources = \ ipebase.cpp \ ipeplatform.cpp \ ipegeo.cpp \ ipexml.cpp \ ipeattributes.cpp \ ipebitmap.cpp \ ipeshape.cpp \ ipegroup.cpp \ ipeimage.cpp \ ipetext.cpp \ ipepath.cpp \ ipereference.cpp \ ipeobject.cpp \ ipefactory.cpp \ ipestdstyles.cpp \ ipeiml.cpp \ ipepage.cpp \ ipepainter.cpp \ ipetoolbase.cpp \ ipepdfparser.cpp \ ipepdfwriter.cpp \ iperesources.cpp \ ipestyle.cpp \ ipesnap.cpp \ ipeutils.cpp \ ipelatex.cpp \ ipedoc.cpp ifdef WIN32 sources += ipebitmap_win.cpp else sources += ipebitmap_unix.cpp endif $(TARGET): $(objects) $(MAKE_LIBDIR) $(CXX) $(LDFLAGS) $(DLL_LDFLAGS) $(SONAME) -o $@ $^ $(LIBS) $(MAKE_SYMLINKS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPEHEADERDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_FILES) ../include/*.h $(INSTALL_ROOT)$(IPEHEADERDIR) $(INSTALL_SYMLINKS) # -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipeshape.cpp0000644000175000017500000006160413561570220016600 0ustar otfriedotfried// -------------------------------------------------------------------- // Shapes // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeshape.h" #include "ipepainter.h" using namespace ipe; // -------------------------------------------------------------------- inline bool snapVertex(const Vector &mouse, const Vector &v, Vector &pos, double &bound) { return v.snap(mouse, pos, bound); } inline void snapBezier(const Vector &mouse, const Bezier &bez, Vector &pos, double &bound) { double t; (void) bez.snap(mouse, t, pos, bound); } // -------------------------------------------------------------------- /*! \class ipe::CurveSegment \ingroup geo \brief A segment on an SubPath. A segment is either an elliptic arc, a straight segment, or a B-spline curve, depending on its type(). This is a lightweight object, created on the fly by Curve::segment(). There is no public constructor, so the only way to create such an object is through that method. The type() is one of the following: - \c ESegment: the segment has two control points, and represents a line segment. - \c ESpline: a B-spline curve with n control points. The first and last control point's knot value is repeated three times, so the curve begins and ends in these points. A spline with 4 control points is a single Bezier curve with those control points. A spline with 3 control points is defined to be a quadratic Bezier curve with those control points. - \c EOldSpline: an incorrectly defined B-spline, used by Ipe for many years. Supported for compatibility. - \c EArc: an elliptic arc, with begin and end point. The supporting ellipse is defined by the matrix(), it is the image under the affine transformation matrix() of the unit circle. matrix() is such that its inverse transforms both start and end position to points (nearly) on the unit circle. The arc is the image of the positively (counter-clockwise) directed arc from the pre-image of the start position to the pre-image of the end position. Whether this is a positively or negatively oriented arc in user space depends on the matrix. */ //! Create a segment. /*! Matrix \a m defaults to null, for all segments but arcs. */ CurveSegment::CurveSegment(Type type, int num, const Vector *cp, const Matrix *m) : iType(type), iCP(cp), iNumCP(num), iM(m) { // nothing } //! Return segment as Arc. /*! Panics if segment is not an arc. */ Arc CurveSegment::arc() const { assert(type() == EArc); return Arc(*iM, cp(0), cp(1)); } //! Convert B-spline to a sequence of Bezier splines. void CurveSegment::beziers(std::vector &bez) const { if (iType == EOldSpline) Bezier::oldSpline(countCP(), iCP, bez); else Bezier::spline(countCP(), iCP, bez); } //! Draw the segment. /*! Current position of the \a painter is already on first control point. */ void CurveSegment::draw(Painter &painter) const { switch (type()) { case ESegment: painter.lineTo(cp(1)); break; case EOldSpline: case ESpline: { std::vector bez; beziers(bez); for (const auto & b : bez) painter.curveTo(b); break; } case EArc: painter.drawArc(arc()); break; } } //! Add segment to bounding box. /*! Does not assume that first control point has already been added. If \a cpf is true, then control points of splines, Bezier curves, and the center of arcs are included in the bbox (so that snapping can find them). Otherwise, a tight bounding box for the geometric object itself is computed. */ void CurveSegment::addToBBox(Rect &box, const Matrix &m, bool cpf) const { switch (type()) { case ESegment: box.addPoint(m * cp(0)); box.addPoint(m * cp(1)); break; case EArc: box.addRect((m * arc()).bbox()); if (cpf) box.addPoint((m * matrix()).translation()); break; case ESpline: case EOldSpline: if (cpf) { for (int i = 0; i < countCP(); ++i) box.addPoint(m * cp(i)); } else { std::vector bez; beziers(bez); for (const auto & b : bez) box.addRect((m * b).bbox()); } break; } } //! Return distance to the segment. double CurveSegment::distance(const Vector &v, const Matrix &m, double bound) const { switch (type()) { case ESegment: return Segment(m * cp(0), m * cp(1)).distance(v, bound); case EArc: return (m * arc()).distance(v, bound); case EOldSpline: case ESpline: { std::vector bez; beziers(bez); double d = bound; double d1; for (const auto & b : bez) { if ((d1 = (m * b).distance(v, d)) < d) d = d1; } return d; } default: // make compiler happy return bound; } } //! Snap to vertex of the segment. /*! The method assumes that the first control point has already been tested. */ void CurveSegment::snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool ctl) const { switch (type()) { case ESegment: if (ctl) // segment midpoint snapVertex(mouse, m * (0.5 * (cp(0) + cp(1))), pos, bound); else snapVertex(mouse, m * cp(1), pos, bound); break; case EArc: // snap to center and endpoints if (ctl) // center snapVertex(mouse, (m * matrix()).translation(), pos, bound); else snapVertex(mouse, m * cp(1), pos, bound); break; case ESpline: case EOldSpline: // real end point is cp(countCP() - 1) // snap to all control points if (ctl) { for (int i = 1; i < countCP() - 1; ++i) snapVertex(mouse, m * cp(i), pos, bound); } else snapVertex(mouse, m * cp(countCP() - 1), pos, bound); break; } } void CurveSegment::snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { switch (type()) { case ESegment: Segment(m * cp(0), m * cp(1)).snap(mouse, pos, bound); break; case EArc: { Arc a = m * arc(); Vector pos1; Angle angle; double d1 = a.distance(mouse, bound, pos1, angle); if (d1 < bound) { bound = d1; pos = pos1; } break; } case EOldSpline: case ESpline: { std::vector bez; beziers(bez); for (const auto & b : bez) snapBezier(mouse, m * b, pos, bound); break; } } } // -------------------------------------------------------------------- /*! \class ipe::Curve \ingroup geo \brief Subpath consisting of a sequence of CurveSegment's. */ //! Create an empty, open subpath Curve::Curve() { iClosed = false; } //! Append a straight segment to the subpath. void Curve::appendSegment(const Vector &v0, const Vector &v1) { if (iSeg.empty()) iCP.push_back(v0); assert(v0 == iCP.back()); iCP.push_back(v1); Seg seg; seg.iType = CurveSegment::ESegment; seg.iLastCP = iCP.size() - 1; seg.iMatrix = iM.size() - 1; iSeg.push_back(seg); } //! Append elliptic arc to the subpath. void Curve::appendArc(const Matrix &m, const Vector &v0, const Vector &v1) { if (iSeg.empty()) iCP.push_back(v0); assert(v0 == iCP.back()); iCP.push_back(v1); iM.push_back(m); Seg seg; seg.iType = CurveSegment::EArc; seg.iLastCP = iCP.size() - 1; seg.iMatrix = iM.size() - 1; iSeg.push_back(seg); } //! Append B-spline curve. void Curve::appendSpline(const std::vector &v, CurveSegment::Type type) { assert(type == CurveSegment::ESpline || type == CurveSegment::EOldSpline); if (iSeg.empty()) iCP.push_back(v[0]); assert(v[0] == iCP.back()); for (int i = 1; i < size(v); ++i) iCP.push_back(v[i]); Seg seg; seg.iType = type; seg.iLastCP = iCP.size() - 1; seg.iMatrix = iM.size() - 1; iSeg.push_back(seg); } //! Set whether subpath is closed or not. void Curve::setClosed(bool closed) { iClosed = closed; } SubPath::Type Curve::type() const { return ECurve; } const Curve *Curve::asCurve() const { return this; } //! Return segment. /*! If \a i is negative, elements from the end are returned. The closing segment of a closed path is not accessible this way (use closingSegment() instead)! */ CurveSegment Curve::segment(int i) const { if (i < 0) i += iSeg.size(); const Seg &seg = iSeg[i]; const Matrix *m = &iM[seg.iMatrix]; int cpbg = (i > 0) ? iSeg[i-1].iLastCP : 0; const Vector *cp = &iCP[cpbg]; return CurveSegment(seg.iType, seg.iLastCP - cpbg + 1, cp, m); } void Curve::save(Stream &stream) const { // moveto first control point stream << iCP[0] << " m\n"; int vtx = 1; // next control point int mat = 0; for (std::vector::const_iterator it = iSeg.begin(); it != iSeg.end(); ++it) { switch (it->iType) { case CurveSegment::ESegment: assert(vtx == it->iLastCP); stream << iCP[vtx++] << " l\n"; break; case CurveSegment::EArc: assert(vtx == it->iLastCP && mat == it->iMatrix); stream << iM[mat++] << " " << iCP[vtx++] << " a\n"; break; case CurveSegment::EOldSpline: while (vtx < it->iLastCP) stream << iCP[vtx++] << "\n"; stream << iCP[vtx++] << " s\n"; break; case CurveSegment::ESpline: while (vtx < it->iLastCP) stream << iCP[vtx++] << "\n"; stream << iCP[vtx++] << " c\n"; break; } } if (closed()) stream << "h\n"; } void Curve::draw(Painter &painter) const { painter.moveTo(iCP[0]); for (int i = 0; i < countSegments(); ++i) segment(i).draw(painter); if (closed()) painter.closePath(); } void Curve::addToBBox(Rect &box, const Matrix &m, bool cp) const { for (int i = 0; i < countSegments(); ++i) segment(i).addToBBox(box, m, cp); } double Curve::distance(const Vector &v, const Matrix &m, double bound) const { double d = bound; for (int i = 0; i < countSegments(); ++i) { double d1 = segment(i).distance(v, m, d); if (d1 < d) d = d1; } if (closed()) { Vector u[2]; double d1 = closingSegment(u).distance(v, m , d); if (d1 < d) d = d1; } return d; } void Curve::snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool ctl) const { if (!ctl) snapVertex(mouse, m * segment(0).cp(0), pos, bound); else if (iClosed) // midpoint of closing segment snapVertex(mouse, m * (0.5 * (iCP.back() + iCP.front())), pos, bound); for (int i = 0; i < countSegments(); ++i) segment(i).snapVtx(mouse, m, pos, bound, ctl); } void Curve::snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { snapVertex(mouse, m * segment(0).cp(0), pos, bound); for (int i = 0; i < countSegments(); ++i) segment(i).snapBnd(mouse, m, pos, bound); if (closed()) { Vector u[2]; closingSegment(u).snapBnd(mouse, m, pos, bound); } } //! Returns the closing segment of a closed path. /*! Since the closing segment isn't actually stored inside this object, you have to provide a length-2 vector for the control points. This method panics if the Curve is not closed. */ CurveSegment Curve::closingSegment(Vector u[2]) const { assert(iClosed); u[0] = iCP.back(); u[1] = iCP.front(); return CurveSegment(CurveSegment::ESegment, 2, u, nullptr); } // -------------------------------------------------------------------- /*! \class ipe::SubPath \ingroup geo \brief A subpath of a Path. A subpath is either open, or closed. There are two special kinds of closed subpaths, namely ellipses and closed B-splines. */ //! Implementation of pure virtual destructor. SubPath::~SubPath() { // nothing } //! Is this subpath closed? /*! Default implementation returns \c true. */ bool SubPath::closed() const { return true; } //! Return this object as an Ellipse, or nullptr if it's not an ellipse. const Ellipse *SubPath::asEllipse() const { return nullptr; } //! Return this object as an ClosedSpline, or nullptr if it's not a closed spline. const ClosedSpline *SubPath::asClosedSpline() const { return nullptr; } //! Return this object as an Curve, or else nullptr. const Curve *SubPath::asCurve() const { return nullptr; } // -------------------------------------------------------------------- /*! \class ipe::Ellipse \ingroup geo \brief An ellipse subpath */ Ellipse::Ellipse(const Matrix &m) : iM(m) { // nothing } SubPath::Type Ellipse::type() const { return EEllipse; } const Ellipse *Ellipse::asEllipse() const { return this; } void Ellipse::save(Stream &stream) const { stream << matrix() << " e\n"; } void Ellipse::draw(Painter &painter) const { painter.drawArc(Arc(iM)); } void Ellipse::addToBBox(Rect &box, const Matrix &m, bool cp) const { box.addRect(Arc(m * iM).bbox()); } double Ellipse::distance(const Vector &v, const Matrix &m, double bound) const { Arc arc(m * iM); return arc.distance(v, bound); } //! snaps to center of ellipse. void Ellipse::snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool ctl) const { if (ctl) snapVertex(mouse, (m * iM).translation(), pos, bound); } void Ellipse::snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { Arc arc(m * iM); Vector pos1; Angle angle; double d1 = arc.distance(mouse, bound, pos1, angle); if (d1 < bound) { bound = d1; pos = pos1; } } // -------------------------------------------------------------------- /*! \class ipe::ClosedSpline \ingroup geo \brief A closed B-spline curve. */ ClosedSpline::ClosedSpline(const std::vector &v) { assert(v.size() >= 3); std::copy(v.begin(), v.end(), std::back_inserter(iCP)); } SubPath::Type ClosedSpline::type() const { return EClosedSpline; } const ClosedSpline *ClosedSpline::asClosedSpline() const { return this; } void ClosedSpline::save(Stream &stream) const { for (int i = 0; i < size(iCP) - 1; ++i) stream << iCP[i] << "\n"; stream << iCP.back() << " u\n"; } void ClosedSpline::draw(Painter &painter) const { std::vector bez; beziers(bez); painter.moveTo(bez.front().iV[0]); for (const auto & b : bez) painter.curveTo(b); painter.closePath(); } void ClosedSpline::addToBBox(Rect &box, const Matrix &m, bool cpf) const { if (cpf) { for (const auto & cp : iCP) box.addPoint(m * cp); } else { std::vector bez; beziers(bez); for (const auto & b : bez) box.addRect((m * b).bbox()); } } double ClosedSpline::distance(const Vector &v, const Matrix &m, double bound) const { std::vector bez; beziers(bez); double d = bound; double d1; for (const auto & b : bez) { if ((d1 = (m * b).distance(v, d)) < d) d = d1; } return d; } void ClosedSpline::beziers(std::vector &bez) const { Bezier::closedSpline(iCP.size(), &iCP.front(), bez); } void ClosedSpline::snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool ctl) const { if (ctl) { // snap to control points for (const auto & cp : iCP) snapVertex(mouse, m * cp, pos, bound); } } void ClosedSpline::snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { std::vector bez; beziers(bez); for (const auto & b : bez) snapBezier(mouse, m * b, pos, bound); } // -------------------------------------------------------------------- /*! \class ipe::Shape \ingroup geo \brief A geometric shape, consisting of several (open or closed) subpaths. This class represents vector graphics geometry following the PDF "path", but is actually a bit more complicated since we add new subtypes: arcs, parabolas, uniform B-splines (in PDF, all of these are converted to cubic Bezier splines). A Shape consists of a set of subpaths (SubPath), each of which is either open or closed, and which are rendered by stroking and filling as a whole. The distinction between open and closed is meaningful for stroking only, for filling any open subpath is implicitely closed. Stroking a set of subpaths is identical to stroking them individually. This is not true for filling: using several subpaths, one can construct objects with holes, and more complicated pattern. A subpath is either an Ellipse (a complete, closed ellipse), a ClosedSpline (a closed uniform B-spline curve), or a Curve. A curve consists of a sequence of segments. Segments are either straight, a quadratic Bezier spline, a cubic Bezier spline, an elliptic arc, or a uniform cubic B-spline. Shape is implemented using reference counting and can be copied and passed by value efficiently. The only mutator methods are appendSubPath() and load(), which can only be called during construction of the Shape (that is, before its implementation has been shared). */ //! Construct an empty shape (zero subpaths). Shape::Shape() { iImp = new Imp; iImp->iRefCount = 1; } //! Copy constructor (constant time). Shape::Shape(const Shape &rhs) { iImp = rhs.iImp; iImp->iRefCount++; } //! Destructor (takes care of reference counting). Shape::~Shape() { if (iImp->iRefCount == 1) delete iImp; else iImp->iRefCount--; } //! Assignment operator (constant-time). Shape &Shape::operator=(const Shape &rhs) { if (this != &rhs) { if (iImp->iRefCount == 1) delete iImp; else iImp->iRefCount--; iImp = rhs.iImp; iImp->iRefCount++; } return *this; } // -------------------------------------------------------------------- //! Convenience function: create a rectangle shape. Shape::Shape(const Rect &rect) { iImp = new Imp; iImp->iRefCount = 1; Curve *sp = new Curve; sp->appendSegment(rect.bottomLeft(), rect.bottomRight()); sp->appendSegment(rect.bottomRight(), rect.topRight()); sp->appendSegment(rect.topRight(), rect.topLeft()); sp->setClosed(true); appendSubPath(sp); } //! Convenience function: create a single line segment. Shape::Shape(const Segment &seg) { iImp = new Imp; iImp->iRefCount = 1; Curve *sp = new Curve; sp->appendSegment(seg.iP, seg.iQ); appendSubPath(sp); } //! Convenience function: create circle with \a center and \a radius. Shape::Shape(const Vector ¢er, double radius) { iImp = new Imp; iImp->iRefCount = 1; appendSubPath(new Ellipse(Matrix(radius, 0.0, 0.0, radius, center.x, center.y))); } //! Convenience function: create circular arc. /*! If \a alpha1 is larger than \a alpha0, the arc is oriented positively, otherwise negatively. */ Shape::Shape(const Vector ¢er, double radius, double alpha0, double alpha1) { iImp = new Imp; iImp->iRefCount = 1; Matrix m = Matrix(radius, 0, 0, radius, center.x, center.y); Vector v0 = m * Vector(Angle(alpha0)); Vector v1 = m * Vector(Angle(alpha1)); if (alpha1 < alpha0) // negative orientation m = m * Linear(1, 0, 0, -1); Curve *sp = new Curve; sp->appendArc(m, v0, v1); appendSubPath(sp); } // -------------------------------------------------------------------- //! Is this Shape a single straight segment? bool Shape::isSegment() const { if (countSubPaths() != 1) return false; const SubPath *p = subPath(0); if (p->type() != SubPath::ECurve || p->closed()) return false; const Curve *c = p->asCurve(); if (c->countSegments() != 1 || c->segment(0).type() != CurveSegment::ESegment) return false; return true; } //! Add shape (transformed by \a m) to \a box. void Shape::addToBBox(Rect &box, const Matrix &m, bool cp) const { for (int i = 0; i < countSubPaths(); ++i) subPath(i)->addToBBox(box, m, cp); } double Shape::distance(const Vector &v, const Matrix &m, double bound) const { double d = bound; for (int i = 0; i < countSubPaths(); ++i) { double d1 = subPath(i)->distance(v, m, d); if (d1 < d) d = d1; } return d; } void Shape::snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool ctl) const { for (int i = 0; i < countSubPaths(); ++i) subPath(i)->snapVtx(mouse, m, pos, bound, ctl); } void Shape::snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { for (int i = 0; i < countSubPaths(); ++i) subPath(i)->snapBnd(mouse, m, pos, bound); } //! Append a SubPath to shape. /*! The Shape will take ownership of the subpath. This method can only be used during construction of the Shape. It will panic if the implementation has been shared. */ void Shape::appendSubPath(SubPath *sp) { assert(iImp->iRefCount == 1); iImp->iSubPaths.push_back(sp); } //! Draw the Shape as a path to \a painter. /*! Does not call newPath() on \a painter. */ void Shape::draw(Painter &painter) const { for (int i = 0; i < countSubPaths(); ++i) subPath(i)->draw(painter); } Shape::Imp::~Imp() { // delete the subpaths for (SubPathSeq::iterator it = iSubPaths.begin(); it != iSubPaths.end(); ++it) { delete *it; *it = nullptr; } } static Vector getVector(std::vector &args) { Vector v; v.x = args[0]; v.y = args[1]; args.erase(args.begin(), args.begin() + 2); return v; } static Matrix getMatrix(std::vector &args) { Matrix m; for (int i = 0; i < 6; ++i) m.a[i] = args[i]; args.erase(args.begin(), args.begin() + 6); return m; } //! Save Shape onto XML stream. void Shape::save(Stream &stream) const { for (int i = 0; i < countSubPaths(); ++i) subPath(i)->save(stream); } //! Create a Shape from XML data. /*! Appends subpaths from XML data to the current Shape. Returns false if the path syntax is incorrect (the Shape will be in an inconsistent state and must be discarded). This method can only be used during construction of the Shape. It will panic if the implementation has been shared. */ bool Shape::load(String data) { assert(iImp->iRefCount == 1); Lex stream(data); String word; String type; Curve *sp = nullptr; Vector org; std::vector args; do { if (stream.token() == "h") { // closing path if (!sp) return false; stream.nextToken(); // eat token sp->setClosed(true); sp = nullptr; } else if (stream.token() == "m") { if (args.size() != 2) return false; stream.nextToken(); // eat token // begin new subpath sp = new Curve; appendSubPath(sp); org = getVector(args); } else if (stream.token() == "l") { // assert(sp && args.size() > 0 && (args.size() % 2 == 0)); if (!sp || args.size() != 2) return false; stream.nextToken(); // eat token while (!args.empty()) { Vector v = getVector(args); sp->appendSegment(org, v); org = v; } } else if (stream.token() == "a") { if (!sp || args.size() != 8) return false; stream.nextToken(); Matrix m = getMatrix(args); if (m.determinant() == 0) return false; // don't accept zero-radius arc Vector v1 = getVector(args); sp->appendArc(m, org, v1); org = v1; } else if (stream.token() == "s" || stream.token() == "q" || stream.token() == "c") { if (!sp || args.size() < 2 || (args.size() % 2 != 0)) return false; bool oldStyle = (stream.token() == "s"); stream.nextToken(); std::vector v; v.push_back(org); while (!args.empty()) v.push_back(getVector(args)); if (oldStyle) sp->appendOldSpline(v); else sp->appendSpline(v); org = v.back(); } else if (stream.token() == "e") { if (args.size() != 6) return false; stream.nextToken(); sp = nullptr; Ellipse *e = new Ellipse(getMatrix(args)); appendSubPath(e); } else if (stream.token() == "u") { if (args.size() < 6 || (args.size() % 2 != 0)) return false; stream.nextToken(); sp = nullptr; std::vector v; while (!args.empty()) v.push_back(getVector(args)); ClosedSpline *e = new ClosedSpline(v); appendSubPath(e); } else { // must be a number double num; stream >> num; args.push_back(num); } stream.skipWhitespace(); } while (!stream.eos()); // sanity checks if (countSubPaths() == 0) return false; for (int i = 0; i < countSubPaths(); ++i) { if (subPath(i)->asCurve() && subPath(i)->asCurve()->countSegments() == 0) return false; } return true; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipetoolbase.cpp0000644000175000017500000000505213561570220017303 0ustar otfriedotfried// -------------------------------------------------------------------- // ipe::Tool // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipetoolbase.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::Tool \ingroup canvas \brief Abstract base class for various canvas tools. The Canvas doesn't know about the various modes for object creation, editing, and moving, but delegates the handling to a subclass of Tool. */ //! Constructor. Tool::Tool(CanvasBase *canvas) : iCanvas(canvas) { // nothing } //! Virtual destructor. Tool::~Tool() { // nothing } //! Called when a mouse button is pressed or released on the canvas. /*! \a button is 1, 2, or 3, with Shift/Ctrl/Alt/Meta modifiers added in (as defined in CanvasBase::TModifiers. \a press is true for button-down, and false for button-up. */ void Tool::mouseButton(int button, bool press) { // ignore it } //! Called when the mouse is moved on the canvas. void Tool::mouseMove() { // ignore it } //! Called when a key is pressed. /*! \a modifiers are as defined in CanvasBase::TModifiers. */ bool Tool::key(String text, int modifiers) { return false; // not handled } //! Snapping to vertices on object currently being drawn. void Tool::snapVtx(const Vector &mouse, Vector &pos, double &bound, bool cp) const { // nothing } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipepath.cpp0000644000175000017500000005107213561570220016432 0ustar otfriedotfried// -------------------------------------------------------------------- // The path object // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepath.h" #include "ipepainter.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::Path \ingroup obj \brief The path object (polylines, polygons, and generalizations). This object represents any vector graphics. The geometry is contained in a Shape. The filling algorithm is the even-odd rule of PDF: To determine whether a point lies inside the filled shape, draw a ray from that point in any direction, and count the number of path segments that cross the ray. If this number is odd, the point is inside; if even, the point is outside. (Path objects can also render using the winding fill rule by setting the fillRule attribute. This isn't really supported by the Ipe user interface, which doesn't show the orientation of paths.) If the path consists of a single line segment and is filled only, then it is not drawn at all. This can be used to draw arrow heads without bodies. The fill color is used to draw the arrows in this case. */ //! Construct from XML data. Path *Path::create(const XmlAttributes &attr, String data) { std::unique_ptr self(new Path(attr)); if (!self->iShape.load(data)) return nullptr; self->makeArrowData(); return self.release(); } //! Create empty path with attributes taken from XML Path::Path(const XmlAttributes &attr) : Object(attr) { bool stroked = false; bool filled = false; iStroke = Attribute::BLACK(); iFill = Attribute::WHITE(); String str; if (attr.has("stroke", str)) { iStroke = Attribute::makeColor(str, Attribute::BLACK()); stroked = true; } if (attr.has("fill", str)) { iFill = Attribute::makeColor(str, Attribute::WHITE()); filled = true; } if (!stroked && !filled) { stroked = true; iStroke= Attribute::BLACK(); } iDashStyle = Attribute::makeDashStyle(attr["dash"]); iPen = Attribute::makeScalar(attr["pen"], Attribute::NORMAL()); if (attr.has("opacity", str)) iOpacity = Attribute(true, str); else iOpacity = Attribute::OPAQUE(); if (attr.has("stroke-opacity", str)) iStrokeOpacity = Attribute(true, str); else iStrokeOpacity = iOpacity; iGradient = Attribute::NORMAL(); iTiling = Attribute::NORMAL(); if (attr.has("gradient", str)) iGradient = Attribute(true, str); else if (attr.has("tiling", str)) iTiling = Attribute(true, str); iPathMode = (stroked ? (filled ? EStrokedAndFilled : EStrokedOnly) : EFilledOnly); iLineCap = EDefaultCap; iLineJoin = EDefaultJoin; iFillRule = EDefaultRule; if (attr.has("cap", str)) iLineCap = TLineCap(Lex(str).getInt() + 1); if (attr.has("join", str)) iLineJoin = TLineJoin(Lex(str).getInt() + 1); if (attr.has("fillrule", str)) { if (str == "eofill") iFillRule = EEvenOddRule; else if (str == "wind") iFillRule = EWindRule; } iHasFArrow = false; iHasRArrow = false; iFArrowShape = iRArrowShape = Attribute::ARROW_NORMAL(); iFArrowSize = iRArrowSize = Attribute::NORMAL(); if (attr.has("arrow", str)) { iHasFArrow = true; int i = str.find("/"); if (i >= 0) { iFArrowShape = Attribute(true, String("arrow/") + str.left(i) + "(spx)"); iFArrowSize = Attribute::makeScalar(str.substr(i+1), Attribute::NORMAL()); } else iFArrowSize = Attribute::makeScalar(str, Attribute::NORMAL()); } if (attr.has("rarrow", str)) { iHasRArrow = true; int i = str.find("/"); if (i >= 0) { iRArrowShape = Attribute(true, String("arrow/") + str.left(i) + "(spx)"); iRArrowSize = Attribute::makeScalar(str.substr(i+1), Attribute::NORMAL()); } else iRArrowSize = Attribute::makeScalar(str, Attribute::NORMAL()); } } void Path::init(const AllAttributes &attr, bool withArrows) { iPathMode = attr.iPathMode; iStroke = attr.iStroke; iFill = attr.iFill; iDashStyle = attr.iDashStyle; iPen = attr.iPen; iOpacity = attr.iOpacity; iStrokeOpacity = attr.iStrokeOpacity; iTiling = attr.iTiling; if (iTiling.isNormal()) iGradient = attr.iGradient; else iGradient = Attribute::NORMAL(); iLineCap = attr.iLineCap; iLineJoin = attr.iLineJoin; iFillRule = attr.iFillRule; iHasFArrow = false; iHasRArrow = false; iFArrowShape = iRArrowShape = Attribute::ARROW_NORMAL(); iFArrowSize = iRArrowSize = Attribute::NORMAL(); if (withArrows) { iFArrowShape = attr.iFArrowShape; iRArrowShape = attr.iRArrowShape; iFArrowSize = attr.iFArrowSize; iRArrowSize = attr.iRArrowSize; iHasFArrow = attr.iFArrow; iHasRArrow = attr.iRArrow; } } //! Create for given shape. Path::Path(const AllAttributes &attr, const Shape &shape, bool withArrows) : Object(attr), iShape(shape) { init(attr, withArrows); makeArrowData(); } //! Return a clone (constant-time). Object *Path::clone() const { return new Path(*this); } //! Compute the arrow information. void Path::makeArrowData() { assert(iShape.countSubPaths() > 0); if (iShape.countSubPaths() > 1 || iShape.subPath(0)->closed()) { iFArrowOk = false; iRArrowOk = false; } else { CurveSegment seg = iShape.subPath(0)->asCurve()->segment(0); iRArrowOk = true; iRArrowPos = seg.cp(0); iRArrowArc = 0; if (seg.type() == CurveSegment::EArc) { iRArrowArc = 1; Angle alpha = (seg.matrix().inverse() * seg.cp(0)).angle(); Linear m = seg.matrix().linear(); iRArrowDir = (m * Vector(Angle(alpha - IpeHalfPi))).angle(); } else { if (seg.cp(1) == seg.cp(0)) iRArrowOk = false; else iRArrowDir = (iRArrowPos - seg.cp(1)).angle(); } seg = iShape.subPath(0)->asCurve()->segment(-1); iFArrowOk = true; iFArrowPos = seg.last(); iFArrowArc = 0; if (seg.type() == CurveSegment::EArc) { iFArrowArc = 1; Angle alpha = (seg.matrix().inverse() * seg.cp(1)).angle(); Linear m = seg.matrix().linear(); iFArrowDir = (m * Vector(Angle(alpha + IpeHalfPi))).angle(); } else { if (seg.cp(seg.countCP() - 2) == seg.last()) iFArrowOk = false; else iFArrowDir = (iFArrowPos - seg.cp(seg.countCP() - 2)).angle(); } } } //! Return pointer to this object. Path *Path::asPath() { return this; } Object::Type Path::type() const { return EPath; } //! Call visitPath of visitor. void Path::accept(Visitor &visitor) const { visitor.visitPath(this); } void Path::saveAsXml(Stream &stream, String layer) const { bool stroked = (iPathMode <= EStrokedAndFilled); bool filled = (iPathMode >= EStrokedAndFilled); stream << "\n"; iShape.save(stream); stream << "\n"; } /*! Draw an arrow of \a size with tip at \a pos directed in direction \a angle. */ void Path::drawArrow(Painter &painter, Vector pos, Angle angle, Attribute shape, Attribute size, double radius) { const Symbol *symbol = painter.cascade()->findSymbol(shape); if (symbol) { double s = painter.cascade()->find(EArrowSize, size).number().toDouble(); Color color = painter.stroke(); // Fixed opaq = painter.opacity(); painter.push(); painter.pushMatrix(); painter.translate(pos); painter.transform(Linear(angle)); painter.untransform(ETransformationsRigidMotions); bool cw = (radius < 0); if (cw) radius = -radius; bool pointy = (shape == Attribute::ARROW_PTARC() || shape == Attribute::ARROW_FPTARC()); if (shape.isArcArrow() && (radius > s)) { Angle delta = s / radius; Angle alpha = atan(1.0/3.0); Arc arc1; Arc arc2; Arc arc3; if (cw) { arc1 = Arc(Matrix(radius, 0, 0, radius, 0, -radius), IpeHalfPi, IpeHalfPi + delta); arc2 = Arc(Matrix(radius, 0, 0, -radius, 0, -radius), -IpeHalfPi - delta, -IpeHalfPi); arc3 = Arc(Matrix(radius, 0, 0, radius, 0, -radius), IpeHalfPi, IpeHalfPi + 0.8 * delta); } else { arc1 = Arc(Matrix(radius, 0, 0, radius, 0, radius), -IpeHalfPi - delta, -IpeHalfPi); arc2 = Arc(Matrix(radius, 0, 0, -radius, 0, radius), IpeHalfPi, IpeHalfPi + delta); arc3 = Arc(Matrix(radius, 0, 0, radius, 0, radius), -IpeHalfPi - 0.8 * delta, -IpeHalfPi); } arc1 = Linear(alpha) * arc1; arc2 = Linear(-alpha) * arc2; painter.setStroke(Attribute(color)); if (shape == Attribute::ARROW_FARC() || shape == Attribute::ARROW_FPTARC()) painter.setFill(Attribute(Color(1000, 1000, 1000))); else painter.setFill(Attribute(color)); // painter.setOpacity(Attribute(opaq)); painter.newPath(); painter.moveTo(arc1.beginp()); painter.drawArc(arc1); if (cw) { if (pointy) painter.lineTo(arc3.endp()); painter.lineTo(arc2.beginp()); painter.drawArc(arc2); } else { painter.drawArc(arc2); if (pointy) painter.lineTo(arc3.beginp()); } painter.closePath(); painter.drawPath(EStrokedAndFilled); } else { Matrix m(s, 0, 0, s, 0, 0); painter.transform(m); painter.setSymStroke(Attribute(color)); painter.setSymFill(Attribute(color)); painter.setSymPen(Attribute(painter.pen())); symbol->iObject->draw(painter); } painter.popMatrix(); painter.pop(); } } void Path::setShape(const Shape &shape) { iShape = shape; makeArrowData(); } void Path::draw(Painter &painter) const { painter.push(); if (iPathMode <= EStrokedAndFilled) { painter.setStroke(iStroke); painter.setDashStyle(iDashStyle); painter.setPen(iPen); painter.setLineCap(lineCap()); painter.setLineJoin(lineJoin()); } if (iPathMode >= EStrokedAndFilled) { painter.setFill(iFill); painter.setFillRule(fillRule()); painter.setTiling(iTiling); painter.setGradient(iGradient); } painter.setOpacity(iOpacity); painter.setStrokeOpacity(iStrokeOpacity); painter.pushMatrix(); painter.transform(matrix()); painter.untransform(transformations()); if (!iShape.isSegment() || iPathMode != EFilledOnly) { painter.newPath(); iShape.draw(painter); painter.drawPath(iPathMode); } if (iPathMode == EStrokedAndFilled && !iGradient.isNormal()) { // need to stroke separately painter.newPath(); iShape.draw(painter); painter.drawPath(EStrokedOnly); } if ((iHasFArrow && iFArrowOk) || (iHasRArrow && iRArrowOk)) { // Draw arrows if (iPathMode == EFilledOnly) { painter.setStroke(iFill); painter.setPen(iPen); painter.setLineCap(lineCap()); painter.setLineJoin(lineJoin()); } if (iHasFArrow && iFArrowOk) { double r = 0.0; if (iFArrowArc && iFArrowShape.isArcArrow()) { CurveSegment seg = iShape.subPath(0)->asCurve()->segment(-1); Vector center = painter.matrix() * seg.matrix().translation(); r = (center - painter.matrix() * iFArrowPos).len(); if ((painter.matrix().linear() * seg.matrix().linear()).determinant()<0) r = -r; } drawArrow(painter, iFArrowPos, iFArrowDir, iFArrowShape, iFArrowSize, r); } if (iHasRArrow && iRArrowOk) { double r = 0.0; if (iRArrowArc && iRArrowShape.isArcArrow()) { CurveSegment seg = iShape.subPath(0)->asCurve()->segment(0); Vector center = painter.matrix() * seg.matrix().translation(); r = (center - painter.matrix() * iRArrowPos).len(); if ((painter.matrix().linear() * seg.matrix().linear()).determinant()>0) r = -r; } drawArrow(painter, iRArrowPos, iRArrowDir, iRArrowShape, iRArrowSize, r); } } painter.popMatrix(); painter.pop(); } void Path::drawSimple(Painter &painter) const { painter.pushMatrix(); painter.transform(matrix()); painter.untransform(transformations()); painter.newPath(); iShape.draw(painter); painter.drawPath(EStrokedOnly); painter.popMatrix(); } void Path::addToBBox(Rect &box, const Matrix &m, bool cp) const { iShape.addToBBox(box, m * matrix(), cp); } double Path::distance(const Vector &v, const Matrix &m, double bound) const { return iShape.distance(v, m * matrix(), bound); } void Path::snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { iShape.snapVtx(mouse, m * matrix(), pos, bound, false); } void Path::snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { iShape.snapVtx(mouse, m * matrix(), pos, bound, true); } void Path::snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { iShape.snapBnd(mouse, m * matrix(), pos, bound); } //! Set whether object will be stroked and filled. void Path::setPathMode(TPathMode pm) { iPathMode = pm; } //! Set stroke color. void Path::setStroke(Attribute stroke) { iStroke = stroke; } //! Set fill color. void Path::setFill(Attribute fill) { iFill = fill; } //! Set tiling pattern of the object. /*! Resets gradient fill. */ void Path::setTiling(Attribute til) { iTiling = til; iGradient = Attribute::NORMAL(); } //! Set gradient fill of the object. /*! Resets tiling pattern. */ void Path::setGradient(Attribute grad) { iGradient = grad; iTiling = Attribute::NORMAL(); } //! Set opacity of the object. void Path::setOpacity(Attribute opaq) { iOpacity = opaq; } //! Set stroke opacity of the object. void Path::setStrokeOpacity(Attribute opaq) { iStrokeOpacity = opaq; } //! Set pen. void Path::setPen(Attribute pen) { iPen = pen; } //! Set dash style. void Path::setDashStyle(Attribute dash) { iDashStyle = dash; } //! Set forward arrow. void Path::setArrow(bool arrow, Attribute shape, Attribute size) { iHasFArrow = arrow; iFArrowShape = shape; iFArrowSize = size; } //! Set backward arrow (if the object can take it). void Path::setRarrow(bool arrow, Attribute shape, Attribute size) { iHasRArrow = arrow; iRArrowShape = shape; iRArrowSize = size; } //! Set line cap style. void Path::setLineCap(TLineCap s) { iLineCap = s; } //! Set line join style. void Path::setLineJoin(TLineJoin s) { iLineJoin = s; } //! Set fill rule. void Path::setFillRule(TFillRule s) { iFillRule = s; } void Path::checkStyle(const Cascade *sheet, AttributeSeq &seq) const { checkSymbol(EColor, iStroke, sheet, seq); checkSymbol(EColor, iFill, sheet, seq); checkSymbol(EDashStyle, iDashStyle, sheet, seq); checkSymbol(EPen, iPen, sheet, seq); checkSymbol(EArrowSize, iFArrowSize, sheet, seq); checkSymbol(EArrowSize, iRArrowSize, sheet, seq); checkSymbol(ESymbol, iFArrowShape, sheet, seq); checkSymbol(ESymbol, iRArrowShape, sheet, seq); checkSymbol(EOpacity, iOpacity, sheet, seq); checkSymbol(EOpacity, iStrokeOpacity, sheet, seq); if (!iTiling.isNormal()) checkSymbol(ETiling, iTiling, sheet, seq); if (!iGradient.isNormal()) checkSymbol(EGradient, iGradient, sheet, seq); } bool Path::setAttribute(Property prop, Attribute value) { switch (prop) { case EPropPathMode: if (value.pathMode() != pathMode()) { setPathMode(value.pathMode()); return true; } break; case EPropStrokeColor: if (value != stroke()) { setStroke(value); return true; } break; case EPropFillColor: if (value != fill()) { setFill(value); return true; } break; case EPropPen: if (value != pen()) { setPen(value); return true; } break; case EPropDashStyle: if (value != dashStyle()) { setDashStyle(value); return true; } break; case EPropTiling: if (value != tiling()) { setTiling(value); return true; } break; case EPropGradient: if (value != gradient()) { setGradient(value); return true; } break; case EPropOpacity: if (value != opacity()) { setOpacity(value); return true; } break; case EPropStrokeOpacity: if (value != strokeOpacity()) { setStrokeOpacity(value); return true; } break; case EPropFArrow: if (value.boolean() != iHasFArrow) { iHasFArrow = value.boolean(); return true; } break; case EPropRArrow: if (value.boolean() != iHasRArrow) { iHasRArrow = value.boolean(); return true; } break; case EPropFArrowSize: if (value != iFArrowSize) { iFArrowSize= value; return true; } break; case EPropRArrowSize: if (value != iRArrowSize) { iRArrowSize = value; return true; } break; case EPropFArrowShape: if (value != iFArrowShape) { iFArrowShape = value; return true; } break; case EPropRArrowShape: if (value != iRArrowShape) { iRArrowShape = value; return true; } break; case EPropLineJoin: assert(value.isEnum()); if (value.lineJoin() != iLineJoin) { iLineJoin = value.lineJoin(); return true; } break; case EPropLineCap: assert(value.isEnum()); if (value.lineCap() != iLineCap) { iLineCap = value.lineCap(); return true; } break; case EPropFillRule: assert(value.isEnum()); if (value.fillRule() != iFillRule) { iFillRule = value.fillRule(); return true; } break; default: return Object::setAttribute(prop, value); } return false; } Attribute Path::getAttribute(Property prop) const noexcept { switch (prop) { case EPropPathMode: return Attribute(iPathMode); case EPropStrokeColor: return stroke(); case EPropFillColor: return fill(); case EPropPen: return pen(); case EPropDashStyle: return dashStyle(); case EPropOpacity: return opacity(); case EPropStrokeOpacity: return strokeOpacity(); case EPropTiling: return tiling(); case EPropGradient: return gradient(); case EPropFArrow: return Attribute::Boolean(iHasFArrow); case EPropRArrow: return Attribute::Boolean(iHasRArrow); case EPropFArrowSize: return iFArrowSize; case EPropRArrowSize: return iRArrowSize; case EPropFArrowShape: return iFArrowShape; case EPropRArrowShape: return iRArrowShape; case EPropLineJoin: return Attribute(iLineJoin); case EPropLineCap: return Attribute(iLineCap); case EPropFillRule: return Attribute(iFillRule); default: return Object::getAttribute(prop); } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipeplatform.cpp0000644000175000017500000004334713561570220017330 0ustar otfriedotfried// -------------------------------------------------------------------- // Platform dependent methods // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebase.h" #include "ipeattributes.h" #ifdef WIN32 #include #include #include #include #else #include #include #endif #ifdef __APPLE__ #include #include // sys/param.h triggers legacy mode for realpath, so that the // last component of the path does not need to exist. #include #include #endif #include #include #include #include #include #include #include using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::Platform \ingroup base \brief Platform dependent methods. */ //! Return the Ipelib version. /*! This is available as a function so that one can verify what version of Ipelib one has actually linked with (as opposed to the header files used during compilation). */ int Platform::libVersion() { return IPELIB_VERSION; } // -------------------------------------------------------------------- static bool initialized = false; static bool showDebug = false; static Platform::DebugHandler debugHandler = nullptr; #ifdef IPEAPPIMAGE static String appImageBase; #endif #ifdef WIN32 static ULONG_PTR gdiplusToken = 0; _locale_t ipeLocale; typedef _locale_t (*LPCreateLocale)(int category, const char *locale); static LPCreateLocale p_create_locale = nullptr; typedef void (*LPFreeLocale)(_locale_t locale); static LPFreeLocale p_free_locale = nullptr; typedef double (*LPStrtodL)(const char *strSource, char **endptr, _locale_t locale); static LPStrtodL p_strtod_l = nullptr; #else locale_t ipeLocale; #endif #ifndef WIN32 static String dotIpe() { const char *home = getenv("HOME"); if (!home) return String(); String res = String(home) + "/.ipe"; if (!Platform::fileExists(res) && mkdir(res.z(), 0700) != 0) return String(); return res + "/"; } #endif #ifdef WIN32 static void readIpeConf() { String fname = Platform::ipeDir("", nullptr); fname += "\\ipe.conf"; String conf = Platform::readFile(fname); if (conf.empty()) return; ipeDebug("ipe.conf = %s", conf.z()); int i = 0; while (i < conf.size()) { String line = conf.getLine(i); _wputenv(line.w().data()); } } #else static void readIpeConf() { String fname = dotIpe() + "/ipe.conf"; String conf = Platform::readFile(fname); if (conf.empty()) return; ipeDebug("ipe.conf = %s", conf.z()); int i = 0; while (i < conf.size()) { String line = conf.getLine(i); putenv(strdup(line.z())); // a leak, but necessary } } #endif static void debugHandlerImpl(const char *msg) { if (showDebug) { fprintf(stderr, "%s\n", msg); #ifdef WIN32 fflush(stderr); OutputDebugStringA(msg); #endif } } static void shutdownIpelib() { #ifdef WIN32 Gdiplus::GdiplusShutdown(gdiplusToken); if (p_create_locale != nullptr) p_free_locale(ipeLocale); #else freelocale(ipeLocale); #endif Repository::cleanup(); } //! Initialize Ipelib. /*! This method must be called before Ipelib is used. It creates a LC_NUMERIC locale set to 'C', which is necessary for correct loading and saving of Ipe objects. The method also checks that the correct version of Ipelib is loaded, and aborts with an error message if the version is not correct. Also enables ipeDebug messages if environment variable IPEDEBUG is defined. (You can override this using setDebug). */ void Platform::initLib(int version) { if (initialized) return; initialized = true; readIpeConf(); showDebug = false; if (getenv("IPEDEBUG")) { showDebug = true; fprintf(stderr, "Debug messages enabled\n"); } debugHandler = debugHandlerImpl; #ifdef IPEAPPIMAGE const char *cwd = getcwd(nullptr, 0); if (cwd) appImageBase = cwd; else appImageBase = "."; #endif #ifdef WIN32 HMODULE hDll = LoadLibraryA("msvcrt.dll"); if (hDll) { p_create_locale = (LPCreateLocale) GetProcAddress(hDll, "_create_locale"); p_free_locale = (LPFreeLocale) GetProcAddress(hDll, "_free_locale"); p_strtod_l = (LPStrtodL) GetProcAddress(hDll, "_strtod_l"); } if (p_create_locale != nullptr) ipeLocale = p_create_locale(LC_NUMERIC, "C"); Gdiplus::GdiplusStartupInput gdiplusStartupInput; Gdiplus::GdiplusStartup(&gdiplusToken, &gdiplusStartupInput, nullptr); #else ipeLocale = newlocale(LC_NUMERIC_MASK, "C", nullptr); #endif atexit(shutdownIpelib); #ifndef IPE_NO_IPELIB_VERSION_CHECK if (version == IPELIB_VERSION) return; fprintf(stderr, "Ipetoipe has been compiled with header files for Ipelib %d\n" "but is dynamically linked against libipe %d.\n" "Check with 'ldd' which libipe is being loaded, and " "replace it by the correct version or set LD_LIBRARY_PATH.\n", version, IPELIB_VERSION); exit(99); #endif } //! Enable or disable display of ipeDebug messages. void Platform::setDebug(bool debug) { showDebug = debug; } // -------------------------------------------------------------------- void ipeDebug(const char *msg, ...) noexcept { if (debugHandler) { char buf[8196]; va_list ap; va_start(ap, msg); std::vsprintf(buf, msg, ap); va_end(ap); debugHandler(buf); } } // -------------------------------------------------------------------- //! Returns current working directory. /*! Returns empty string if something fails. */ String Platform::currentDirectory() { #ifdef WIN32 wchar_t *buffer = _wgetcwd(nullptr, 0); return String(buffer); #else char buffer[1024]; if (getcwd(buffer, 1024) != buffer) return String(); return String(buffer); #endif } //! Returns drive on which Ipe executable exists. /*! On Linux and OSX, returns empty string. */ String Platform::ipeDrive() { #ifdef WIN32 String fname = ipeDir("", nullptr); if (fname.size() > 2 && fname[1] == ':') return fname.left(2); #endif return String(); } #ifdef IPEBUNDLE String Platform::ipeDir(const char *suffix, const char *fname) { #ifdef IPESNAPCRAFT const char *p = getenv("SNAP"); String exe = p ? p : "/snap/ipe/current"; exe += "/ipe/"; #else #ifdef IPEAPPIMAGE String exe = appImageBase + "/ipe/"; #else #ifdef WIN32 wchar_t exename[OFS_MAXPATHNAME]; GetModuleFileNameW(nullptr, exename, OFS_MAXPATHNAME); String exe(exename); #else char path[PATH_MAX], rpath[PATH_MAX]; uint32_t size = sizeof(path); String exe; if (_NSGetExecutablePath(path, &size) == 0 && realpath(path, rpath) != nullptr) exe = String(rpath); else ipeDebug("ipeDir: buffer too small; need size %u", size); #endif int i = exe.rfind(IPESEP); if (i >= 0) { exe = exe.left(i); // strip filename i = exe.rfind(IPESEP); if (i >= 0) { exe = exe.left(i); // strip bin directory name } } #ifdef __APPLE__ if (!strcmp(suffix, "doc")) exe += "/SharedSupport/"; else exe += "/Resources/"; #else exe += IPESEP; #endif #endif #endif exe += suffix; if (fname) { exe += IPESEP; exe += fname; } return exe; } #endif //! Return path for the directory containing pdflatex and xelatex. /*! If empty means look on PATH. */ String Platform::latexPath() { String result; #ifdef WIN32 const wchar_t *p = _wgetenv(L"IPELATEXPATH"); if (p) result = String(p); if (result.left(4) == "ipe:") result = ipeDrive() + result.substr(4); #else char *p = getenv("IPELATEXPATH"); if (p) result = p; #endif return result; } //! Returns directory for running Latex. /*! The directory is created if it does not exist. Returns an empty string if the directory cannot be found or cannot be created. The directory returned ends in the path separator. */ String Platform::latexDirectory() { #ifdef WIN32 String latexDir; const wchar_t *p = _wgetenv(L"IPELATEXDIR"); if (p) { latexDir = String(p); if (latexDir.left(4) == "ipe:") latexDir = ipeDrive() + latexDir.substr(4); } else { wchar_t szPath[MAX_PATH]; if (SUCCEEDED(SHGetFolderPathW(nullptr, CSIDL_LOCAL_APPDATA, nullptr, 0, szPath))) { latexDir = String(szPath) + "\\ipe"; } else { p = _wgetenv(L"LOCALAPPDATA"); if (p) latexDir = String(p) + "\\ipe"; else latexDir = ipeDir("latexrun"); } } if (latexDir.right(1) == "\\") latexDir = latexDir.left(latexDir.size() - 1); if (!fileExists(latexDir)) { if (Platform::mkdir(latexDir.z()) != 0) return String(); } latexDir += "\\"; return latexDir; #else const char *p = getenv("IPELATEXDIR"); String latexDir; if (p) { latexDir = p; if (latexDir.right(1) == "/") latexDir = latexDir.left(latexDir.size() - 1); } else { latexDir = dotIpe() + "latexrun"; } if (!fileExists(latexDir) && mkdir(latexDir.z(), 0700) != 0) return String(); latexDir += "/"; return latexDir; #endif } //! Determine whether file exists. bool Platform::fileExists(String fname) { #ifdef WIN32 return (_waccess(fname.w().data(), F_OK) == 0); #else return (access(fname.z(), F_OK) == 0); #endif } //! Convert relative filename to absolute. /*! This also works when the filename does not exist, or at least it tries. */ String Platform::realPath(String fname) { #ifdef WIN32 wchar_t wresult[MAX_PATH]; // this function works also when fname does not exist GetFullPathNameW(fname.w().data(), MAX_PATH, wresult, nullptr); return String(wresult); #else char rpath[PATH_MAX]; if (realpath(fname.z(), rpath)) return String(rpath); if (errno != ENOENT || fname.left(1) == "/") return fname; // not much we can do if (realpath(".", rpath) == nullptr) return fname; // nothing we can do return String(rpath) + "/" + fname; #endif } //! List all files in directory /*! Return true if successful, false on error. */ bool Platform::listDirectory(String path, std::vector &files) { #ifdef WIN32 String pattern = path + "\\*"; struct _wfinddata_t info; intptr_t h = _wfindfirst(pattern.w().data(), &info); if (h == -1L) return false; files.push_back(String(info.name)); while (_wfindnext(h, &info) == 0) files.push_back(String(info.name)); _findclose(h); return true; #else DIR *dir = opendir(path.z()); if (dir == nullptr) return false; struct dirent *entry = readdir(dir); while (entry != nullptr) { String s(entry->d_name); if (s != "." && s != "..") files.push_back(s); entry = readdir(dir); } closedir(dir); return true; #endif } //! Read entire file into string. /*! Returns an empty string if file cannot be found or read. There is no way to distinguish an empty file from this. */ String Platform::readFile(String fname) { std::FILE *file = Platform::fopen(fname.z(), "rb"); if (!file) return String(); String s; int ch; while ((ch = std::fgetc(file)) != EOF) s.append(ch); std::fclose(file); return s; } //! Runs latex on file ipetemp.tex in given directory. /*! directory of docname is added to TEXINPUTS if its non-empty. */ int Platform::runLatex(String dir, LatexType engine, String docname) noexcept { const char *latex = (engine == LatexType::Xetex) ? "xelatex" : (engine == LatexType::Luatex) ? "lualatex" : "pdflatex"; String url = Platform::readFile(dir + "url.txt"); bool online = (url.left(4) == "http"); String texinputs; if (!online && !docname.empty()) { docname = realPath(docname); int i = docname.size(); while (i > 0 && docname[i-1] != IPESEP) --i; if (i > 0) texinputs = docname.substr(0, i-1); } #ifdef WIN32 if (!online && getenv("IPETEXFORMAT")) { latex = (engine == LatexType::Xetex) ? "xetex ^&latex" : (engine == LatexType::Luatex) ? "luatex ^&latex" : "pdftex ^&pdflatex"; } String bat; if (dir.size() > 2 && dir[1] == ':') { bat += dir.substr(0, 2); bat += "\r\n"; } bat += "cd \""; bat += dir; bat += "\"\r\n"; if (!texinputs.empty()) { bat += "setlocal\r\n"; bat += "set TEXINPUTS=.;"; bat += texinputs; bat += ";%TEXINPUTS%\r\n"; } if (online) { bat += ipeDir("bin", "ipecurl.exe"); bat += " "; bat += latex; bat += "\r\n"; } else { String path = latexPath(); if (!path.empty()) { bat += "PATH "; bat += path; bat += ";%PATH%\r\n"; } bat += latex; bat += " ipetemp.tex\r\n"; } if (!texinputs.empty()) bat += "endlocal\r\n"; // bat += "pause\r\n"; // alternative for Wine // CMD.EXE input needs to be encoded in "OEM codepage", // which can be different from "Windows codepage" std::wstring wbat = bat.w(); Buffer oemBat(2 * wbat.size() + 1); CharToOemW(wbat.data(), oemBat.data()); String s = dir + "runlatex.bat"; std::FILE *f = Platform::fopen(s.z(), "wb"); if (!f) return -1; std::fputs(oemBat.data(), f); std::fclose(f); // Declare and initialize process blocks PROCESS_INFORMATION processInformation; STARTUPINFOW startupInfo; memset(&processInformation, 0, sizeof(processInformation)); memset(&startupInfo, 0, sizeof(startupInfo)); startupInfo.cb = sizeof(startupInfo); // Call the executable program String cmd = String("cmd /c call \"") + dir + String("runlatex.bat\""); std::wstring wcmd = cmd.w(); int result = CreateProcessW(nullptr, wcmd.data(), nullptr, nullptr, FALSE, NORMAL_PRIORITY_CLASS|CREATE_NO_WINDOW, nullptr, nullptr, &startupInfo, &processInformation); if (result == 0) return -1; // failure to create process // Wait until child process exits. WaitForSingleObject(processInformation.hProcess, INFINITE); // Close process and thread handles. CloseHandle(processInformation.hProcess); CloseHandle(processInformation.hThread); // Apparently WaitForSingleObject doesn't work in Wine const char *wine = getenv("IPEWINE"); if (wine) Sleep(Lex(wine).getInt()); return 0; #else if (!online && getenv("IPETEXFORMAT")) { latex = (engine == LatexType::Xetex) ? "xetex \\&latex" : (engine == LatexType::Luatex) ? "luatex \\&latex" : "pdftex \\&pdflatex"; } String s("cd \""); s += dir; s += "\"; rm -f ipetemp.log; "; if (!texinputs.empty()) { s += "export TEXINPUTS=\""; s += texinputs; s += ":$TEXINPUTS\"; "; } if (online) { #ifdef __APPLE__ s += ipeDir("../MacOS", "ipecurl "); #else s += "ipecurl "; #endif s += latex; } else { String path = latexPath(); if (path.empty()) s += latex; else s += String("\"") + path + "/" + latex + "\""; s += " ipetemp.tex"; } s += " > /dev/null"; int result = std::system(s.z()); if (result != -1) result = WEXITSTATUS(result); return result; #endif } #ifdef WIN32 FILE *Platform::fopen(const char *fname, const char *mode) { return _wfopen(String(fname).w().data(), String(mode).w().data()); } int Platform::mkdir(const char *dname) { return _wmkdir(String(dname).w().data()); } //! Return a wide string including a terminating zero character. std::wstring String::w() const noexcept { if (empty()) return L"\0"; int rw = MultiByteToWideChar(CP_UTF8, 0, data(), size(), nullptr, 0); std::wstring result(rw + 1, wchar_t(0)); MultiByteToWideChar(CP_UTF8, 0, data(), size(), &result[0], rw); return result; } String::String(const wchar_t *wbuf) { if (!wbuf) { iImp = emptyString(); } else { int rm = WideCharToMultiByte(CP_UTF8, 0, wbuf, -1, nullptr, 0, nullptr, nullptr); iImp = new Imp; iImp->iRefCount = 1; iImp->iSize = rm - 1; // rm includes the trailing zero iImp->iCapacity = (rm + 32) & ~15; iImp->iData = new char[iImp->iCapacity]; WideCharToMultiByte(CP_UTF8, 0, wbuf, -1, iImp->iData, rm, nullptr, nullptr); } } #endif // -------------------------------------------------------------------- double Platform::toDouble(String s) { #ifdef WIN32 if (p_create_locale != nullptr) return _strtod_l(s.z(), nullptr, ipeLocale); else return strtod(s.z(), nullptr); #else return strtod_l(s.z(), nullptr, ipeLocale); #endif } int Platform::toNumber(String s, int &iValue, double &dValue) { char *fin = const_cast(s.z()); iValue = std::strtol(s.z(), &fin, 10); while (*fin == ' ' || *fin == '\t') ++fin; if (*fin == '\0') return 1; // integer #ifdef WIN32 if (p_create_locale != nullptr) dValue = _strtod_l(s.z(), &fin, ipeLocale); else dValue = strtod(s.z(), &fin); #else dValue = strtod_l(s.z(), &fin, ipeLocale); #endif while (*fin == ' ' || *fin == '\t') ++fin; if (*fin == '\0') return 2; // double // error return 0; } void ipeAssertionFailed(const char *file, int line, const char *assertion) { fprintf(stderr, "Assertion failed on line #%d (%s): '%s'\n", line, file, assertion); abort(); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipepdfwriter.cpp0000644000175000017500000010370013561570220017500 0ustar otfriedotfried// -------------------------------------------------------------------- // Creating PDF output // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeimage.h" #include "ipetext.h" #include "ipepainter.h" #include "ipegroup.h" #include "ipereference.h" #include "ipeutils.h" #include "ipepdfwriter.h" #include "ipepdfparser.h" #include "iperesources.h" using namespace ipe; typedef std::vector::const_iterator BmIter; // -------------------------------------------------------------------- PdfPainter::PdfPainter(const Cascade *style, Stream &stream) : Painter(style), iStream(stream) { State state; state.iStroke = Color(0,0,0); state.iFill = Color(0,0,0); state.iPen = Fixed(1); state.iDashStyle = "[]0"; state.iLineCap = style->lineCap(); state.iLineJoin = style->lineJoin(); state.iOpacity = Fixed(1); state.iStrokeOpacity = Fixed(1); iStream << state.iLineCap - 1 << " J " << state.iLineJoin - 1 << " j\n"; iActiveState.push_back(state); } void PdfPainter::doNewPath() { drawAttributes(); } void PdfPainter::doMoveTo(const Vector &v) { iStream << v << " m\n"; } void PdfPainter::doLineTo(const Vector &v) { iStream << v << " l\n"; } void PdfPainter::doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3) { iStream << v1 << " " << v2 << " " << v3 << " c\n"; } void PdfPainter::doClosePath() { iStream << "h "; } void PdfPainter::doAddClipPath() { iStream << "W* n "; } void PdfPainter::doPush() { State state = iActiveState.back(); iActiveState.push_back(state); iStream << "q "; } void PdfPainter::doPop() { iActiveState.pop_back(); iStream << "Q\n"; } void PdfPainter::drawColor(Stream &stream, Color color, const char *gray, const char *rgb) { if (color.isGray()) stream << color.iRed << " " << gray << "\n"; else stream << color << " " << rgb << "\n"; } void PdfPainter::drawAttributes() { State &s = iState.back(); State &sa = iActiveState.back(); if (s.iDashStyle != sa.iDashStyle) { sa.iDashStyle = s.iDashStyle; iStream << s.iDashStyle << " d\n"; } if (s.iPen != sa.iPen) { sa.iPen = s.iPen; iStream << s.iPen << " w\n"; } if (s.iLineCap != sa.iLineCap) { sa.iLineCap = s.iLineCap; iStream << s.iLineCap - 1 << " J\n"; } if (s.iLineJoin != sa.iLineJoin) { sa.iLineJoin = s.iLineJoin; iStream << s.iLineJoin - 1 << " j\n"; } if (s.iStroke != sa.iStroke) { sa.iStroke = s.iStroke; drawColor(iStream, s.iStroke, "G", "RG"); } if (s.iFill != sa.iFill || !s.iTiling.isNormal()) { sa.iFill = s.iFill; if (!s.iTiling.isNormal()) { iStream << "/PCS cs\n"; s.iFill.saveRGB(iStream); iStream << " /Pat" << s.iTiling.index() << " scn\n"; } else drawColor(iStream, s.iFill, "g", "rg"); } drawOpacity(true); } static const char *opacityName(Fixed alpha) { static char buf[12]; sprintf(buf, "/alpha%03d", alpha.internal()); return buf; } void PdfPainter::drawOpacity(bool withStroke) { State &s = iState.back(); State &sa = iActiveState.back(); if (s.iOpacity != sa.iOpacity) { sa.iOpacity = s.iOpacity; sa.iStrokeOpacity = s.iOpacity; iStream << opacityName(s.iOpacity) << " gs\n"; } if (withStroke && s.iStrokeOpacity != sa.iStrokeOpacity) { iStream << opacityName(s.iStrokeOpacity) << "s gs\n"; } } // If gradient fill is set, then StrokeAndFill does NOT stroke! void PdfPainter::doDrawPath(TPathMode mode) { bool eofill = (fillRule() == EEvenOddRule); // if (!mode) // iStream << "n\n"; // no op path const Gradient *g = nullptr; Attribute grad = iState.back().iGradient; if (!grad.isNormal()) g = iCascade->findGradient(grad); if (g) { if (mode == EStrokedOnly) iStream << "S\n"; else iStream << (eofill ? "q W* n " : "q W n ") << matrix() * g->iMatrix << " cm /Grad" << grad.index() << " sh Q\n"; } else { if (mode == EFilledOnly) iStream << (eofill ? "f*\n" : "f\n"); else if (mode == EStrokedOnly) iStream << "S\n"; else iStream << (eofill ? "B*\n" : "B\n"); // fill and then stroke } } void PdfPainter::doDrawBitmap(Bitmap bitmap) { if (bitmap.objNum() < 0) return; drawOpacity(false); iStream << matrix() << " cm /Image" << bitmap.objNum() << " Do\n"; } void PdfPainter::doDrawText(const Text *text) { const Text::XForm *xf = text->getXForm(); if (!xf) return; drawOpacity(false); pushMatrix(); transform(Matrix(xf->iStretch, 0, 0, xf->iStretch, 0, 0)); translate(xf->iTranslation); iStream << matrix() << " cm " ; iStream << "/" << xf->iName << " Do\n"; popMatrix(); } void PdfPainter::doDrawSymbol(Attribute symbol) { const Symbol *sym = cascade()->findSymbol(symbol); if (!sym) return; if (sym->iXForm) iStream << "/Symbol" << symbol.index() << " Do\n"; else sym->iObject->draw(*this); } // -------------------------------------------------------------------- /*! \class ipe::PdfWriter \brief Create PDF file. This class is responsible for the creation of a PDF file from the Ipe data. You have to create a PdfWriter first, providing a file that has been opened for (binary) writing and is empty. Then call createPages() to embed the pages. Optionally, call \c createXmlStream to embed a stream with the XML representation of the document. Finally, call \c createTrailer to complete the PDF document, and close the file. Some reserved PDF object numbers: - 0: Must be left empty (a PDF restriction). - 1: XML stream. - 2: Parent of all pages objects. - 3: ExtGState resource from pdflatex - 4: Shading resource from pdflatex - 5: Pattern resource from pdflatex - 6: ColorSpace resource from pdflatex */ //! Create a PDF writer operating on this (open and empty) file. PdfWriter::PdfWriter(TellStream &stream, const Document *doc, const PdfResources *resources, uint32_t flags, int fromPage, int toPage, int compression) : iStream(stream), iDoc(doc), iResources(resources), iSaveFlags(flags), iFromPage(fromPage), iToPage(toPage) { iCompressLevel = compression; iObjNum = 7; // 0 - 6 are reserved iXmlStreamNum = -1; // no XML stream yet iExtGState = -1; iPatternNum = -1; iBookmarks = -1; iDests = -1; if (iFromPage < 0 || iFromPage >= iDoc->countPages()) iFromPage = 0; if (iToPage < iFromPage || iToPage >= iDoc->countPages()) iToPage = iDoc->countPages() - 1; // mark all bitmaps as not embedded BitmapFinder bm; iDoc->findBitmaps(bm); int id = -1; for (std::vector::iterator it = bm.iBitmaps.begin(); it != bm.iBitmaps.end(); ++it) { it->setObjNum(id); --id; } iStream << "%PDF-1.4\n"; // embed all fonts and other resources from Pdflatex embedResources(); // embed resources from pdflatex embedLatexResource(3, "ExtGState"); embedLatexResource(4, "Shading"); embedLatexResource(5, "Pattern"); embedLatexResource(6, "ColorSpace"); // embed all extgstate objects AttributeSeq os; iDoc->cascade()->allNames(EOpacity, os); if (os.size() > 0) { iExtGState = startObject(); iStream << "<<\n"; for (const auto & obj : os) { Attribute alpha = iDoc->cascade()->find(EOpacity, obj); assert(alpha.isNumber()); iStream << opacityName(alpha.number()) << " << /CA " << alpha.number() << " /ca " << alpha.number() << " >>\n"; iStream << opacityName(alpha.number()) << "s << /CA " << alpha.number() << " >>\n"; } iStream << ">> endobj\n"; } // embed all gradients AttributeSeq gs; iDoc->cascade()->allNames(EGradient, gs); for (const auto & grad : gs) { const Gradient *g = iDoc->cascade()->findGradient(grad); int num = startObject(); iStream << "<<\n" << " /ShadingType " << int(g->iType) << "\n" << " /ColorSpace /DeviceRGB\n"; if (g->iType == Gradient::EAxial) iStream << " /Coords [" << g->iV[0] << " " << g->iV[1] << "]\n"; else iStream << " /Coords [" << g->iV[0] << " " << g->iRadius[0] << " " << g->iV[1] << " " << g->iRadius[1] << "]\n"; iStream << " /Extend [" << (g->iExtend ? "true true]\n" : "false false]\n"); if (g->iStops.size() == 2) { iStream << " /Function << /FunctionType 2 /Domain [ 0 1 ] /N 1\n" << " /C0 ["; g->iStops[0].color.saveRGB(iStream); iStream << "]\n" << " /C1 ["; g->iStops[1].color.saveRGB(iStream); iStream << "] >>\n"; } else { // need to stitch iStream << " /Function <<\n" << " /FunctionType 3 /Domain [ 0 1 ]\n" << " /Bounds ["; int count = 0; for (int i = 1; i < size(g->iStops) - 1; ++i) { if (g->iStops[i].offset > g->iStops[i-1].offset) { iStream << g->iStops[i].offset << " "; ++count; } } iStream << "]\n /Encode ["; for (int i = 0; i <= count; ++i) iStream << "0.0 1.0 "; iStream << "]\n /Functions [\n"; for (int i = 1; i < size(g->iStops); ++i) { if (g->iStops[i].offset > g->iStops[i-1].offset) { iStream << " << /FunctionType 2 /Domain [ 0 1 ] /N 1 /C0 ["; g->iStops[i-1].color.saveRGB(iStream); iStream << "] /C1 ["; g->iStops[i].color.saveRGB(iStream); iStream << "] >>\n"; } } iStream << "] >>\n"; } iStream << ">> endobj\n"; iGradients[grad.index()] = num; } // embed all tilings AttributeSeq ts; std::map patterns; iDoc->cascade()->allNames(ETiling, ts); if (ts.size() > 0) { for (const auto & tiling : ts) { const Tiling *t = iDoc->cascade()->findTiling(tiling); Linear m(t->iAngle); int num = startObject(); iStream << "<<\n" << "/Type /Pattern\n" << "/PatternType 1\n" // tiling pattern << "/PaintType 2\n" // uncolored pattern << "/TilingType 2\n" // faster << "/BBox [ 0 0 100 " << t->iStep << " ]\n" << "/XStep 100\n" << "/YStep " << t->iStep << "\n" << "/Resources << >>\n" << "/Matrix [" << m << " 0 0]\n"; String s; StringStream ss(s); ss << "0 0 100 " << t->iWidth << " re f\n"; createStream(s.data(), s.size(), false); patterns[tiling.index()] = num; } // create pattern dictionary iPatternNum = startObject(); iStream << "<<\n"; for (const auto & pattern : ts) { iStream << "/Pat" << pattern.index() << " " << patterns[pattern.index()] << " 0 R\n"; } iStream << ">> endobj\n"; } // embed all symbols with xform attribute AttributeSeq sys; iDoc->cascade()->allNames(ESymbol, sys); if (sys.size()) { for (const auto & sysi : sys) { const Symbol *sym = iDoc->cascade()->findSymbol(sysi); if (sym->iXForm) { // compute bbox for object BBoxPainter bboxPainter(iDoc->cascade()); sym->iObject->draw(bboxPainter); Rect bbox = bboxPainter.bbox(); // embed all bitmaps it uses BitmapFinder bm; sym->iObject->accept(bm); embedBitmaps(bm); int num = startObject(); iStream << "<<\n"; iStream << "/Type /XObject\n"; iStream << "/Subtype /Form\n"; iStream << "/BBox [" << bbox << "]\n"; createResources(bm); String s; StringStream ss(s); PdfPainter painter(iDoc->cascade(), ss); sym->iObject->draw(painter); createStream(s.data(), s.size(), false); iSymbols[sysi.index()] = num; } } } } //! Destructor. PdfWriter::~PdfWriter() { // nothing } /*! Write the beginning of the next object: "no 0 obj " and save information about file position. Default argument uses next unused object number. Returns number of new object. */ int PdfWriter::startObject(int objnum) { if (objnum < 0) objnum = iObjNum++; iXref[objnum] = iStream.tell(); iStream << objnum << " 0 obj "; return objnum; } bool PdfWriter::hasResource(String kind) const noexcept { return iResources && iResources->resourcesOfKind(kind); } /*! Write all PDF resources to the PDF file, and record their object numbers. Embeds nothing if \c resources is nullptr, but must be called nevertheless. */ void PdfWriter::embedResources() { bool inflate = (iCompressLevel == 0); if (iResources) { const std::vector &seq = iResources->embedSequence(); for (auto &num : seq) { const PdfObj *obj = iResources->object(num); int embedNum = startObject(); if (obj->dict() && obj->dict()->get("IpeId", nullptr)) embedIpeXForm(obj->dict()); else obj->write(iStream, &iResourceNumber, inflate); iStream << " endobj\n"; iResourceNumber[num] = embedNum; } } } void PdfWriter::embedIpeXForm(const PdfDict *d) { bool inflate = (iCompressLevel == 0) && d->deflated(); iStream << "<<"; for (int i = 0; i < d->count(); ++i) { String key = d->key(i); // skip /IpeId etc keys if (key.left(3) == "Ipe") continue; if ((inflate && key == "Filter") || key == "Length") continue; // remove /FlateDecode filter and /Length iStream << "/" << key << " "; if (key == "Resources") { const PdfObj *res = d->value(i); if (res->ref()) res = iResources->object(res->ref()->value()); if (res->dict()) embedXFormResource(res->dict()); else // should not happen! d->value(i)->write(iStream, &iResourceNumber); } else if (key == "BBox") { const TextPadding *pad = iDoc->cascade()->findTextPadding(); std::vector bbox; d->getNumberArray("BBox", nullptr, bbox); if (pad && bbox.size() == 4) { bbox[0] -= pad->iLeft; bbox[1] -= pad->iBottom; bbox[2] += pad->iRight; bbox[3] += pad->iTop; } iStream << "["; for (auto it = bbox.begin(); it != bbox.end(); ++it) iStream << *it << " "; iStream << "]"; } else d->value(i)->write(iStream, &iResourceNumber); iStream << " "; } Buffer stream = inflate ? d->inflate() : d->stream(); if (stream.size() > 0) { iStream << "/Length " << stream.size() << ">>\nstream\n"; for (int i = 0; i < stream.size(); ++i) iStream.putChar(stream[i]); iStream << "\nendstream"; } else iStream << ">>"; } void PdfWriter::embedXFormResource(const PdfDict *d) { iStream << "<<"; for (int i = 0; i < d->count(); ++i) { String key = d->key(i); iStream << "/" << key << " "; if (key == "ColorSpace" || key == "Shading" || key == "Pattern" || key == "ExtGState") { ipeDebug("PDF Writer: Conflicting resource in XForm: %s", key.z()); } else d->value(i)->write(iStream, &iResourceNumber); } if (hasResource("ExtGState")) iStream << "/ExtGState 3 0 R\n"; if (hasResource("Shading")) iStream << "/ColorSpace 4 0 R\n"; if (hasResource("Pattern")) iStream << "/Pattern 5 0 R\n"; if (hasResource("ColorSpace")) iStream << "/ColorSpace 6 0 R\n"; iStream << ">>"; } void PdfWriter::embedLatexResource(int num, String kind) { if (hasResource(kind)) { startObject(num); iStream << "<<\n"; embedResource(kind); iStream << ">> endobj\n"; } } void PdfWriter::embedResource(String kind) { if (!iResources) return; const PdfDict *d = iResources->resourcesOfKind(kind); if (!d) return; for (int i = 0; i < d->count(); ++i) { iStream << "/" << d->key(i) << " "; d->value(i)->write(iStream, &iResourceNumber); iStream << " "; } } //! Write a stream. /*! Write a stream, either plain or compressed, depending on compress level. Object must have been created with dictionary start having been written. If \a preCompressed is true, the data is already deflated. */ void PdfWriter::createStream(const char *data, int size, bool preCompressed) { if (preCompressed) { iStream << "/Length " << size << " /Filter /FlateDecode >>\nstream\n"; iStream.putRaw(data, size); iStream << "\nendstream endobj\n"; return; } if (iCompressLevel > 0) { int deflatedSize; Buffer deflated = DeflateStream::deflate(data, size, deflatedSize, iCompressLevel); iStream << "/Length " << deflatedSize << " /Filter /FlateDecode >>\nstream\n"; iStream.putRaw(deflated.data(), deflatedSize); iStream << "\nendstream endobj\n"; } else { iStream << "/Length " << size << " >>\nstream\n"; iStream.putRaw(data, size); iStream << "endstream endobj\n"; } } // -------------------------------------------------------------------- void PdfWriter::embedBitmap(Bitmap bitmap) { int smaskNum = -1; auto embed = bitmap.embed(); if (bitmap.hasAlpha() && embed.second.size() > 0) { smaskNum = startObject(); iStream << "<<\n"; iStream << "/Type /XObject\n"; iStream << "/Subtype /Image\n"; iStream << "/Width " << bitmap.width() << "\n"; iStream << "/Height " << bitmap.height() << "\n"; iStream << "/ColorSpace /DeviceGray\n"; iStream << "/Filter /FlateDecode\n"; iStream << "/BitsPerComponent 8\n"; iStream << "/Length " << embed.second.size() << "\n>> stream\n"; iStream.putRaw(embed.second.data(), embed.second.size()); iStream << "\nendstream endobj\n"; } int objnum = startObject(); iStream << "<<\n"; iStream << "/Type /XObject\n"; iStream << "/Subtype /Image\n"; iStream << "/Width " << bitmap.width() << "\n"; iStream << "/Height " << bitmap.height() << "\n"; if (bitmap.isGray()) iStream << "/ColorSpace /DeviceGray\n"; else iStream << "/ColorSpace /DeviceRGB\n"; if (bitmap.isJpeg()) iStream << "/Filter /DCTDecode\n"; else iStream << "/Filter /FlateDecode\n"; iStream << "/BitsPerComponent 8\n"; if (smaskNum >= 0) { iStream << "/SMask " << smaskNum << " 0 R\n"; } else if (bitmap.colorKey() >= 0) { int r = (bitmap.colorKey() >> 16) & 0xff; int g = (bitmap.colorKey() >> 8) & 0xff; int b = bitmap.colorKey() & 0xff; iStream << "/Mask [" << r << " " << r; if (!bitmap.isGray()) iStream << " " << g << " " << g << " " << b << " " << b; iStream << "]\n"; } iStream << "/Length " << embed.first.size() << "\n>> stream\n"; iStream.putRaw(embed.first.data(), embed.first.size()); iStream << "\nendstream endobj\n"; bitmap.setObjNum(objnum); } void PdfWriter::embedBitmaps(const BitmapFinder &bm) { for (BmIter it = bm.iBitmaps.begin(); it != bm.iBitmaps.end(); ++it) { BmIter it1 = std::find(iBitmaps.begin(), iBitmaps.end(), *it); if (it1 == iBitmaps.end()) { // look again, more carefully for (it1 = iBitmaps.begin(); it1 != iBitmaps.end() && !it1->equal(*it); ++it1) ; if (it1 == iBitmaps.end()) embedBitmap(*it); // not yet embedded else it->setObjNum(it1->objNum()); // identical Bitmap is embedded iBitmaps.push_back(*it); } } } void PdfWriter::createResources(const BitmapFinder &bm) { // These are only the resources needed by Ipe drawing directly. // Resources used from inside text objects (e.g. by tikz) // are stored inside the XObject resources. // Font is only used inside XObject, no font resource needed on page // Resources: // ProcSet, ExtGState, ColorSpace, Pattern, Shading, XObject, Font // not used now: Properties // ProcSet iStream << "/Resources <<\n /ProcSet [/PDF"; if (iResources) iStream << "/Text"; if (!bm.iBitmaps.empty()) iStream << "/ImageB/ImageC"; iStream << "]\n"; // Shading if (iGradients.size()) { iStream << " /Shading <<"; for (std::map::const_iterator it = iGradients.begin(); it != iGradients.end(); ++it) iStream << " /Grad" << it->first << " " << it->second << " 0 R"; iStream << " >>\n"; } // ExtGState if (iExtGState >= 0) iStream << " /ExtGState " << iExtGState << " 0 R\n"; // ColorSpace if (iPatternNum >= 0) { iStream << " /ColorSpace << /PCS [/Pattern /DeviceRGB] "; iStream << ">>\n"; } // Pattern if (iPatternNum >= 0) iStream << " /Pattern " << iPatternNum << " 0 R\n"; // XObject // TODO: Is "hasResource" here used correctly? // From Tikz xobject resources seem to go into the Ipe xform. if (!bm.iBitmaps.empty() || !iSymbols.empty() || hasResource("XObject")) { iStream << " /XObject << "; for (BmIter it = bm.iBitmaps.begin(); it != bm.iBitmaps.end(); ++it) { // mention each PDF object only once BmIter it1; for (it1 = bm.iBitmaps.begin(); it1 != it && it1->objNum() != it->objNum(); it1++) ; if (it1 == it) iStream << "/Image" << it->objNum() << " " << it->objNum() << " 0 R "; } for (std::map::const_iterator it = iSymbols.begin(); it != iSymbols.end(); ++it) iStream << "/Symbol" << it->first << " " << it->second << " 0 R "; embedResource("XObject"); iStream << ">>\n"; } iStream << " >>\n"; } // -------------------------------------------------------------------- void PdfWriter::paintView(Stream &stream, int pno, int view) { const Page *page = iDoc->page(pno); PdfPainter painter(iDoc->cascade(), stream); const Symbol *background = iDoc->cascade()->findSymbol(Attribute::BACKGROUND()); if (background && page->findLayer("BACKGROUND") < 0) painter.drawSymbol(Attribute::BACKGROUND()); if (iDoc->properties().iNumberPages && iResources) { const Text *pn = iResources->pageNumber(pno, view); if (pn) pn->draw(painter); } const Text *title = page->titleText(); if (title) title->draw(painter); for (int i = 0; i < page->count(); ++i) { if (page->objectVisible(view, i)) page->object(i)->draw(painter); } } //! create contents and page stream for this page view. void PdfWriter::createPageView(int pno, int view) { const Page *page = iDoc->page(pno); // Find bitmaps to embed BitmapFinder bm; const Symbol *background = iDoc->cascade()->findSymbol(Attribute::BACKGROUND()); if (background && page->findLayer("BACKGROUND") < 0) background->iObject->accept(bm); bm.scanPage(page); // ipeDebug("# of bitmaps: %d", bm.iBitmaps.size()); embedBitmaps(bm); // create page stream String pagedata; StringStream sstream(pagedata); if (iCompressLevel > 0) { DeflateStream dfStream(sstream, iCompressLevel); paintView(dfStream, pno, view); dfStream.close(); } else paintView(sstream, pno, view); int firstLink = -1; int lastLink = -1; for (int i = 0; i < page->count(); ++i) { const Group *g = page->object(i)->asGroup(); if (g && page->objectVisible(view, i) && !g->url().empty()) { lastLink = startObject(); if (firstLink < 0) firstLink = lastLink; iStream << "<<\n" << "/Type /Annot\n" << "/Subtype /Link\n" << "/H /N\n" << "/Rect [" << page->bbox(i) << "]\n" << "/A <url(); if (url.left(6) == "named:") { iStream << "/Named/N/" << url.substr(6); } else { if (url.left(7) == "launch:") { url = url.substr(7); iStream << "/Launch/F"; } else if (url.left(5) == "goto:") { url = url.substr(5); iStream << "/GoTo/D"; } else iStream << "/URI/URI"; writeString(url); } iStream << ">>\n>> endobj\n"; } } int notesObj = -1; if (!page->notes().empty() && (!(iSaveFlags & SaveFlag::Export) || (iSaveFlags & SaveFlag::KeepNotes))) { notesObj = startObject(); iStream << "<<\n" << "/Type /Annot\n" << "/Subtype /Text\n" << "/Rect [20 40 30 40]\n" << "/F 4\n" << "/Contents "; writeString(page->notes()); iStream << "\n>> endobj\n"; } int contentsobj = startObject(); iStream << "<<\n"; createStream(pagedata.data(), pagedata.size(), (iCompressLevel > 0)); int pageobj = startObject(); iStream << "<<\n"; iStream << "/Type /Page\n"; if (firstLink >= 0 || notesObj >= 0) { iStream << "/Annots [ "; if (firstLink >= 0) { while (firstLink <= lastLink) iStream << firstLink++ << " 0 R "; } if (notesObj >= 0) iStream << notesObj << " 0 R"; iStream << "]\n"; } iStream << "/Contents " << contentsobj << " 0 R\n"; // iStream << "/Rotate 0\n"; createResources(bm); if (!page->effect(view).isNormal()) { const Effect *effect = iDoc->cascade()->findEffect(page->effect(view)); if (effect) effect->pageDictionary(iStream); } const Layout *layout = iDoc->cascade()->findLayout(); iStream << "/MediaBox [ " << layout->paper() << "]\n"; int viewBBoxLayer = page->findLayer("VIEWBBOX"); Rect bbox; if (viewBBoxLayer >= 0 && page->visible(view, viewBBoxLayer)) bbox = page->viewBBox(iDoc->cascade(), view); else bbox = page->pageBBox(iDoc->cascade()); if (layout->iCrop && !bbox.isEmpty()) iStream << "/CropBox [" << bbox << "]\n"; if (!bbox.isEmpty()) iStream << "/ArtBox [" << bbox << "]\n"; iStream << "/Parent 2 0 R\n"; iStream << ">> endobj\n"; iPageObjectNumbers.push_back({ pno, view, pageobj }); } //! Create all PDF pages. void PdfWriter::createPages() { for (int page = iFromPage; page <= iToPage; ++page) { if ((iSaveFlags & SaveFlag::MarkedView) && !iDoc->page(page)->marked()) continue; int nViews = iDoc->page(page)->countViews(); if (iSaveFlags & SaveFlag::MarkedView) { bool shown = false; for (int view = 0; view < nViews; ++view) { if (iDoc->page(page)->markedView(view)) { createPageView(page, view); shown = true; } } if (!shown) createPageView(page, nViews - 1); } else { for (int view = 0; view < nViews; ++view) createPageView(page, view); } } } //! Create a stream containing the XML data. void PdfWriter::createXmlStream(String xmldata, bool preCompressed) { iXmlStreamNum = startObject(1); iStream << "<<\n/Type /Ipe\n"; createStream(xmldata.data(), xmldata.size(), preCompressed); } //! Write a PDF string object to the PDF stream. void PdfWriter::writeString(String text) { // Check if it is all ASCII bool isAscii = true; for (int i = 0; isAscii && i < text.size(); ++i) { if (text[i] & 0x80) isAscii = false; } if (isAscii) { iStream << "("; for (int i = 0; i < text.size(); ++i) { char ch = text[i]; switch (ch) { case '(': case ')': case '\\': iStream << "\\"; // fall through default: iStream << ch; break; } } iStream << ")"; } else { char buf[5]; iStream << ""; } } // -------------------------------------------------------------------- int PdfWriter::pageObjectNumber(int page, int view) { auto it = std::find_if(iPageObjectNumbers.begin(), iPageObjectNumbers.end(), [=](const PON &pon) {return pon.page == page && pon.view == view;}); if (it != iPageObjectNumbers.end()) return it->objNum; ipeDebug("pageObjectNumber not found, this is a bug!"); return 0; } struct Section { int iPage; int iObjNum; std::vector iSubPages; }; //! Create the bookmarks (PDF outline). void PdfWriter::createBookmarks() { // first collect all information std::vector
sections; for (int pg = iFromPage; pg <= iToPage; ++pg) { if ((iSaveFlags & SaveFlag::MarkedView) && !iDoc->page(pg)->marked()) continue; String s = iDoc->page(pg)->section(0); String ss = iDoc->page(pg)->section(1); if (!s.empty()) { Section sec; sec.iPage = pg; sections.push_back(sec); } if (!sections.empty() && !ss.empty()) sections.back().iSubPages.push_back(pg); } if (sections.empty()) return; // reserve outline object iBookmarks = iObjNum++; // assign object numbers for (int s = 0; s < size(sections); ++s) { sections[s].iObjNum = iObjNum++; iObjNum += sections[s].iSubPages.size(); // leave space for subsections } // embed root startObject(iBookmarks); iStream << "<<\n/First " << sections[0].iObjNum << " 0 R\n" << "/Count " << int(sections.size()) << "\n" << "/Last " << sections.back().iObjNum << " 0 R\n>> endobj\n"; for (int s = 0; s < size(sections); ++s) { int count = sections[s].iSubPages.size(); int obj = sections[s].iObjNum; // embed section startObject(obj); iStream << "<<\n/Title "; writeString(iDoc->page(sections[s].iPage)->section(0)); iStream << "\n/Parent " << iBookmarks << " 0 R\n" << "/Dest [ " << pageObjectNumber(sections[s].iPage, 0) << " 0 R /XYZ null null null ]\n"; if (s > 0) iStream << "/Prev " << sections[s-1].iObjNum << " 0 R\n"; if (s < size(sections) - 1) iStream << "/Next " << sections[s+1].iObjNum << " 0 R\n"; if (count > 0) iStream << "/Count " << -count << "\n" << "/First " << (obj + 1) << " 0 R\n" << "/Last " << (obj + count) << " 0 R\n"; iStream << ">> endobj\n"; // using ids obj + 1 .. obj + count for the subsections for (int ss = 0; ss < count; ++ss) { int pageNo = sections[s].iSubPages[ss]; startObject(obj + ss + 1); iStream << "<<\n/Title "; writeString(iDoc->page(pageNo)->section(1)); iStream << "\n/Parent " << obj << " 0 R\n" << "/Dest [ " << pageObjectNumber(pageNo, 0) << " 0 R /XYZ null null null ]\n"; if (ss > 0) iStream << "/Prev " << (obj + ss) << " 0 R\n"; if (ss < count - 1) iStream << "/Next " << (obj + ss + 2) << " 0 R\n"; iStream << ">> endobj\n"; } } } //! Create the named destinations. void PdfWriter::createNamedDests() { std::vector> dests; for (int pg = iFromPage; pg <= iToPage; ++pg) { if ((iSaveFlags & SaveFlag::MarkedView) && !iDoc->page(pg)->marked()) continue; String s = iDoc->page(pg)->section(0); if (!s.empty()) dests.push_back(std::make_pair(s, pageObjectNumber(pg, 0))); } if (dests.empty()) return; std::sort(dests.begin(), dests.end()); iDests = startObject(); iStream << "<<\n/Limits ["; writeString(dests.front().first); iStream << " "; writeString(dests.back().first); iStream << "]\n/Names [\n"; for (const auto & dest : dests) { writeString(dest.first); iStream << " [" << dest.second << " 0 R /XYZ null null null]\n"; } iStream << "]>> endobj\n"; } // -------------------------------------------------------------------- //! Create the root objects and trailer of the PDF file. void PdfWriter::createTrailer() { const Document::SProperties &props = iDoc->properties(); // create /Pages startObject(2); iStream << "<<\n" << "/Type /Pages\n"; iStream << "/Count " << int(iPageObjectNumbers.size()) << "\n"; iStream << "/Kids [ "; for (auto pon : iPageObjectNumbers) iStream << pon.objNum << " 0 R "; iStream << "]\n>> endobj\n"; // create Name dictionary int nameDict = -1; if (iDests >= 0) { nameDict = startObject(); iStream << "<> endobj\n"; } // create PieceInfo int pieceInfo = startObject(); iStream << "<> >> endobj\n"; // create /Catalog int catalogobj = startObject(); iStream << "<<\n/Type /Catalog\n/Pages 2 0 R\n" << "/PieceInfo " << pieceInfo << " 0 R\n"; if (props.iFullScreen) iStream << "/PageMode /FullScreen\n"; if (iBookmarks >= 0) { if (!props.iFullScreen) iStream << "/PageMode /UseOutlines\n"; iStream << "/Outlines " << iBookmarks << " 0 R\n"; } if (nameDict >= 0) iStream << "/Names " << nameDict << " 0 R\n"; if (iDoc->countTotalViews() > 1) { iStream << "/PageLabels << /Nums [ "; int count = 0; for (int page = 0; page < iDoc->countPages(); ++page) { if (!(iSaveFlags & SaveFlag::MarkedView) || iDoc->page(page)->marked()) { int nviews = (iSaveFlags & SaveFlag::MarkedView) ? iDoc->page(page)->countMarkedViews() : iDoc->page(page)->countViews(); if (nviews > 1) { iStream << count << " <>"; } else { // one view only! iStream << count << " <

>"; } count += nviews; } } iStream << "] >>\n"; } iStream << ">> endobj\n"; // create /Info int infoobj = startObject(); iStream << "<<\n"; if (!props.iCreator.empty()) { iStream << "/Creator (" << props.iCreator << ")\n"; iStream << "/Producer (" << props.iCreator << ")\n"; } if (!props.iTitle.empty()) { iStream << "/Title "; writeString(props.iTitle); iStream << "\n"; } if (!props.iAuthor.empty()) { iStream << "/Author "; writeString(props.iAuthor); iStream << "\n"; } if (!props.iSubject.empty()) { iStream << "/Subject "; writeString(props.iSubject); iStream << "\n"; } if (!props.iKeywords.empty()) { iStream << "/Keywords "; writeString(props.iKeywords); iStream << "\n"; } iStream << "/CreationDate (" << props.iCreated << ")\n"; iStream << "/ModDate (" << props.iModified << ")\n"; iStream << ">> endobj\n"; // create Xref long xrefpos = iStream.tell(); iStream << "xref\n0 " << iObjNum << "\n"; for (int obj = 0; obj < iObjNum; ++obj) { std::map::const_iterator it = iXref.find(obj); char s[12]; if (it == iXref.end()) { std::sprintf(s, "%010d", obj); iStream << s << " 00000 f \n"; // note the final space! } else { std::sprintf(s, "%010ld", iXref[obj]); iStream << s << " 00000 n \n"; // note the final space! } } iStream << "trailer\n<<\n"; iStream << "/Size " << iObjNum << "\n"; iStream << "/Root " << catalogobj << " 0 R\n"; iStream << "/Info " << infoobj << " 0 R\n"; iStream << ">>\nstartxref\n" << int(xrefpos) << "\n%%EOF\n"; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipegroup.cpp0000644000175000017500000002465513561570220016641 0ustar otfriedotfried// -------------------------------------------------------------------- // The group object // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipegroup.h" #include "ipepainter.h" #include "ipetext.h" #include "ipeshape.h" using namespace ipe; /*! \class ipe::Group \ingroup obj \brief The group object. Ipe objects can be grouped together, and the resulting composite can be used like any Ipe object. This is an application of the "Composite" pattern. */ //! Create empty group (objects can be added later). Group::Group() : Object() { iImp = new Imp; iImp->iRefCount = 1; iImp->iPinned = ENoPin; iDecoration = Attribute::NORMAL(); } //! Create empty group with these attributes (objects can be added later). Group::Group(const XmlAttributes &attr) : Object(attr) { iImp = new Imp; iImp->iRefCount = 1; iImp->iPinned = ENoPin; String str; if (attr.has("clip", str)) { Shape clip; if (clip.load(str)) iClip = clip; } iUrl = attr["url"]; iDecoration = attr.has("decoration", str) ? Attribute(true, str) : Attribute::NORMAL(); } //! Copy constructor. Constant time --- components are not copied! Group::Group(const Group &rhs) : Object(rhs) { iImp = rhs.iImp; iImp->iRefCount++; iClip = rhs.iClip; iUrl = rhs.iUrl; iDecoration = rhs.iDecoration; } //! Destructor. Group::~Group() { if (iImp->iRefCount == 1) { for (List::iterator it = iImp->iObjects.begin(); it != iImp->iObjects.end(); ++it) { delete *it; *it = nullptr; } delete iImp; } else iImp->iRefCount--; } //! Assignment operator (constant-time). Group &Group::operator=(const Group &rhs) { if (this != &rhs) { if (iImp->iRefCount == 1) delete iImp; else iImp->iRefCount--; iImp = rhs.iImp; iImp->iRefCount++; iClip = rhs.iClip; iUrl = rhs.iUrl; iDecoration = rhs.iDecoration; Object::operator=(rhs); } return *this; } //! Clone a group object (constant-time). Object *Group::clone() const { return new Group(*this); } //! Return pointer to this object. Group *Group::asGroup() { return this; } //! Return pointer to this object. const Group *Group::asGroup() const { return this; } Object::Type Group::type() const { return EGroup; } //! Add an object. /*! Takes ownership of the object. This will panic if the object shares its implementation! The method is only useful right after construction of the group. */ void Group::push_back(Object *obj) { assert(iImp->iRefCount == 1); iImp->iObjects.push_back(obj); iImp->iPinned = TPinned(iImp->iPinned | obj->pinned()); } //! Save all the components, one by one, in XML format. void Group::saveComponentsAsXml(Stream &stream) const { for (const_iterator it = begin(); it != end(); ++it) (*it)->saveAsXml(stream, String()); } //! Call visitGroup of visitor. void Group::accept(Visitor &visitor) const { visitor.visitGroup(this); } void Group::saveAsXml(Stream &stream, String layer) const { stream << "\n"; saveComponentsAsXml(stream); stream << "\n"; } // -------------------------------------------------------------------- class DecorationPainter : public Painter { public: DecorationPainter(Painter &painter, const Vector ¢er, double dx, double dy); protected: virtual void doPush(); virtual void doPop(); virtual void doNewPath(); virtual void doMoveTo(const Vector &v); virtual void doLineTo(const Vector &v); virtual void doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3); virtual void doClosePath(); virtual void doDrawPath(TPathMode mode); Vector adapt(const Vector &v); private: Painter &iPainter; Vector iCenter; double iX, iY; }; DecorationPainter::DecorationPainter(Painter &painter, const Vector ¢er, double dx, double dy) : Painter(painter.cascade()), iPainter(painter), iCenter(center), iX(dx), iY(dy) { // nothing } Vector DecorationPainter::adapt(const Vector &v) { Vector r; r.x = (v.x < iCenter.x) ? v.x - iX : v.x + iX; r.y = (v.y < iCenter.y) ? v.y - iY : v.y + iY; return r; } void DecorationPainter::doPush() { iPainter.push(); } void DecorationPainter::doPop() { iPainter.pop(); } void DecorationPainter::doNewPath() { iPainter.setState(iState.back()); iPainter.newPath(); } void DecorationPainter::doMoveTo(const Vector &v) { iPainter.moveTo(adapt(v)); } void DecorationPainter::doLineTo(const Vector &v) { iPainter.lineTo(adapt(v)); } void DecorationPainter::doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3) { iPainter.curveTo(adapt(v1), adapt(v2), adapt(v3)); } void DecorationPainter::doClosePath() { iPainter.closePath(); } void DecorationPainter::doDrawPath(TPathMode mode) { iPainter.drawPath(mode); } // -------------------------------------------------------------------- void Group::draw(Painter &painter) const { if (!iDecoration.isNormal()) { painter.pushMatrix(); auto m = painter.matrix(); painter.untransform(ETransformationsTranslations); Rect r; addToBBox(r, m, false); double dx = 0.5 * (r.width() - 200.0); double dy = 0.5 * (r.height() - 100.0); DecorationPainter dp(painter, r.center(), dx, dy); dp.translate(r.center() - Vector(200.0, 150.0)); dp.drawSymbol(iDecoration); painter.popMatrix(); } painter.pushMatrix(); painter.transform(matrix()); painter.untransform(transformations()); if (iClip.countSubPaths()) { painter.push(); painter.newPath(); iClip.draw(painter); painter.addClipPath(); } for (const_iterator it = begin(); it != end(); ++it) (*it)->draw(painter); if (iClip.countSubPaths()) painter.pop(); painter.popMatrix(); } void Group::drawSimple(Painter &painter) const { painter.pushMatrix(); painter.transform(matrix()); painter.untransform(transformations()); if (iClip.countSubPaths()) { painter.push(); painter.newPath(); iClip.draw(painter); painter.addClipPath(); } for (const_iterator it = begin(); it != end(); ++it) (*it)->drawSimple(painter); if (iClip.countSubPaths()) painter.pop(); painter.popMatrix(); } void Group::addToBBox(Rect &box, const Matrix &m, bool cp) const { Matrix m1 = m * matrix(); Rect tbox; for (const_iterator it = begin(); it != end(); ++it) { (*it)->addToBBox(tbox, m1, cp); } // now clip to clipping path if (iClip.countSubPaths()) { Rect cbox; iClip.addToBBox(cbox, m1, false); tbox.clipTo(cbox); } box.addRect(tbox); } //! Return total pinning status of group and its elements. TPinned Group::pinned() const { return TPinned(Object::pinned() | iImp->iPinned); } double Group::distance(const Vector &v, const Matrix &m, double bound) const { double d = bound; double d1; Matrix m1 = m * matrix(); for (const_iterator it = begin(); it != end(); ++it) { if ((d1 = (*it)->distance(v, m1, d)) < d) d = d1; } return d; } void Group::snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { Matrix m1 = m * matrix(); for (const_iterator it = begin(); it != end(); ++it) (*it)->snapVtx(mouse, m1, pos, bound); } void Group::snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { Matrix m1 = m * matrix(); for (const_iterator it = begin(); it != end(); ++it) (*it)->snapCtl(mouse, m1, pos, bound); } void Group::snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const { Matrix m1 = m * matrix(); for (const_iterator it = begin(); it != end(); ++it) (*it)->snapBnd(mouse, m1, pos, bound); } void Group::checkStyle(const Cascade *sheet, AttributeSeq &seq) const { for (const_iterator it = begin(); it != end(); ++it) (*it)->checkStyle(sheet, seq); } //! Set clip path for this group. /*! Any previously set clip path is deleted. */ void Group::setClip(const Shape &clip) { iClip = clip; } //! Set link destination to use this group as a hyperlink. void Group::setUrl(String url) { iUrl = url; } //! Create private implementation. void Group::detach() { Imp *old = iImp; iImp = new Imp; iImp->iRefCount = 1; iImp->iPinned = old->iPinned; for (const_iterator it = old->iObjects.begin(); it != old->iObjects.end(); ++it) iImp->iObjects.push_back((*it)->clone()); } Attribute Group::getAttribute(Property prop) const noexcept { if (prop == EPropDecoration) return iDecoration; else return Object::getAttribute(prop); } //! Set attribute on all children. bool Group::setAttribute(Property prop, Attribute value) { if (prop == EPropPinned || prop == EPropTransformations) return Object::setAttribute(prop, value); if (prop == EPropDecoration) { auto old = iDecoration; iDecoration = value; return (old != iDecoration); } // all others are handled by elements themselves detach(); bool result = false; for (List::iterator it = iImp->iObjects.begin(); it != iImp->iObjects.end(); ++it) result |= (*it)->setAttribute(prop, value); return result; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelib/ipeutils.cpp0000644000175000017500000004005013561570220016630 0ustar otfriedotfried// -------------------------------------------------------------------- // Various utility classes // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeutils.h" #include "ipepage.h" #include "ipegroup.h" #include "ipereference.h" #include "ipeimage.h" #include "ipetext.h" #include "ipelet.h" #include using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::BitmapFinder \ingroup high \brief A visitor that recursively scans objects and collects all bitmaps. */ void BitmapFinder::scanPage(const Page *page) { for (int i = 0; i < page->count(); ++i) page->object(i)->accept(*this); } void BitmapFinder::visitGroup(const Group *obj) { for (Group::const_iterator it = obj->begin(); it != obj->end(); ++it) (*it)->accept(*this); } void BitmapFinder::visitImage(const Image *obj) { iBitmaps.push_back(obj->bitmap()); } // -------------------------------------------------------------------- /*! \class ipe::BBoxPainter \ingroup high \brief Paint objects using this painter to compute an accurate bounding box. The Object::bbox member function computes a bounding box useful for distance calculations and optimizations. To find a bounding box that is accurate for the actual \b drawn object, paint the object using a BBoxPainter, and retrieve the box with bbox. */ BBoxPainter::BBoxPainter(const Cascade *style) : Painter(style) { iClipBox.push_back(Rect()); // no clipping yet } void BBoxPainter::doPush() { iClipBox.push_back(iClipBox.back()); } void BBoxPainter::doPop() { iClipBox.pop_back(); } void BBoxPainter::doNewPath() { iPathBox.clear(); } void BBoxPainter::doMoveTo(const Vector &v) { iV = v; iPathBox.addPoint(iV); } void BBoxPainter::doLineTo(const Vector &v) { iV = v; iPathBox.addPoint(iV); } void BBoxPainter::doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3) { Bezier bez(iV, v1, v2, v3); Rect bb = bez.bbox(); iPathBox.addPoint(bb.bottomLeft()); iPathBox.addPoint(bb.topRight()); iV = v3; } void BBoxPainter::doDrawBitmap(Bitmap) { Rect box; box.addPoint(matrix() * Vector(0.0, 0.0)); box.addPoint(matrix() * Vector(0.0, 1.0)); box.addPoint(matrix() * Vector(1.0, 1.0)); box.addPoint(matrix() * Vector(1.0, 0.0)); box.clipTo(iClipBox.back()); iBBox.addRect(box); } void BBoxPainter::doDrawText(const Text *text) { // this is not correct if the text is transformed // as documented in the manual Rect box; box.addPoint(matrix() * Vector(0,0)); box.addPoint(matrix() * Vector(0, text->totalHeight())); box.addPoint(matrix() * Vector(text->width(), text->totalHeight())); box.addPoint(matrix() * Vector(text->width(), 0)); const TextPadding *pad = cascade()->findTextPadding(); box.addPoint(box.bottomLeft() - Vector(pad->iLeft, pad->iBottom)); box.addPoint(box.topRight() + Vector(pad->iRight, pad->iTop)); box.clipTo(iClipBox.back()); iBBox.addRect(box); } void BBoxPainter::doDrawPath(TPathMode mode) { double lw = pen().toDouble() / 2.0; if (!iPathBox.isEmpty()) { iPathBox.clipTo(iClipBox.back()); if (!iPathBox.isEmpty()) { iBBox.addPoint(iPathBox.bottomLeft() - Vector(lw, lw)); iBBox.addPoint(iPathBox.topRight() + Vector(lw, lw)); } } } void BBoxPainter::doAddClipPath() { if (iClipBox.back().isEmpty()) iClipBox.back() = iPathBox; else iClipBox.back().clipTo(iPathBox); } // -------------------------------------------------------------------- /*! \class ipe::A85Stream \ingroup high \brief Filter stream adding ASCII85 encoding. */ inline uint32_t a85word(const uint8_t *p) { return (p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3]; } inline void a85encode(uint32_t w, char *p) { p[4] = char(w % 85 + 33); w /= 85; p[3] = char(w % 85 + 33); w /= 85; p[2] = char(w % 85 + 33); w /= 85; p[1] = char(w % 85 + 33); p[0] = char(w / 85 + 33); } A85Stream::A85Stream(Stream &stream) : iStream(stream) { iN = 0; iCol = 0; } void A85Stream::putChar(char ch) { iCh[iN++] = ch; if (iN == 4) { // encode and write uint32_t w = a85word(iCh); if (w == 0) { iStream.putChar('z'); ++iCol; } else { char buf[6]; buf[5] = '\0'; a85encode(w, buf); iStream.putCString(buf); iCol += 5; } if (iCol > 70) { iStream.putChar('\n'); iCol = 0; } iN = 0; } } void A85Stream::close() { if (iN) { for (int k = iN; k < 4; ++k) iCh[k] = 0; uint32_t w = a85word(iCh); char buf[6]; a85encode(w, buf); buf[iN + 1] = '\0'; iStream.putCString(buf); } iStream.putCString("~>\n"); iStream.close(); } // -------------------------------------------------------------------- /*! \class ipe::Base64Stream \ingroup high \brief Filter stream adding Base64 encoding. */ static const char base64letter[65] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; inline uint32_t base64word(const uint8_t *p) { return (p[0] << 16) | (p[1] << 8) | p[2]; } inline void base64encode(uint32_t w, char *p) { p[4] = '\0'; p[3] = base64letter[w % 64]; w >>= 6; p[2] = base64letter[w % 64]; w >>= 6; p[1] = base64letter[w % 64]; w >>= 6; p[0] = base64letter[w % 64]; } Base64Stream::Base64Stream(Stream &stream) : iStream(stream) { iN = 0; iCol = 0; } void Base64Stream::putChar(char ch) { iCh[iN++] = ch; if (iN == 3) { // encode and write uint32_t w = base64word(iCh); char buf[5]; base64encode(w, buf); iStream.putCString(buf); iCol += 4; if (iCol > 70) { iStream.putChar('\n'); iCol = 0; } iN = 0; } } void Base64Stream::close() { if (iN) { for (int k = iN; k < 3; ++k) iCh[k] = 0; uint32_t w = base64word(iCh); char buf[5]; base64encode(w, buf); for (int k = iN + 1; k < 4; ++k) buf[k] = '='; iStream.putCString(buf); } iStream.putCString("\n"); iStream.close(); } // -------------------------------------------------------------------- /*! \class ipe::A85Source \ingroup high \brief Filter source adding ASCII85 decoding. */ A85Source::A85Source(DataSource &source) : iSource(source) { iEof = false; iN = 0; // number of characters buffered iIndex = 0; // next character to return } int A85Source::getChar() { if (iIndex < iN) return uint8_t(iBuf[iIndex++]); if (iEof) return EOF; int ch; do { ch = iSource.getChar(); } while (ch == '\n' || ch == '\r' || ch == ' '); if (ch == '~' || ch == EOF) { iEof = true; iN = 0; // no more data, immediate EOF return EOF; } iIndex = 1; iN = 4; if (ch == 'z') { iBuf[0] = iBuf[1] = iBuf[2] = iBuf[3] = 0; return uint8_t(iBuf[0]); } int c[5]; c[0] = ch; for (int k = 1; k < 5; ++k) { do { c[k] = iSource.getChar(); } while (c[k] == '\n' || c[k] == '\r' || c[k] == ' '); if (c[k] == '~' || c[k] == EOF) { iN = k - 1; iEof = true; break; } } for (int k = iN + 1; k < 5; ++k) c[k] = 0x21 + 84; uint32_t t = 0; for (int k = 0; k < 5; ++k) t = t * 85 + (c[k] - 0x21); for (int k = 3; k >= 0; --k) { iBuf[k] = char(t & 0xff); t >>= 8; } return iBuf[0]; }; // -------------------------------------------------------------------- /*! \class ipe::Base64Source \ingroup high \brief Filter source adding Base64 decoding. */ static signed char base64_value[] = { 62, -1, -1, -1, 63, // 2b..2f 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, -1, -1, -1, 0, -1, -1, // 30..3f -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, // 40..4f 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -1, -1, -1, -1, -1, // 50..5f -1, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, // 60..6f 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, // 70..7a }; inline bool base64illegal(int ch) { return (ch < '+' || ch > 'z' || base64_value[ch - '+'] < 0); } inline int base64value(int ch) { return base64_value[ch - '+']; } Base64Source::Base64Source(DataSource &source) : iSource(source) { iEof = false; iIndex = 0; // buffer empty iBufLen = 0; } int Base64Source::getChar() { if (iEof) return EOF; if (iIndex < iBufLen) return uint8_t(iBuf[iIndex++]); char buf[4]; for (int i = 0; i < 4; ++i) { int ch; do { ch = iSource.getChar(); } while (ch == '\n' || ch == '\r' || ch == ' '); // non-base64 characters terminate stream if (ch == EOF || base64illegal(ch)) { iEof = true; // no more data, immediate EOF return EOF; } buf[i] = ch; } uint32_t w = base64value(buf[0]) << 18; w |= (base64value(buf[1]) << 12); w |= (base64value(buf[2]) << 6); w |= base64value(buf[3]); iBuf[0] = (w >> 16) & 0xff; iBuf[1] = (w >> 8) & 0xff; iBuf[2] = w & 0xff; iBufLen = 3; if (buf[3] == '=') { --iBufLen; if (buf[2] == '=') --iBufLen; } iIndex = 1; return uint8_t(iBuf[0]); }; // -------------------------------------------------------------------- /*! \class ipe::DeflateStream \ingroup high \brief Filter stream adding flate compression. */ struct DeflateStream::Private { z_stream iFlate; }; DeflateStream::DeflateStream(Stream &stream, int level) : iStream(stream), iIn(0x400), iOut(0x400) // create buffers { iPriv = new Private; z_streamp z = &iPriv->iFlate; z->zalloc = nullptr; z->zfree = nullptr; z->opaque = nullptr; int err = ::deflateInit(z, level); if (err != Z_OK) { ipeDebug("deflateInit returns error %d", err); assert(false); } iN = 0; } DeflateStream::~DeflateStream() { if (iPriv) { z_streamp z = &iPriv->iFlate; ::deflateEnd(z); delete iPriv; } } void DeflateStream::putChar(char ch) { iIn[iN++] = ch; if (iN < iIn.size()) return; // compress and write z_streamp z = &iPriv->iFlate; z->next_in = (Bytef *) iIn.data(); z->avail_in = iIn.size(); while (z->avail_in) { z->next_out = (Bytef *) iOut.data(); z->avail_out = iOut.size(); int err = ::deflate(z, Z_NO_FLUSH); if (err != Z_OK) { ipeDebug("deflate returns error %d", err); assert(false); } // save output iStream.putRaw(iOut.data(), z->next_out - (Bytef *) iOut.data()); } iN = 0; } void DeflateStream::close() { // compress and write remaining data z_streamp z = &iPriv->iFlate; z->next_in = (Bytef *) iIn.data(); z->avail_in = iN; int err; do { z->next_out = (Bytef *) iOut.data(); z->avail_out = iOut.size(); err = ::deflate(z, Z_FINISH); if (err != Z_OK && err != Z_STREAM_END) { ipeDebug("deflate returns error %d", err); assert(false); } iStream.putRaw(iOut.data(), z->next_out - (Bytef *) iOut.data()); } while (err == Z_OK); err = ::deflateEnd(z); if (err != Z_OK) { ipeDebug("deflateEnd returns error %d", err); assert(false); } delete iPriv; iPriv = nullptr; // make sure no more writing possible iStream.close(); } //! Deflate a buffer in a single run. /*! The returned buffer may be larger than necessary: \a deflatedSize is set to the number of bytes actually used. */ Buffer DeflateStream::deflate(const char *data, int size, int &deflatedSize, int compressLevel) { uLong dfsize = uLong(size * 1.001 + 13); Buffer deflatedData(dfsize); int err = ::compress2((Bytef *) deflatedData.data(), &dfsize, (const Bytef *) data, size, compressLevel); if (err != Z_OK) { ipeDebug("Zlib compress2 returns errror %d", err); assert(false); } deflatedSize = dfsize; return deflatedData; } // -------------------------------------------------------------------- /*! \class ipe::InflateSource \ingroup high \brief Filter source adding flate decompression. */ struct InflateSource::Private { z_stream iFlate; }; InflateSource::InflateSource(DataSource &source) : iSource(source), iIn(0x400), iOut(0x400) { iPriv = new Private; z_streamp z = &iPriv->iFlate; z->zalloc = nullptr; z->zfree = nullptr; z->opaque = nullptr; fillBuffer(); int err = ::inflateInit(z); if (err != Z_OK) { ipeDebug("inflateInit returns error %d", err); delete iPriv; iPriv = nullptr; // set EOF return; } iP = iOut.data(); z->next_out = (Bytef *) iP; } InflateSource::~InflateSource() { if (iPriv) { z_streamp z = &iPriv->iFlate; ::inflateEnd(z); delete iPriv; } } void InflateSource::fillBuffer() { char *p = iIn.data(); char *p1 = iIn.data() + iIn.size(); z_streamp z = &iPriv->iFlate; z->next_in = (Bytef *) p; z->avail_in = 0; while (p < p1) { int ch = iSource.getChar(); if (ch == EOF) return; *p++ = char(ch); z->avail_in++; } } //! Get one more character, or EOF. int InflateSource::getChar() { if (!iPriv) return EOF; z_streamp z = &iPriv->iFlate; if (iP < (char *) z->next_out) return uint8_t(*iP++); // next to decompress some data if (z->avail_in == 0) fillBuffer(); if (z->avail_in > 0) { // data is available z->next_out = (Bytef *) iOut.data(); z->avail_out = iOut.size(); int err = ::inflate(z, Z_NO_FLUSH); if (err != Z_OK && err != Z_STREAM_END) { ipeDebug("inflate returns error %d", err); ::inflateEnd(z); delete iPriv; iPriv = nullptr; // set EOF return EOF; } iP = iOut.data(); if (iP < (char *) z->next_out) return uint8_t(*iP++); // didn't get any new data, must be EOF } // fillBuffer didn't get any data, must be EOF, so we are done ::inflateEnd(z); delete iPriv; iPriv = nullptr; return EOF; } // -------------------------------------------------------------------- /*! \defgroup ipelet The Ipelet interface \brief Implementation of Ipe plugins. Ipelets are dynamically loaded plugins for Ipe written in Lua. The Ipelet class makes it easy for ipelet authors to write ipelets in C++ without using Lua's C API. They only need to provide some boilerplate Lua code to define the labels and functions of the ipelet, and use the Lua function "loadIpelet" to load a DLL containing a C++ class derived from Ipelet. The run() method of this class can then be called from Lua. The C++ code has access to services provided by Ipe through an IpeletHelper object. Ipelet derived classes are restricted to operate on the current page of the document, and cannot modify the StyleSheet or other properties of the document. If you wish to write an ipelet doing this, you need to work in Lua (or create a C++ library using the Lua C API). */ /*! \class ipe::Ipelet \ingroup ipelet \brief Abstract base class for Ipelets. */ //! Pure virtual destructor. Ipelet::~Ipelet() { // nothing } // -------------------------------------------------------------------- /*! \class ipe::IpeletHelper \ingroup ipelet \brief Service provider for Ipelets. C++ Ipelets can ask Ipe to perform various services and request information using this class. */ //! Pure virtual destructor. IpeletHelper::~IpeletHelper() { // nothing } // -------------------------------------------------------------------- ipe-7.2.13/src/ipeextract/0000755000175000017500000000000013561570220015173 5ustar otfriedotfriedipe-7.2.13/src/ipeextract/ipeextract.cpp0000644000175000017500000002551513561570220020057 0ustar otfriedotfried// -------------------------------------------------------------------- // ipeextract // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipexml.h" #include "ipeutils.h" #include "ipepdfparser.h" #include using namespace ipe; // --------------------------------------------------------------------- enum TFormat {EXml, EPdf, EEps, EIpe5, EUnknown}; String readLine(DataSource &source) { String s; int ch = source.getChar(); while (ch != EOF && ch != '\n') { s += char(ch); ch = source.getChar(); } return s; } //! Determine format of file in \a source. TFormat fileFormat(DataSource &source) { String s1 = readLine(source); String s2 = readLine(source); if (s1.substr(0, 5) == " tag if (lt && iCh == 'b') { String tag; while (isTagChar(iCh)) { tag += char(iCh); fputc(iCh, iOut); getChar(); } // at char after tag if (tag == "bitmap" && !parseBitmap()) return false; } } return true; } // write out attributes, but drop 'pdfObject' void StreamParser::writeAttributes(const XmlAttributes &attr) { for (XmlAttributes::const_iterator it = attr.begin(); it != attr.end(); ++it) if (it->first != "pdfObject") fprintf(iOut, " %s=\"%s\"", it->first.z(), it->second.z()); fprintf(iOut, ">\n"); } static void writeBits(FILE *out, Buffer bits) { const char *data = bits.data(); const char *fin = data + bits.size(); int col = 0; while (data != fin) { fprintf(out, "%02x", (*data++ & 0xff)); if (++col == 36) { fputc('\n', out); col = 0; } } if (col > 0) fputc('\n', out); } bool StreamParser::parseBitmap() { XmlAttributes attr; if (!parseAttributes(attr)) return false; String objNumStr; if (attr.slash() && attr.has("pdfObject", objNumStr)) { Lex lex(objNumStr); Buffer bits = image(lex.getInt()); Buffer alpha; lex.skipWhitespace(); if (!lex.eos()) { alpha = image(lex.getInt()); fprintf(iOut, " alphaLength=\"%d\"", alpha.size()); } fprintf(iOut, " length=\"%d\"", bits.size()); writeAttributes(attr); writeBits(iOut, bits); if (alpha.size() > 0) writeBits(iOut, alpha); fprintf(iOut, "\n"); } else { // just write out attributes writeAttributes(attr); } return true; } // -------------------------------------------------------------------- class StreamParserPdf : public StreamParser { public: explicit StreamParserPdf(PdfFile &loader, DataSource &source, std::FILE *out) : StreamParser(source, out), iLoader(loader) { /* nothing */ } virtual Buffer image(int objNum); private: PdfFile &iLoader; }; Buffer StreamParserPdf::image(int objNum) { const PdfObj *obj = iLoader.object(objNum); if (!obj || !obj->dict() || obj->dict()->stream().size() == 0) return Buffer(); return obj->dict()->stream(); } // -------------------------------------------------------------------- class PsSource : public DataSource { public: PsSource(DataSource &source) : iSource(source) { /* nothing */ } bool skipToXml(); String readLine(); Buffer image(int index) const; int getNext() const; inline bool deflated() const { return iDeflated; } virtual int getChar(); private: DataSource &iSource; std::vector iImages; bool iEos; bool iDeflated; }; int PsSource::getChar() { int ch = iSource.getChar(); if (ch == '\n') iSource.getChar(); // remove '%' return ch; } String PsSource::readLine() { String s; int ch = iSource.getChar(); while (ch != EOF && ch != '\n') { s += char(ch); ch = iSource.getChar(); } iEos = (ch == EOF); return s; } Buffer PsSource::image(int index) const { if (1 <= index && index <= int(iImages.size())) return iImages[index - 1]; else return Buffer(); } bool PsSource::skipToXml() { iDeflated = false; String s1 = readLine(); String s2 = readLine(); if (s1.substr(0, 11) != "%!PS-Adobe-" || s2.substr(0, 11) != "%%Creator: ") return false; if (s2.substr(11, 6) == "Ipelib") { // the 'modern' file format of Ipe 6.0 preview 17 and later do { s1 = readLine(); if (s1.substr(0, 17) == "%%BeginIpeImage: ") { Lex lex(s1.substr(17)); int num, len; lex >> num >> len; if (num != int(iImages.size() + 1)) return false; (void) readLine(); // skip 'image' Buffer buf(len); A85Source a85(iSource); char *p = buf.data(); char *p1 = p + buf.size(); while (p < p1) { int ch = a85.getChar(); if (ch == EOF) return false; *p++ = char(ch); } iImages.push_back(buf); } } while (!iEos && s1.substr(0, 13) != "%%BeginIpeXml"); iDeflated = (s1.substr(13, 14) == ": /FlateDecode"); } else { // the 'old' file format generated through pdftops do { s1 = readLine(); } while (!iEos && s1.substr(0, 10) != "%%EndSetup"); } if (iEos) return false; (void) iSource.getChar(); // skip '%' before return true; } // -------------------------------------------------------------------- class StreamParserPs : public StreamParser { public: explicit StreamParserPs(PsSource &loader, DataSource &source, std::FILE *out) : StreamParser(source, out), iLoader(loader) { /* nothing */ } virtual Buffer image(int objNum); private: PsSource &iLoader; }; Buffer StreamParserPs::image(int objNum) { return iLoader.image(objNum); } // -------------------------------------------------------------------- static bool extractPs(DataSource &source, std::FILE *out) { PsSource psSource(source); if (!psSource.skipToXml()) { fprintf(stderr, "Could not find XML stream.\n"); return false; } if (psSource.deflated()) { A85Source a85(psSource); InflateSource source(a85); StreamParserPs parser(psSource, source, out); return parser.parse(); } else { StreamParserPs parser(psSource, psSource, out); return parser.parse(); } return false; } static bool extractPdf(DataSource &source, std::FILE *out) { PdfFile loader; if (!loader.parse(source)) { fprintf(stderr, "Error parsing PDF file - probably not an Ipe file.\n"); return false; } // try ancient format version first (early previews of Ipe 6.0) const PdfObj *obj = loader.catalog()->get("Ipe", &loader); // otherwise try most recent format (>= 7.2.11) if (!obj) { obj = loader.catalog()->get("PieceInfo", &loader); if (obj && obj->dict()) { obj = obj->dict()->get("Ipe", &loader); if (obj && obj->dict()) obj = obj->dict()->get("Private", &loader); } } if (!obj) obj = loader.object(1); if (!obj || !obj->dict()) { fprintf(stderr, "Input file does not contain an Ipe XML stream.\n"); return false; } const PdfObj *type = obj->dict()->get("Type", nullptr); if (!type || !type->name() || type->name()->value() != "Ipe") { fprintf(stderr, "Input file does not contain an Ipe XML stream.\n"); return false; } Buffer buffer = obj->dict()->stream(); BufferSource xml(buffer); if (obj->dict()->deflated()) { InflateSource xml1(xml); StreamParserPdf parser(loader, xml1, out); return parser.parse(); } else { StreamParserPdf parser(loader, xml, out); return parser.parse(); } } // -------------------------------------------------------------------- static void usage() { fprintf(stderr, "Usage: ipeextract ( | ) []\n" "Ipeextract extracts the XML stream from a PDF or Postscript file\n" "generated by any version of Ipe 6 or Ipe 7.\n" ); exit(1); } int main(int argc, char *argv[]) { Platform::initLib(IPELIB_VERSION); // ensure one or two arguments if (argc != 2 && argc != 3) usage(); const char *src = argv[1]; String dst; if (argc == 3) { dst = argv[2]; } else { String s = src; if (s.right(4) == ".pdf" || s.right(4) == ".eps") dst = s.left(s.size() - 3) + "xml"; else dst = s + ".xml"; } std::FILE *fd = Platform::fopen(src, "rb"); if (!fd) { std::fprintf(stderr, "Could not open '%s'\n", src); exit(1); } FileSource source(fd); TFormat format = fileFormat(source); if (format == EXml) { fprintf(stderr, "Input file is already in XML format.\n"); } else if (format == EIpe5) { fprintf(stderr, "Input file is in Ipe5 format.\n" "Run 'ipe5toxml' to convert it to XML format.\n"); } else { std::rewind(fd); std::FILE *out = Platform::fopen(dst.z(), "wb"); if (!out) { fprintf(stderr, "Could not open '%s' for writing.\n", dst.z()); } else { bool res = (format == EPdf) ? extractPdf(source, out) : extractPs(source, out); if (!res) fprintf(stderr, "Error during extraction of XML stream.\n"); std::fclose(out); } } std::fclose(fd); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipeextract/Makefile0000644000175000017500000000134213561570220016633 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for Ipeextract # -------------------------------------------------------------------- OBJDIR = $(BUILDDIR)/obj/ipeextract include ../common.mak TARGET = $(call exe_target,ipeextract) CPPFLAGS += -I../include LIBS += -L$(buildlib) -lipe all: $(TARGET) sources = ipeextract.cpp $(TARGET): $(objects) $(MAKE_BINDIR) $(CXX) $(LDFLAGS) -o $@ $^ $(LIBS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPEBINDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPEBINDIR) # -------------------------------------------------------------------- ipe-7.2.13/src/common.mak0000644000175000017500000001730313561570220015011 0ustar otfriedotfried# -*- makefile -*- # -------------------------------------------------------------------- # # Building Ipe --- common definitions # # -------------------------------------------------------------------- # Are we compiling for Windows? For Mac OS X? ifdef COMSPEC WIN32 = 1 IPEBUNDLE = 1 IPEUI = WIN32 else ifdef IPECROSS WIN32 = 1 IPEBUNDLE = 1 IPEUI = WIN32 else UNAME = $(shell uname) ifeq "$(UNAME)" "Darwin" MACOS = 1 IPEUI = COCOA IPECONFIGMAK ?= macos.mak else IPEUI ?= QT ifdef IPESNAPCRAFT IPECONFIGMAK ?= snapcraft.mak else ifdef IPEAPPIMAGE IPECONFIGMAK ?= snapcraft.mak else IPECONFIGMAK ?= config.mak endif endif endif # -------------------------------------------------------------------- # IPESRCDIR is Ipe's top "src" directory # if 'common.mak' is included on a different level than a subdirectory # of "src", then IPESRCDIR must be set before including 'common.mak'. IPESRCDIR ?= .. # -------------------------------------------------------------------- # Read configuration options (not used on Win32) ifndef WIN32 include $(IPESRCDIR)/$(IPECONFIGMAK) BUILDDIR = $(IPESRCDIR)/../build endif # -------------------------------------------------------------------- # set variables that depend on UI library # -------------------- QT -------------------- ifeq ($(IPEUI),QT) CPPFLAGS += -DIPEUI_QT # Qt5 requires -fPIC depending on its own compilation settings. CPPFLAGS += -fPIC CXXFLAGS += -fPIC DLL_CFLAGS = -fPIC IPEUI_QT := 1 UI_CFLAGS = $(QT_CFLAGS) UI_LIBS = $(QT_LIBS) moc_sources = $(addprefix moc_, $(subst .h,.cpp,$(moc_headers))) all_sources = $(sources) $(qt_sources) objects = $(addprefix $(OBJDIR)/, $(subst .cpp,.o,$(all_sources) \ $(moc_sources))) # -------------------- WIN32 -------------------- else ifeq ($(IPEUI), WIN32) CPPFLAGS += -DIPEUI_WIN32 IPEUI_WIN32 := 1 UI_CFLAGS := UI_LIBS := -lcomctl32 -lcomdlg32 -lgdi32 -lgdiplus all_sources = $(sources) $(win_sources) objects = $(addprefix $(OBJDIR)/, $(subst .cpp,.o,$(all_sources))) # -------------------- COCOA -------------------- else ifeq ($(IPEUI), COCOA) CPPFLAGS += -DIPEUI_COCOA IPEUI_COCOA := 1 CXXFLAGS += -mmacosx-version-min=10.10 -Wdeprecated-declarations LDFLAGS += -mmacosx-version-min=10.10 UI_CFLAGS = $(IPEOBJCPP) UI_LIBS = -framework Cocoa -framework AppKit \ -framework ApplicationServices all_sources = $(sources) $(cocoa_sources) objects = $(addprefix $(OBJDIR)/, $(subst .cpp,.o,$(all_sources))) # -------------------- GTK -------------------- else ifeq ($(IPEUI), GTK) CPPFLAGS += -DIPEUI_GTK -DGDK_DISABLE_DEPRECATED -DGTK_DISABLE_DEPRECATED IPEUI_GTK := 1 GTK_CFLAGS ?= $(shell pkg-config --cflags gtk+-2.0) GTK_LIBS ?= $(shell pkg-config --libs gtk+-2.0) UI_CFLAGS = $(GTK_CFLAGS) UI_LIBS = $(GTK_LIBS) all_sources = $(sources) $(gtk_sources) BUILDDIR = $(IPESRCDIR)/../gtkbuild objects = $(addprefix $(OBJDIR)/, $(subst .cpp,.o,$(all_sources))) else error("Unknown IPEUI selected") endif CXXFLAGS += -Wall ifdef IPESTRICT CXXFLAGS += -Wsign-compare -Wzero-as-null-pointer-constant -Werror -DIPESTRICT CPPFLAGS += -std=c++17 else CPPFLAGS += -std=c++14 endif ifdef IPECXX CXX = $(IPECXX) endif DEPEND ?= $(OBJDIR)/depend.mak .PHONY: clean .PHONY: install .PHONY: all # Variables depending on platform ifdef WIN32 # -------------------- WIN32 -------------------- # Set just in case user has environment variables set IPEDOCDIR := IPEICONDIR := IPECURL := 1 IPE_NO_IPELIB_VERSION_CHECK := 1 CPPFLAGS += -DWIN32 -DUNICODE -D_UNICODE DLL_LDFLAGS += -shared PLUGIN_LDFLAGS += -shared DL_LIBS := JPEG_CFLAGS := JPEG_LIBS := -lgdiplus PNG_CFLAGS := PNG_LIBS := -lgdiplus buildlib = $(BUILDDIR)/bin buildbin = $(BUILDDIR)/bin buildipelets = $(BUILDDIR)/ipelets exe_target = $(BUILDDIR)/bin/$1.exe dll_target = $(buildlib)/$1.dll soname = dll_symlinks = install_symlinks = ipelet_target = $(BUILDDIR)/ipelets/$1.dll ifeq ($(IPECROSS),i686) BUILDDIR = $(IPESRCDIR)/../mingw32 else BUILDDIR = $(IPESRCDIR)/../mingw64 endif CXXFLAGS += -g -O2 ifdef IPECROSS # --------------- Cross compiling with Mingw-w64 --------------- # http://mingw-w64.sourceforge.net/ CXX = $(IPECROSS)-w64-mingw32-g++ CC = $(IPECROSS)-w64-mingw32-gcc STRIP_TARGET = $(IPECROSS)-w64-mingw32-strip $(TARGET) WINDRES = $(IPECROSS)-w64-mingw32-windres IPEDEPS ?= /sw/mingwlibs-$(IPECROSS) else # --------------- Compiling with Mingw-w64 under Windows --------------- WINDRES = windres.exe CXXFLAGS += -g -O2 STRIP_TARGET = strip $(TARGET) IPEDEPS ?= /mingwlibs endif ZLIB_CFLAGS := -I$(IPEDEPS)/include ZLIB_LIBS := -L$(IPEDEPS)/lib -lz FREETYPE_CFLAGS := -I$(IPEDEPS)/include/freetype2 \ -I$(IPEDEPS)/include FREETYPE_LIBS := -L$(IPEDEPS)/lib -lfreetype CAIRO_CFLAGS := -I$(IPEDEPS)/include/cairo CAIRO_LIBS := -L$(IPEDEPS)/lib -lcairo LUA_CFLAGS := -I$(IPEDEPS)/lua53/include LUA_LIBS := $(IPEDEPS)/lua53/lua53.dll CURL_CFLAGS := -DCURL_STATICLIB -I$(IPEDEPS)/include CURL_LIBS := -L$(IPEDEPS)/lib -lcurl -lcrypt32 -lz -lws2_32 else ifdef MACOS # -------------------- Mac OS X -------------------- CXXFLAGS += -g -Os IPEOBJCPP = -x objective-c++ -fobjc-arc DLL_LDFLAGS += -dynamiclib PLUGIN_LDFLAGS += -bundle DL_LIBS ?= -ldl ZLIB_CFLAGS ?= ZLIB_LIBS ?= -lz JPEG_CFLAGS ?= JPEG_LIBS ?= -framework ApplicationServices ifdef IPEBUNDLE IPELIBDIRINFO = @executable_path/../Frameworks BUNDLEDIR ?= $(BUILDDIR)/Ipe.app/Contents RESOURCEDIR = $(BUNDLEDIR)/Resources buildlib = $(BUNDLEDIR)/Frameworks buildbin = $(BUNDLEDIR)/MacOS buildipelets = $(RESOURCEDIR)/ipelets exe_target = $(BUNDLEDIR)/MacOS/$1 ipelet_target = $(RESOURCEDIR)/ipelets/$1.so IPEAPP = 1 else IPELIBDIRINFO ?= $(IPELIBDIR) buildlib = $(BUILDDIR)/lib exe_target = $(BUILDDIR)/bin/$1 ipelet_target = $(BUILDDIR)/ipelets/$1.so buildbin = $(BUILDDIR)/bin buildipelets = $(BUILDDIR)/ipelets endif soname = -Wl,-dylib_install_name,$(IPELIBDIRINFO)/lib$1.$(IPEVERS).dylib dll_target = $(buildlib)/lib$1.$(IPEVERS).dylib dll_symlinks = ln -sf lib$1.$(IPEVERS).dylib $(buildlib)/lib$1.dylib install_symlinks = ln -sf lib$1.$(IPEVERS).dylib \ $(INSTALL_ROOT)$(IPELIBDIR)/lib$1.dylib else # -------------------- Unix -------------------- CXXFLAGS += -g -O2 DLL_LDFLAGS += -shared PLUGIN_LDFLAGS += -shared soname = -Wl,-soname,lib$1.so.$(IPEVERS) dll_target = $(buildlib)/lib$1.so.$(IPEVERS) dll_symlinks = ln -sf lib$1.so.$(IPEVERS) $(buildlib)/lib$1.so install_symlinks = ln -sf lib$1.so.$(IPEVERS) \ $(INSTALL_ROOT)$(IPELIBDIR)/lib$1.so buildlib = $(BUILDDIR)/lib buildbin = $(BUILDDIR)/bin buildipelets = $(BUILDDIR)/ipelets exe_target = $(BUILDDIR)/bin/$1 ipelet_target = $(BUILDDIR)/ipelets/$1.so endif endif # Macros INSTALL_DIR = install -d INSTALL_FILES = install -m 0644 INSTALL_SCRIPTS = install -m 0755 INSTALL_PROGRAMS = install -m 0755 MAKE_BINDIR = mkdir -p $(buildbin) MAKE_LIBDIR = mkdir -p $(buildlib) MAKE_IPELETDIR = mkdir -p $(buildipelets) MAKE_DEPEND = \ mkdir -p $(OBJDIR); \ echo "" > $@; \ for f in $(all_sources); do \ $(CXX) -MM -MT $(OBJDIR)/$${f%%.cpp}.o $(CPPFLAGS) $$f >> $@; done # The rules $(OBJDIR)/%.o: %.cpp @echo Compiling $( ipe-7.2.13/src/ipe/appui_gtk.cpp0000644000175000017500000002134013561570220016267 0ustar otfriedotfried// -------------------------------------------------------------------- // AppUi for GTK // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "appui_gtk.h" #include "ipecanvas_gtk.h" // #include "controls_qt.h" #include "ipelua.h" // for version info only #include "ipefonts.h" #include #include #include using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- static String change_mnemonic(const char *s) { int n = strlen(s); String r; int i = 0; while (i < n) { if (s[i] == '&') { if (i+1 < n && s[i+1] == '&') { r += '&'; ++i; // extra } else r += '_'; } else r += s[i]; ++i; } return r; } void AppUi::addRootMenu(int id, const char *name) { iRootMenu[id] = gtk_menu_item_new_with_mnemonic(change_mnemonic(name).z()); iSubMenu[id] = gtk_menu_new(); } void AppUi::menuitem_cb(GtkWidget *item, gpointer data) { AppUi *ui = (AppUi *) g_object_get_data(G_OBJECT(item), "ipe-appui"); gint idx = GPOINTER_TO_INT(data); ui->action(ui->iActions[idx].name); } void AppUi::addItem(GtkMenuShell *shell, const char *title, const char *name) { if (!title) { GtkWidget *item = gtk_separator_menu_item_new(); gtk_menu_shell_append(shell, item); gtk_widget_show(item); return; } bool checkable = (shell == GTK_MENU_SHELL(iSubMenu[EModeMenu]) || String(name).find('|') >= 0); if (name[0] == '*') { checkable = true; name = name + 1; } GtkWidget *item = checkable ? gtk_check_menu_item_new_with_mnemonic(change_mnemonic(title).z()) : gtk_menu_item_new_with_mnemonic(change_mnemonic(title).z()); SAction s; s.name = String(name); s.menuItem = item; iActions.push_back(s); g_object_set_data(G_OBJECT(item), "ipe-appui", this); gtk_menu_shell_append(shell, item); g_signal_connect(item, "activate", G_CALLBACK(menuitem_cb), GINT_TO_POINTER(iActions.size() - 1)); gtk_widget_show(item); } void AppUi::addItem(int id, const char *title, const char *name) { GtkMenuShell *shell = GTK_MENU_SHELL(iSubMenu[id]); addItem(shell, title, name); } static GtkWidget *submenu = 0; static GtkWidget *submenuitem = 0; static int submenuId = 0; void AppUi::startSubMenu(int id, const char *name) { submenuId = id; submenu = gtk_menu_new(); submenuitem = gtk_menu_item_new_with_mnemonic(change_mnemonic(name).z()); } void AppUi::addSubItem(const char *title, const char *name) { GtkMenuShell *shell = GTK_MENU_SHELL(submenu); addItem(shell, title, name); } MENUHANDLE AppUi::endSubMenu() { gtk_menu_item_set_submenu(GTK_MENU_ITEM(submenuitem), submenu); gtk_widget_show(submenuitem); GtkMenuShell *menu = GTK_MENU_SHELL(iSubMenu[submenuId]); gtk_menu_shell_append(menu, submenuitem); return GTK_MENU(submenu); } // -------------------------------------------------------------------- AppUi::AppUi(lua_State *L0, int model) : AppUiBase(L0, model) { iWindow = gtk_window_new(GTK_WINDOW_TOPLEVEL); g_signal_connect(iWindow, "delete-event", G_CALLBACK(gtk_main_quit), NULL); iAccelGroup = gtk_accel_group_new(); gtk_window_add_accel_group(GTK_WINDOW(iWindow), iAccelGroup); buildMenus(); GtkWidget *menu_bar = gtk_menu_bar_new(); GtkWidget *vbox = gtk_vbox_new(FALSE, 0); gtk_container_add(GTK_CONTAINER(iWindow), vbox); gtk_widget_show(vbox); gtk_box_pack_start(GTK_BOX(vbox), menu_bar, FALSE, FALSE, 0); gtk_widget_show(menu_bar); for (int i = 0; i < ENumMenu; ++i) { gtk_widget_show(iRootMenu[i]); gtk_menu_item_set_submenu(GTK_MENU_ITEM(iRootMenu[i]), iSubMenu[i]); gtk_menu_shell_append(GTK_MENU_SHELL(menu_bar), iRootMenu[i]); } Canvas *canvas = new Canvas(iWindow); gtk_box_pack_start(GTK_BOX(vbox), canvas->window(), TRUE, TRUE, 0); gtk_widget_show(canvas->window()); iCanvas = canvas; iCanvas->setObserver(this); iStatusBar = gtk_statusbar_new(); iStatusBarContextid = gtk_statusbar_get_context_id(GTK_STATUSBAR(iStatusBar), "explain"); iMousePosition = gtk_label_new(0); iResolution = gtk_label_new(0); GtkBox *sb = GTK_BOX(gtk_statusbar_get_message_area(GTK_STATUSBAR(iStatusBar))); gtk_box_pack_end(sb, iResolution, FALSE, FALSE, 0); gtk_box_pack_end(sb, iMousePosition, FALSE, FALSE, 0); gtk_widget_show(iResolution); gtk_widget_show(iMousePosition); gtk_box_pack_end(GTK_BOX(vbox), iStatusBar, FALSE, FALSE, 0); gtk_widget_show(iStatusBar); } AppUi::~AppUi() { ipeDebug("AppUi C++ destructor"); // TODO: destroy iWindow or not? } // -------------------------------------------------------------------- void AppUi::resetCombos() { // TODO } void AppUi::addCombo(int sel, String s) { // TODO } void AppUi::addComboColors(AttributeSeq &sym, AttributeSeq &abs) { // TODO } void AppUi::setComboCurrent(int sel, int idx) { // TODO } void AppUi::setButtonColor(int sel, Color color) { // TODO } void AppUi::setLayers(const Page *page, int view) { // TODO } void AppUi::setZoom(double zoom) { char s[32]; sprintf(s, "(%dppi)", int(72.0 * zoom)); iCanvas->setZoom(zoom); gtk_label_set_text(GTK_LABEL(iResolution), s); } void AppUi::setPathView(const AllAttributes &all, Cascade *sheet) { // TODO } void AppUi::setCheckMark(String name, Attribute a) { } void AppUi::setActionsEnabled(bool mode) { } void AppUi::setNumbers(String vno, bool vm, String pno, bool pm) { } void AppUi::setNotes(String notes) { } // only used for snapXXX and grid_size bool AppUi::actionState(const char *name) { int idx = actionId(name); return (idx >= 0) ? gtk_check_menu_item_get_active(GTK_CHECK_MENU_ITEM(iActions[idx].menuItem)) : false; } // only used for snapXXX and grid_size void AppUi::setActionState(const char *name, bool value) { int idx = actionId(name); if (idx >= 0) gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(iActions[idx].menuItem), value); } void AppUi::setBookmarks(int no, const String *s) { // TODO } void AppUi::setToolVisible(int m, bool vis) { // TODO } // -------------------------------------------------------------------- int AppUi::actionId(const char *name) const { for (int i = 0; i < int(iActions.size()); ++i) { if (iActions[i].name == name) return i; } return -1; } WINID AppUi::windowId() { return iWindow; } void AppUi::closeWindow() { delete this; } void AppUi::explain(const char *s, int t) { gtk_statusbar_push(GTK_STATUSBAR(iStatusBar), iStatusBarContextid, s); } void AppUi::setWindowCaption(bool mod, const char *s) { // TODO: What is mod for? gtk_window_set_title(GTK_WINDOW(iWindow), s); } void AppUi::setMouseIndicator(const char *s) { gtk_label_set_text(GTK_LABEL(iMousePosition), s); } void AppUi::showWindow(int width, int height) { gtk_widget_set_size_request(GTK_WIDGET(iWindow), width, height); gtk_widget_show(iWindow); } int AppUi::setClipboard(lua_State *L) { const char *data = luaL_checkstring(L, 1); GtkClipboard *b = gtk_clipboard_get(GDK_SELECTION_CLIPBOARD); gtk_clipboard_set_text(b, data, -1); return 0; } int AppUi::clipboard(lua_State *L) { // TODO IMPLEMENT IMAGE GtkClipboard *b = gtk_clipboard_get(GDK_SELECTION_CLIPBOARD); char *data = gtk_clipboard_wait_for_text(b); if (data) { lua_pushstring(L, data); g_free(data); return 1; } return 0; } // -------------------------------------------------------------------- void AppUi::action(String name) { luaAction(name); } int AppUi::pageSorter(lua_State *L, Document *doc, int width, int height, int thumbWidth) { // TODO return 0; } AppUiBase *createAppUi(lua_State *L0, int model) { return new AppUi(L0, model); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/appui.cpp0000644000175000017500000005752413561570220015437 0ustar otfriedotfried// -------------------------------------------------------------------- // AppUi // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "appui.h" #include "tools.h" #include "ipelua.h" #include "ipecairopainter.h" using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- const char * const AppUiBase::selectorNames[] = { "stroke", "fill", "pen", "textsize", "markshape", "symbolsize", "gridsize", "anglesize", "view", "page", "viewmarked", "pagemarked" }; AppUiBase::AppUiBase(lua_State *L0, int model) { L = L0; iModel = model; isInkMode = false; iMouseIn = 0; // points iMouseFactor = 1.0; // scale 1:1 iCoordinatesFormat = "%g%s, %g%s"; lua_getglobal(L, "prefs"); lua_getfield(L, -1, "coordinates_format"); if (lua_isstring(L, -1)) { iCoordinatesFormat = lua_tolstring(L, -1, nullptr); } lua_pop(L, 1); // coordinates_format lua_getfield(L, -1, "width_notes_bookmarks"); if (lua_isnumber(L, -1)) { iWidthNotesBookmarks = lua_tointegerx(L, -1, nullptr); } lua_pop(L, 1); // width_notes_bookmarks iUiScale = 100; lua_getfield(L, -1, "ui_scale"); if (lua_isnumber(L, -1)) iUiScale = lua_tointegerx(L, -1, nullptr); lua_pop(L, 1); // ui_scale iToolbarScale = 100; lua_getfield(L, -1, "toolbar_scale"); if (lua_isnumber(L, -1)) iToolbarScale = lua_tointegerx(L, -1, nullptr); lua_pop(L, 1); // toolbar_scale iUiGap = 0; lua_getfield(L, -1, "ui_gap"); if (lua_isnumber(L, -1)) iUiGap = lua_tointegerx(L, -1, nullptr); lua_pop(L, 1); // ui_gap lua_getfield(L, -1, "mini_edit"); isMiniEdit = lua_toboolean(L, -1); lua_pop(L, 1); // mini_edit lua_getfield(L, -1, "left_dock_floats"); iLeftDockFloats = lua_toboolean(L, -1); lua_pop(L, 1); // left_dock_floats iScalings.push_back(1); lua_getfield(L, -1, "scale_factors"); if (lua_istable(L, -1)) { int n = lua_rawlen(L, -1); for (int i = 1; i <= n; ++i) { lua_rawgeti(L, -1, i); if (lua_isnumber(L, -1)) iScalings.push_back(lua_tointegerx(L, -1, nullptr)); lua_pop(L, 1); // number } } lua_pop(L, 2); // prefs, scale_factors } AppUiBase::~AppUiBase() { ipeDebug("AppUiBase C++ destructor"); luaL_unref(L, LUA_REGISTRYINDEX, iModel); // collect this model lua_gc(L, LUA_GCCOLLECT, 0); } // -------------------------------------------------------------------- void AppUiBase::buildMenus() { addRootMenu(EFileMenu, "&File"); addRootMenu(EEditMenu, "&Edit"); addRootMenu(EPropertiesMenu, "P&roperties"); addRootMenu(ESnapMenu, "&Snap"); addRootMenu(EModeMenu, "&Mode"); addRootMenu(EZoomMenu, "&Zoom"); addRootMenu(ELayerMenu, "&Layers"); addRootMenu(EViewMenu, "&Views"); addRootMenu(EPageMenu, "&Pages"); addRootMenu(EIpeletMenu, "&Ipelets"); addRootMenu(EHelpMenu, "&Help"); addItem(EFileMenu, "New Window", "new_window"); addItem(EFileMenu, "New", "new"); addItem(EFileMenu, "Open", "open"); addItem(EFileMenu, "Save", "save"); addItem(EFileMenu, "Save as", "save_as"); addItem(EFileMenu); addItem(EFileMenu, "Export as PNG", "export_png"); addItem(EFileMenu, "Export as EPS", "export_eps"); addItem(EFileMenu, "Export as SVG", "export_svg"); addItem(EFileMenu); addItem(EFileMenu, "Insert image", "insert_image"); addItem(EFileMenu); addItem(EFileMenu, "Automatically run Latex", "*auto_latex"); addItem(EFileMenu, "Run Latex", "run_latex"); addItem(EFileMenu); addItem(EFileMenu, "Close", "close"); addItem(EEditMenu, "Undo", "undo"); addItem(EEditMenu, "Redo", "redo"); addItem(EEditMenu); addItem(EEditMenu, "Cut", "cut"); addItem(EEditMenu, "Copy", "copy"); addItem(EEditMenu, "Paste", "paste"); addItem(EEditMenu, "Paste at cursor", "paste_at_cursor"); addItem(EEditMenu, "Delete", "delete"); addItem(EEditMenu); addItem(EEditMenu, "Group", "group"); addItem(EEditMenu, "Ungroup", "ungroup"); addItem(EEditMenu, "Front", "front"); addItem(EEditMenu, "Back", "back"); addItem(EEditMenu, "Forward", "forward"); addItem(EEditMenu, "Backward", "backward"); addItem(EEditMenu, "Just before", "before"); addItem(EEditMenu, "Just behind", "behind"); addItem(EEditMenu, "Duplicate", "duplicate"); addItem(EEditMenu, "Select all", "select_all"); addItem(EEditMenu); addItem(EEditMenu, "Pick properties", "pick_properties"); addItem(EEditMenu, "Apply properties", "apply_properties"); addItem(EEditMenu); addItem(EEditMenu, "Insert text box", "insert_text_box"); addItem(EEditMenu, "Change text width", "change_width"); addItem(EEditMenu, "Edit object", "edit"); addItem(EEditMenu, "Edit object as XML", "edit_as_xml"); addItem(EEditMenu); addItem(EEditMenu, "Edit group", "edit_group"); addItem(EEditMenu, "End group edit", "end_group_edit"); addItem(EEditMenu); addItem(EEditMenu, "Document properties", "document_properties"); addItem(EEditMenu, "Style sheets", "style_sheets"); addItem(EEditMenu, "Update style sheets", "update_style_sheets"); addItem(EEditMenu, "Check symbolic attributes", "check_style"); startSubMenu(EPropertiesMenu, "Pinned"); addSubItem("none", "pinned|none"); addSubItem("horizontal", "pinned|horizontal"); addSubItem("vertical", "pinned|vertical"); addSubItem("fixed", "pinned|fixed"); endSubMenu(); startSubMenu(EPropertiesMenu, "Transformations"); addSubItem("translations", "transformations|translations"); addSubItem("rigid motions", "transformations|rigid"); addSubItem("affine", "transformations|affine"); endSubMenu(); addItem(EPropertiesMenu); startSubMenu(EPropertiesMenu, "Minipage style", ESubmenuTextStyle); iTextStyleMenu = endSubMenu(); startSubMenu(EPropertiesMenu, "Label style", ESubmenuLabelStyle); iLabelStyleMenu = endSubMenu(); startSubMenu(EPropertiesMenu, "Horizontal alignment"); addSubItem("left", "horizontalalignment|left"); addSubItem("center", "horizontalalignment|hcenter"); addSubItem("right", "horizontalalignment|right"); endSubMenu(); startSubMenu(EPropertiesMenu, "Vertical alignment"); addSubItem("bottom", "verticalalignment|bottom"); addSubItem("baseline", "verticalalignment|baseline"); addSubItem("center", "verticalalignment|vcenter"); addSubItem("top", "verticalalignment|top"); endSubMenu(); startSubMenu(EPropertiesMenu, "Transformable text"); addSubItem("Yes", "transformabletext|true"); addSubItem("No", "transformabletext|false"); endSubMenu(); addItem(EModeMenu, "Select objects (with Shift: non-destructive)", "mode_select"); addItem(EModeMenu, "Translate objects (with Shift: horizontal/vertical)", "mode_translate"); addItem(EModeMenu, "Rotate objects", "mode_rotate"); addItem(EModeMenu, "Stretch objects (with Shift: scale objects)", "mode_stretch"); addItem(EModeMenu, "Shear objects", "mode_shear"); addItem(EModeMenu, "Move graph nodes", "mode_graph"); addItem(EModeMenu, "Pan the canvas", "mode_pan"); addItem(EModeMenu, "Shred objects", "mode_shredder"); addItem(EModeMenu); addItem(EModeMenu, "Text labels", "mode_label"); addItem(EModeMenu, "Mathematical symbols", "mode_math"); addItem(EModeMenu, "Paragraphs", "mode_paragraph"); addItem(EModeMenu, "Marks", "mode_marks"); addItem(EModeMenu, "Axis-parallel rectangles (with Shift: squares)", "mode_rectangles1"); addItem(EModeMenu, "Axis-parallel rectangles, by center (with Shift: squares)", "mode_rectangles2"); addItem(EModeMenu, "Rectangles (with Shift: squares)", "mode_rectangles3"); addItem(EModeMenu, "Parallelograms (with Shift: axis-parallel)", "mode_parallelogram"); addItem(EModeMenu, "Lines and polylines", "mode_lines"); addItem(EModeMenu, "Polygons", "mode_polygons"); addItem(EModeMenu, "Splines", "mode_splines"); addItem(EModeMenu, "Splinegons", "mode_splinegons"); addItem(EModeMenu, "Circular arcs (by center, right and left point)", "mode_arc1"); addItem(EModeMenu, "Circular arcs (by center, left and right point)", "mode_arc2"); addItem(EModeMenu, "Circular arcs (by 3 points)", "mode_arc3"); addItem(EModeMenu, "Circles (by center and radius)", "mode_circle1"); addItem(EModeMenu, "Circles (by diameter)", "mode_circle2"); addItem(EModeMenu, "Circles (by 3 points)", "mode_circle3"); addItem(EModeMenu, "Ink", "mode_ink"); // @ means the action can be used while drawing // * means the action is checkable (on/off) // Checkable actions work differently in Qt and Win32/Cocoa: // Qt already toggles the state // In Win32/Cocoa the action needs to toggle the state. addItem(ESnapMenu, "Snap to vertex", "@*snapvtx"); addItem(ESnapMenu, "Snap to control point", "@*snapctl"); addItem(ESnapMenu, "Snap to boundary", "@*snapbd"); addItem(ESnapMenu, "Snap to intersection", "@*snapint"); addItem(ESnapMenu, "Snap to grid", "@*snapgrid"); addItem(ESnapMenu, "Angular snap", "@*snapangle"); addItem(ESnapMenu, "Automatic snap", "@*snapauto"); addItem(ESnapMenu); startSubMenu(ESnapMenu, "Grid size", ESubmenuGridSize); iGridSizeMenu = endSubMenu(); startSubMenu(ESnapMenu, "Radial angle", ESubmenuAngleSize); iAngleSizeMenu = endSubMenu(); addItem(ESnapMenu); addItem(ESnapMenu, "Set origin", "@set_origin"); addItem(ESnapMenu, "Set origin && snap", "@set_origin_snap"); addItem(ESnapMenu, "Show axes", "@*show_axes"); addItem(ESnapMenu, "Set direction", "@set_direction"); addItem(ESnapMenu, "Set tangent direction", "@set_tangent_direction"); addItem(ESnapMenu, "Reset direction", "@reset_direction"); addItem(ESnapMenu, "Set line", "@set_line"); addItem(ESnapMenu, "Set line && snap", "@set_line_snap"); addItem(EZoomMenu, "Fullscreen", "@*fullscreen"); addItem(EZoomMenu, "Grid visible", "@*grid_visible"); addItem(EZoomMenu, "Pretty display", "@*pretty_display"); startSubMenu(EZoomMenu, "Coordinates"); addSubItem("points", "@coordinates|points"); addSubItem("mm", "@coordinates|mm"); addSubItem("m", "@coordinates|m"); addSubItem("inch", "@coordinates|inch"); endSubMenu(); startSubMenu(EZoomMenu, "Coordinate scale"); for (int s : iScalings) { char display[32]; char action[32]; if (s < 0) sprintf(display, "%d:1", -s); else sprintf(display, "1:%d", s); sprintf(action, "@scaling|%d", s); addSubItem(display, action); } endSubMenu(); addItem(EZoomMenu); addItem(EZoomMenu, "Zoom in", "@zoom_in"); addItem(EZoomMenu, "Zoom out", "@zoom_out"); addItem(EZoomMenu, "Normal size", "@normal_size"); addItem(EZoomMenu, "Fit page", "@fit_page"); addItem(EZoomMenu, "Fit width", "@fit_width"); addItem(EZoomMenu, "Fit page top", "@fit_top"); addItem(EZoomMenu, "Fit objects", "@fit_objects"); addItem(EZoomMenu, "Fit selection", "@fit_selection"); addItem(EZoomMenu); addItem(EZoomMenu, "Pan here", "@pan_here"); addItem(ELayerMenu, "New layer", "new_layer"); addItem(ELayerMenu, "Rename active layer", "rename_active_layer"); addItem(ELayerMenu); addItem(ELayerMenu, "Select all in active layer", "select_in_active_layer"); startSubMenu(ELayerMenu, "Select all in layer", ESubmenuSelectLayer); iSelectLayerMenu = endSubMenu(); addItem(ELayerMenu, "Move to active layer", "move_to_active_layer"); startSubMenu(ELayerMenu, "Move to layer", ESubmenuMoveLayer); iMoveToLayerMenu = endSubMenu(); addItem(EViewMenu, "Next view", "next_view"); addItem(EViewMenu, "Previous view", "previous_view"); addItem(EViewMenu, "First view", "first_view"); addItem(EViewMenu, "Last view", "last_view"); addItem(EViewMenu); addItem(EViewMenu, "New layer, new view", "new_layer_view"); addItem(EViewMenu, "New view", "new_view"); addItem(EViewMenu, "Delete view", "delete_view"); addItem(EViewMenu); addItem(EViewMenu, "Jump to view", "jump_view"); addItem(EViewMenu, "Edit view", "edit_view"); addItem(EPageMenu, "Next page", "next_page"); addItem(EPageMenu, "Previous page", "previous_page"); addItem(EPageMenu, "First page", "first_page"); addItem(EPageMenu, "Last page", "last_page"); addItem(EPageMenu); addItem(EPageMenu, "New page", "new_page"); addItem(EPageMenu, "Cut page", "cut_page"); addItem(EPageMenu, "Copy page", "copy_page"); addItem(EPageMenu, "Paste page", "paste_page"); addItem(EPageMenu, "Delete page", "delete_page"); addItem(EPageMenu); addItem(EPageMenu, "Jump to page", "jump_page"); addItem(EPageMenu, "Edit title && sections", "edit_title"); addItem(EPageMenu, "Edit notes", "edit_notes"); addItem(EPageMenu, "Page sorter", "page_sorter"); addItem(EPageMenu); #ifndef IPEUI_QT // In Qt these are created using "toggleViewAction()" addItem(EPageMenu, "Notes", "@*toggle_notes"); addItem(EPageMenu, "Bookmarks", "@*toggle_bookmarks"); #endif addItem(EHelpMenu, "Ipe &manual", "manual"); addItem(EHelpMenu, "Preferences", "preferences"); addItem(EHelpMenu, "Onscreen keyboard", "@keyboard"); addItem(EHelpMenu, "Show &configuration", "show_configuration"); addItem(EHelpMenu, "Show &libraries", "show_libraries"); addItem(EHelpMenu, "&Ipelet information", "about_ipelets"); #ifdef IPECURL addItem(EHelpMenu, "Enable online Latex-compilation", "cloud_latex"); #endif lua_getglobal(L, "prefs"); lua_getfield(L, -1, "developer"); if (lua_toboolean(L, -1)) { startSubMenu(EHelpMenu, "Developer"); addSubItem("Reload ipelets", "developer_reload_ipelets"); addSubItem("List shortcuts", "developer_list_shortcuts"); endSubMenu(); } lua_pop(L, 2); // developer, prefs #ifndef IPEUI_COCOA addItem(EHelpMenu, "&About Ipe", "about"); #endif // build Ipelet menu lua_getglobal(L, "ipelets"); int n = lua_rawlen(L, -1); for (int i = 1; i <= n; ++i) { lua_rawgeti(L, -1, i); lua_getfield(L, -1, "label"); if (!lua_isstring(L, -1)) { lua_pop(L, 2); // label, ipelet continue; } String label(lua_tolstring(L, -1, nullptr)); lua_pop(L, 1); lua_getfield(L, -1, "name"); String name(lua_tolstring(L, -1, nullptr)); lua_pop(L, 1); lua_getfield(L, -1, "methods"); char buf[20]; if (lua_isnil(L, -1)) { String action("ipelet_1_"); action += name; addItem(EIpeletMenu, label.z(), action.z()); } else { int m = lua_rawlen(L, -1); startSubMenu(EIpeletMenu, label.z()); for (int j = 1; j <= m; ++j) { lua_rawgeti(L, -1, j); lua_getfield(L, -1, "label"); sprintf(buf, "ipelet_%d_", j); String action(buf); action += name; addSubItem(lua_tolstring(L, -1, nullptr), action.z()); lua_pop(L, 2); // sublabel, method } endSubMenu(); } lua_pop(L, 2); // methods, ipelet } lua_pop(L, 1); } // -------------------------------------------------------------------- void AppUiBase::canvasObserverWheelMoved(double xDegrees, double yDegrees, int kind) { if (xDegrees != 0.0 || yDegrees != 0.0) { lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "wheel_zoom"); lua_insert(L, -2); // model lua_pushnumber(L, xDegrees); lua_pushnumber(L, yDegrees); lua_pushinteger(L, kind); luacall(L, 4, 0); } else // result of a zoom gesture (Windows only, currently) setZoom(iCanvas->zoom()); } void AppUiBase::canvasObserverToolChanged(bool hasTool) { setActionsEnabled(!hasTool || isInkMode); } static void adjust(double &x, int mode, double factor) { if (ipe::abs(x) < 1e-12) x = 0.0; x *= factor; switch (mode) { case 1: // mm x = (x / 72.0) * 25.4; break; case 2: // m x = (x / 72000.0) * 25.4; break; case 3: // in x /= 72; break; default: break; } } static const char * const mouse_units[] = { "", " mm", " m", " in" }; void AppUiBase::canvasObserverPositionChanged() { Vector v = iCanvas->CanvasBase::pos(); const Snap &snap = iCanvas->snap(); if (snap.iWithAxes) { v = v - snap.iOrigin; v = Linear(-snap.iDir) * v; } adjust(v.x, iMouseIn, iMouseFactor); adjust(v.y, iMouseIn, iMouseFactor); const char *units = mouse_units[iMouseIn]; char s[256]; sprintf(s, iCoordinatesFormat.z(), v.x, units, v.y, units); setMouseIndicator(s); } void AppUiBase::canvasObserverMouseAction(int button) { lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "mouseButtonAction"); lua_insert(L, -2); // model push_button(L, button); luacall(L, 3, 0); } void AppUiBase::canvasObserverSizeChanged() { lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "sizeChanged"); lua_insert(L, -2); // model luacall(L, 1, 0); } // -------------------------------------------------------------------- int AppUiBase::actionInfo(lua_State *L) const { return 0; // only Windows will override this } static void call_selector(lua_State *L, int model, String name) { // calls model selector lua_rawgeti(L, LUA_REGISTRYINDEX, model); lua_getfield(L, -1, "selector"); lua_pushvalue(L, -2); // model lua_remove(L, -3); push_string(L, name); } void AppUiBase::luaSelector(String name, String value) { call_selector(L, iModel, name); if (value == "true") lua_pushboolean(L, true); else if (value == "false") lua_pushboolean(L, false); else push_string(L, value); luacall(L, 3, 0); } void AppUiBase::luaAbsoluteButton(const char *s) { // calls model selector lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "absoluteButton"); lua_insert(L, -2); // method, model lua_pushstring(L, s); luacall(L, 2, 0); } // -------------------------------------------------------------------- void AppUiBase::luaAction(String name) { if (isInkMode && iCanvas->tool() != nullptr) return; // refuse any action while drawing ink if (name.left(12) == "coordinates|") { if (name.right(2) == "mm") iMouseIn = 1; else if (name.right(1) == "m") iMouseIn = 2; else if (name.right(4) == "inch") iMouseIn = 3; else iMouseIn = 0; } else if (name.left(8) == "scaling|") { Lex lex(name.substr(8)); int s = lex.getInt(); if (s < 0) iMouseFactor = 1.0 / -s; else iMouseFactor = s; } else if (name.find('|') >= 0) { // calls model selector int i = name.find('|'); luaSelector(name.left(i), name.substr(i+1)); } else { // calls model action lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "action"); lua_insert(L, -2); // before model push_string(L, name); luacall(L, 2, 0); } } void AppUiBase::luaShowPathStylePopup(Vector v) { lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "showPathStylePopup"); lua_insert(L, -2); // before model push_vector(L, v); luacall(L, 2, 0); } void AppUiBase::luaShowLayerBoxPopup(Vector v, String layer) { lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "showLayerBoxPopup"); lua_insert(L, -2); // before model push_vector(L, v); push_string(L, layer); luacall(L, 3, 0); } void AppUiBase::luaLayerAction(String name, String layer) { lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "layerAction"); lua_insert(L, -2); // before model push_string(L, name); push_string(L, layer); luacall(L, 3, 0); } void AppUiBase::luaBookmarkSelected(int index) { lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "bookmark"); lua_insert(L, -2); // method, model lua_pushnumber(L, index + 1); luacall(L, 2, 0); } // -------------------------------------------------------------------- static String stripMark(Attribute mark) { String s = mark.string(); if (s.left(5) == "mark/") { int i = s.rfind('('); return s.substr(5, i > 0 ? i-5 : -1); } else return String(); } void AppUiBase::showInCombo(const Cascade *sheet, Kind kind, int sel, const char *deflt) { AttributeSeq seq; sheet->allNames(kind, seq); if (!seq.size() && deflt != nullptr) { addCombo(sel, deflt); iComboContents[sel].push_back(deflt); } for (const auto & att : seq) { String s = att.string(); addCombo(sel, s); iComboContents[sel].push_back(s); } } void AppUiBase::showMarksInCombo(const Cascade *sheet) { AttributeSeq seq; sheet->allNames(ESymbol, seq); for (const auto & att : seq) { String s = stripMark(att); if (!s.empty()) { addCombo(EUiMarkShape, s); iComboContents[EUiMarkShape].push_back(s); } } } void AppUiBase::setupSymbolicNames(const Cascade *sheet) { resetCombos(); for (int i = 0; i < EUiView; ++i) iComboContents[i].clear(); AttributeSeq seq, absColor; sheet->allNames(EColor, seq); for (const auto & att : seq) absColor.push_back(sheet->find(EColor, att)); addComboColors(seq, absColor); showInCombo(sheet, EPen, EUiPen); showInCombo(sheet, ETextSize, EUiTextSize); showInCombo(sheet, ESymbolSize, EUiSymbolSize); showMarksInCombo(sheet); showInCombo(sheet, EGridSize, EUiGridSize, "16pt"); showInCombo(sheet, EAngleSize, EUiAngleSize, "45 deg"); } void AppUiBase::setGridAngleSize(Attribute abs_grid, Attribute abs_angle) { AttributeSeq seq; iCascade->allNames(EGridSize, seq); if (!seq.size()) setComboCurrent(EUiGridSize, 0); for (int i = 0; i < size(seq); ++i) { if (iCascade->find(EGridSize, seq[i]) == abs_grid) { setComboCurrent(EUiGridSize, i); break; } } seq.clear(); iCascade->allNames(EAngleSize, seq); if (!seq.size()) setComboCurrent(EUiAngleSize, 0); for (int i = 0; i < size(seq); ++i) { if (iCascade->find(EAngleSize, seq[i]) == abs_angle) { setComboCurrent(EUiAngleSize, i); break; } } } // -------------------------------------------------------------------- void AppUiBase::setAttribute(int sel, Attribute a) { String s = a.string(); for (int i = 0; i < int(iComboContents[sel].size()); ++i) { if (iComboContents[sel][i] == s) { setComboCurrent(sel, i); return; } } } void AppUiBase::setAttributes(const AllAttributes &all, Cascade *sheet) { iAll = all; iCascade = sheet; setPathView(all, sheet); setAttribute(EUiStroke, iAll.iStroke); setAttribute(EUiFill, iAll.iFill); Color stroke = iCascade->find(EColor, iAll.iStroke).color(); Color fill = iCascade->find(EColor, iAll.iFill).color(); setButtonColor(EUiStroke, stroke); setButtonColor(EUiFill, fill); setAttribute(EUiPen, iAll.iPen); setAttribute(EUiTextSize, iAll.iTextSize); setAttribute(EUiSymbolSize, iAll.iSymbolSize); String s = stripMark(iAll.iMarkShape); for (int i = 0; i < int(iComboContents[EUiMarkShape].size()); ++i) { if (iComboContents[EUiMarkShape][i] == s) { setComboCurrent(EUiMarkShape, i); break; } } setCheckMark("horizontalalignment", Attribute(iAll.iHorizontalAlignment)); setCheckMark("verticalalignment", Attribute(iAll.iVerticalAlignment)); setCheckMark("pinned", Attribute(iAll.iPinned)); setCheckMark("transformabletext", Attribute::Boolean(iAll.iTransformableText)); setCheckMark("transformations", Attribute(iAll.iTransformations)); setCheckMark("linejoin", Attribute(iAll.iLineJoin)); setCheckMark("linecap", Attribute(iAll.iLineCap)); setCheckMark("fillrule", Attribute(iAll.iFillRule)); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/main_cocoa.cpp0000644000175000017500000001613613561570220016403 0ustar otfriedotfried// -*- objc -*- // main.mm /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebase.h" #include "ipelua.h" #include "controls_cocoa.h" // for COPYRIGHT_YEAR #include "appui.h" using namespace ipe; using namespace ipelua; #include "main_common.i" // -------------------------------------------------------------------- static void setup_globals(lua_State *L) { lua_getglobal(L, "package"); const char *luapath = getenv("IPELUAPATH"); if (luapath) lua_pushstring(L, luapath); else push_string(L, Platform::ipeDir("lua", "?.lua")); lua_setfield(L, -2, "path"); lua_newtable(L); // config table lua_pushliteral(L, "apple"); lua_setfield(L, -2, "platform"); lua_pushliteral(L, "cocoa"); lua_setfield(L, -2, "toolkit"); setup_config(L, "system_styles", nullptr, "styles"); setup_config(L, "system_ipelets", nullptr, "ipelets"); setup_config(L, "docdir", "IPEDOCDIR", "doc"); setup_common_config(L); NSArray *args = [[NSProcessInfo processInfo] arguments]; int argc = [args count]; lua_createtable(L, 0, argc - 1); for (int i = 1; i < argc; ++i) { lua_pushstring(L, [args[i] UTF8String]); lua_rawseti(L, -2, i); } lua_setglobal(L, "argv"); NSRect e = [[NSScreen mainScreen] frame]; int cx = int(e.size.height); int cy = int(e.size.width); lua_createtable(L, 0, 2); lua_pushinteger(L, cx); lua_rawseti(L, -2, 1); lua_pushinteger(L, cy); lua_rawseti(L, -2, 2); lua_setfield(L, -2, "screen_geometry"); lua_setglobal(L, "config"); lua_pushcfunction(L, ipe_tonumber); lua_setglobal(L, "tonumber"); } // -------------------------------------------------------------------- static bool run_mainloop = false; // On Mac OS, the event loop is already running, // but if mainloop isn't called from Lua, we terminate. static int mainloop(lua_State *L) { run_mainloop = true; return 0; } // -------------------------------------------------------------------- // Is bug #147 still relevant? @interface AppDelegate : NSObject @end // -------------------------------------------------------------------- static const char * const about_text = "Copyright (c) 1993-%d Otfried Cheong\n\n" "The extensible drawing editor Ipe creates figures " "in Postscript and PDF format, " "using LaTeX to format the text in the figures.\n" "Ipe is released under the GNU Public License.\n" "See http://ipe.otfried.org for details.\n" "You can \"like\" Ipe and follow Ipe announcements on Facebook " "(http://www.facebook.com/drawing.editor.Ipe7).\n\n" "If you are an Ipe fan and want to show others, have a look at the " "Ipe T-shirts (www.shirtee.com/en/store/ipe).\n\n" "Platinum sponsors\n\n" " * Hee-Kap Ahn\n" " * Martin Ziegler\n\n" "If you enjoy Ipe, you can become a member of the exclusive community of " "Ipe patrons (http://patreon.com/otfried). " "For the price of a cup of coffee per month you can make a meaningful contribution " "to the continuing development of Ipe."; // -------------------------------------------------------------------- @implementation AppDelegate { lua_State *L; } - (instancetype) init { self = [super init]; if (self) { L = setup_lua(); setup_globals(L); } return self; } - (instancetype) initWithCoder:(NSCoder *) decoder { // this is needed on OSX 10.9, but not called on 10.11 return [self init]; } - (void) aboutIpe:(id) sender { NSString *text = [NSString stringWithFormat:@"Ipe %d.%d.%d", IPELIB_VERSION / 10000, (IPELIB_VERSION / 100) % 100, IPELIB_VERSION % 100]; NSString *info = [NSString stringWithFormat:@(about_text), COPYRIGHT_YEAR]; NSAlert *alert = [[NSAlert alloc] init]; [alert setMessageText:text]; [alert setInformativeText:info]; [alert setAlertStyle:NSInformationalAlertStyle]; [alert runModal]; } - (void) ipeAlwaysAction:(id) sender { String method = "action_"; method += N2I([sender ipeAction]); lua_getglobal(L, method.z()); lua_call(L, 0, 0); } - (BOOL) applicationShouldTerminateAfterLastWindowClosed:(NSApplication *) app { lua_getglobal(L, "prefs"); lua_getfield(L, -1, "terminate_on_close"); bool term = lua_toboolean(L, -1); lua_pop(L, 2); return term; } - (void) applicationWillFinishLaunching:(NSNotification *) notification { lua_run_ipe(L, mainloop); } - (void) applicationDidFinishLaunching:(NSNotification *) notification { if (!run_mainloop) [NSApp terminate:self]; } - (NSApplicationTerminateReply) applicationShouldTerminate:(NSNotification *) notification { NSArray *wins = [NSApp windows]; int count = 0; int modified = 0; for (NSWindow *w : wins) { if ([w isMemberOfClass:[NSWindow class]]) { if ([w.delegate respondsToSelector:@selector(ipeIsModified:)]) { bool mod = [w.delegate performSelector:@selector(ipeIsModified:) withObject:self]; count++; if (mod) modified++; } } } ipeDebug("%d windows, %d modified", count, modified); if (modified == 0) return NSTerminateNow; NSString *warn = [NSString stringWithFormat: @"%d of your %d open Ipe windows contain unsaved changes!", modified, count]; NSAlert *alert = [[NSAlert alloc] init]; [alert setMessageText:@"Really quit Ipe?"]; [alert setInformativeText:warn]; [alert setAlertStyle:NSWarningAlertStyle]; [alert addButtonWithTitle:@"Discard all changes"]; [alert addButtonWithTitle:@"Cancel"]; switch ([alert runModal]) { case NSAlertFirstButtonReturn: return NSTerminateNow; default: return NSTerminateCancel; } } - (void) applicationWillTerminate:(NSNotification *) notification { lua_close(L); } - (BOOL) application:(NSApplication *) theApplication openFile:(NSString *) filename { lua_getglobal(L, "file_open_event"); lua_pushstring(L, filename.UTF8String); lua_call(L, 1, 0); return YES; } @end // -------------------------------------------------------------------- int main(int argc, const char * argv[]) { ipe::Platform::initLib(ipe::IPELIB_VERSION); return NSApplicationMain(argc, argv); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/main_gtk.cpp0000644000175000017500000000677513561570220016114 0ustar otfriedotfried// -------------------------------------------------------------------- // Main function // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebase.h" #include "ipelua.h" #include #include #include using namespace ipe; using namespace ipelua; #include "main_common.i" // -------------------------------------------------------------------- static void setup_globals(lua_State *L) { lua_getglobal(L, "package"); const char *luapath = getenv("IPELUAPATH"); if (luapath) lua_pushstring(L, luapath); else lua_pushliteral(L, IPELUADIR "/?.lua"); lua_setfield(L, -2, "path"); lua_newtable(L); // config table lua_pushliteral(L, "unix"); lua_setfield(L, -2, "platform"); lua_pushliteral(L, "gtk"); lua_setfield(L, -2, "toolkit"); setup_config(L, "system_styles", 0, IPESTYLEDIR); setup_config(L, "system_ipelets", 0, IPELETDIR); setup_config(L, "docdir", "IPEDOCDIR", IPEDOCDIR); push_string(L, Platform::latexDirectory()); lua_setfield(L, -2, "latexdir"); push_string(L, Platform::latexPath()); lua_setfield(L, -2, "latexpath"); push_string(L, ipeIconDirectory()); lua_setfield(L, -2, "icons"); lua_pushfstring(L, "Ipe %d.%d.%d", IPELIB_VERSION / 10000, (IPELIB_VERSION / 100) % 100, IPELIB_VERSION % 100); lua_setfield(L, -2, "version"); GdkScreen* screen = gdk_screen_get_default(); int width = gdk_screen_get_width(screen); int height = gdk_screen_get_height(screen); ipeDebug("Screen resolution is (%d x %d)", width, height); lua_createtable(L, 0, 2); lua_pushinteger(L, width); lua_rawseti(L, -2, 1); lua_pushinteger(L, height); lua_rawseti(L, -2, 2); lua_setfield(L, -2, "screen_geometry"); lua_setglobal(L, "config"); lua_pushcfunction(L, ipe_tonumber); lua_setglobal(L, "tonumber"); } // -------------------------------------------------------------------- int mainloop(lua_State *L) { gtk_main(); return 0; } int main(int argc, char *argv[]) { Platform::initLib(IPELIB_VERSION); gtk_init(&argc, &argv); lua_State *L = setup_lua(); // create table with arguments lua_createtable(L, 0, argc - 1); for (int i = 1; i < argc; ++i) { lua_pushstring(L, argv[i]); lua_rawseti(L, -2, i); } lua_setglobal(L, "argv"); setup_globals(L); lua_run_ipe(L, mainloop); lua_close(L); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/appui_win.h0000644000175000017500000001334713561570220015754 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Appui for Win32 // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef APPUI_WIN_H #define APPUI_WIN_H #include "appui.h" class PathView; class LayerList; using namespace ipe; // -------------------------------------------------------------------- class AppUi : public AppUiBase { public: static void init(HINSTANCE hInstance, int nCmdShow); static bool isDrawing(HWND target); AppUi(lua_State *L0, int model); ~AppUi(); virtual void action(String name) override; virtual void setLayers(const Page *page, int view) override; virtual void setZoom(double zoom) override; virtual void setActionsEnabled(bool mode) override; virtual void setNumbers(String vno, bool vm, String pno, bool pm) override; virtual void setNotes(String notes) override; virtual WINID windowId() override; virtual void closeWindow() override; virtual bool actionState(const char *name) override; virtual void setActionState(const char *name, bool value) override; virtual void setWindowCaption(bool mod, const char *s) override; virtual void explain(const char *s, int t) override; virtual void showWindow(int width, int height) override; virtual void setBookmarks(int no, const String *s) override; virtual void setToolVisible(int m, bool vis) override; virtual int actionInfo(lua_State *L) const override; virtual int pageSorter(lua_State *L, Document *doc, int width, int height, int thumbWidth) override; virtual int clipboard(lua_State *L) override; virtual int setClipboard(lua_State *L) override; void toggleFullscreen(); private: void initUi(); void layoutChildren(bool resizeRebar); void createAction(String name, String tooltip, bool canWhileDrawing = false); int findAction(const char *name) const; int actionId(const char *name) const; void addItem(HMENU menu, const char *title, const char *name); virtual void addRootMenu(int id, const char *name) override; virtual void addItem(int id, const char *title, const char *name) override; virtual void startSubMenu(int id, const char *name, int tag) override; virtual void addSubItem(const char *title, const char *name) override; virtual MENUHANDLE endSubMenu() override; virtual void setSnapIndicator(const char *s) override; virtual void setMouseIndicator(const char *s) override; virtual void addCombo(int sel, String s) override; virtual void resetCombos() override; virtual void addComboColors(AttributeSeq &sym, AttributeSeq &abs) override; virtual void setComboCurrent(int sel, int idx) override; virtual void setCheckMark(String name, Attribute a) override; virtual void setPathView(const AllAttributes &all, Cascade *sheet) override; virtual void setButtonColor(int sel, Color color) override; void populateTextStyleMenu(); void populateLayerMenus(); void populateSizeMenus(); void populateSizeMenu(HMENU h, int sel, int base); void cmd(int id, int notification); void setCheckMark(String name, String value); void aboutIpe(); void closeRequested(); int iconId(const char *name) const; HWND createToolBar(HINSTANCE hInst); void addTButton(HWND tb, const char *name = nullptr, int flags = 0); void setTooltip(HWND h, String tip, bool isComboBoxEx = false); void toggleVisibility(String action, HWND h); void setLeftDockVisibility(bool vis); HWND createButton(HINSTANCE hInst, int id, int flags = BS_BITMAP|BS_PUSHBUTTON); inline int uiscale(int x) { return iUiScale * x / 100; } private: static LRESULT CALLBACK wndProc(HWND hwnd, UINT Message, WPARAM wParam, LPARAM lParam); static BOOL CALLBACK enumThreadWndProc(HWND hwnd, LPARAM lParam); static const wchar_t className[]; private: struct SAction { String name; String tooltip; int icon; bool alwaysOn; }; std::vector iActions; HMENU hMenuBar; HMENU hRootMenu[ENumMenu]; HIMAGELIST hIcons; HIMAGELIST hColorIcons; HFONT hFont; HWND hwnd; HWND hwndCanvas; HWND hTip; HWND hStatusBar; HWND hSnapTools; HWND hEditTools; HWND hObjectTools; HWND hRebar; HWND hNotes; HWND hBookmarks; HWND hProperties; HWND hLayerGroup; HWND hNotesGroup; HWND hBookmarksGroup; HWND hButton[EUiGridSize]; HWND hSelector[EUiView]; HWND hViewNumber; HWND hPageNumber; HWND hViewMarked; HWND hPageMarked; PathView *iPathView; HWND hLayers; bool iSettingLayers; std::vector iLayerNames; // for fullscreen mode bool iFullScreen; bool iWasMaximized; RECT iWindowRect; LONG iWindowStyle; LONG iWindowExStyle; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipe/uilua.cpp0000644000175000017500000005623413561570220015435 0ustar otfriedotfried// -------------------------------------------------------------------- // Lua bindings for user interface // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "appui.h" #include "ipecanvas.h" #include "tools.h" #include "ipelua.h" #include "ipethumbs.h" #include #include using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- static CanvasBase *check_canvas(lua_State *L, int i) { AppUiBase **ui = (AppUiBase **) luaL_checkudata(L, i, "Ipe.appui"); return (*ui)->canvas(); } inline AppUiBase **check_appui(lua_State *L, int i) { return (AppUiBase **) luaL_checkudata(L, i, "Ipe.appui"); } static int appui_tostring(lua_State *L) { check_appui(L, 1); lua_pushfstring(L, "AppUi@%p", lua_topointer(L, 1)); return 1; } /* When the Lua model is collected, its "ui" userdata will be garbage collected as well. At this point, the C++ object has long been deleted. */ static int appui_destructor(lua_State *L) { check_appui(L, 1); ipeDebug("AppUi Lua destructor"); return 0; } // -------------------------------------------------------------------- static int appui_setPage(lua_State *L) { AppUiBase **ui = check_appui(L, 1); Page *page = check_page(L, 2)->page; int pno = luaL_checkinteger(L, 3) - 1; int view = check_viewno(L, 4, page); Cascade *sheets = check_cascade(L, 5)->cascade; (*ui)->canvas()->setPage(page, pno, view, sheets); return 0; } static int appui_setResources(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); Document **d = check_document(L, 2); const PdfResources *res = (*d)->resources(); canvas->setResources(res); return 0; } static int appui_pan(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); Vector p = canvas->pan(); push_vector(L, p); return 1; } static int appui_setPan(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); Vector *v = check_vector(L, 2); canvas->setPan(*v); return 0; } static int appui_zoom(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); lua_pushnumber(L, canvas->zoom()); return 1; } static int appui_setZoom(lua_State *L) { AppUiBase **ui = check_appui(L, 1); (*ui)->setZoom(luaL_checknumber(L, 2)); return 0; } static int appui_setSnapIndicator(lua_State *L) { AppUiBase **ui = check_appui(L, 1); (*ui)->setSnapIndicator(luaL_checklstring(L, 2, nullptr)); return 0; } static int appui_pos(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); push_vector(L, canvas->pos()); return 1; } static int appui_globalPos(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); push_vector(L, canvas->globalPos()); return 1; } static int appui_unsnappedPos(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); push_vector(L, canvas->unsnappedPos()); return 1; } static int appui_simpleSnapPos(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); push_vector(L, canvas->simpleSnapPos()); return 1; } static int appui_setFifiVisible(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); canvas->setFifiVisible(lua_toboolean(L, 2)); return 0; } static int appui_setInkMode(lua_State *L) { AppUiBase **ui = check_appui(L, 1); bool ink = lua_toboolean(L, 2); (*ui)->setInkMode(ink); (*ui)->canvas()->setInkMode(ink); return 0; } static int appui_setSelectionVisible(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); canvas->setSelectionVisible(lua_toboolean(L, 2)); return 0; } static int appui_setSnap(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); Snap snap = canvas->snap(); get_snap(L, 2, snap); canvas->setSnap(snap); return 0; } static int appui_setAutoOrigin(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); Vector *v = check_vector(L, 2); canvas->setAutoOrigin(*v); return 0; } static int appui_update(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); if (lua_isnone(L, 2) || lua_isboolean(L, 2)) { if (lua_isnone(L, 2) || lua_toboolean(L, 2)) canvas->update(); else canvas->updateTool(); } else { ipe::Rect *r = check_rect(L, 2); Vector bl = canvas->userToDev(r->topLeft()); Vector tr = canvas->userToDev(r->bottomRight()); canvas->invalidate(int(bl.x-1), int(bl.y-1), int(tr.x - bl.x + 2), int(tr.y - bl.y + 2)); } return 0; } static int appui_finishTool(lua_State *L) { AppUiBase **ui = check_appui(L, 1); (*ui)->canvas()->finishTool(); (*ui)->explain("", 0); return 0; } static int appui_canvasSize(lua_State *L) { CanvasBase *canvas = (CanvasBase *) check_canvas(L, 1); push_vector(L, Vector(canvas->canvasWidth(), canvas->canvasHeight())); return 1; } static void check_rgb(lua_State *L, int i, int &r, int &g, int &b) { r = int(1000 * luaL_checknumber(L, i) + 0.5); g = int(1000 * luaL_checknumber(L, i+1) + 0.5); b = int(1000 * luaL_checknumber(L, i+2) + 0.5); luaL_argcheck(L, (0 <= r && r <= 1000 && 0 <= g && g <= 1000 && 0 <= b && b <= 1000), 2, "color components must be between 0.0 and 1.0"); } static int appui_setCursor(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); if (lua_isnumber(L, 2)) { double s = lua_tonumberx(L, 2, nullptr); int r, g, b; check_rgb(L, 3, r, g, b); Color color(r, g, b); canvas->setCursor(CanvasBase::EDotCursor, s, &color); } else if (lua_isstring(L, 2)) { static const char * const cursor_names[] = { "standard", "hand", "cross", nullptr }; CanvasBase::TCursor t = CanvasBase::TCursor(luaL_checkoption(L, 2, nullptr, cursor_names)); canvas->setCursor(t); } else canvas->setCursor(CanvasBase::EStandardCursor); return 0; } static int appui_setNumbering(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); bool t = lua_toboolean(L, 2); CanvasBase::Style s = canvas->canvasStyle(); s.numberPages = t; canvas->setCanvasStyle(s); return 0; } static int appui_setPretty(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); bool t = lua_toboolean(L, 2); CanvasBase::Style s = canvas->canvasStyle(); s.pretty = t; canvas->setCanvasStyle(s); return 0; } // -------------------------------------------------------------------- static int appui_pantool(lua_State *L) { ipeDebug("pantool"); CanvasBase *canvas = check_canvas(L, 1); Page *page = check_page(L, 2)->page; int view = check_viewno(L, 3, page); PanTool *tool = new PanTool(canvas, page, view); canvas->setTool(tool); return 0; } static int appui_selecttool(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); Page *page = check_page(L, 2)->page; int view = check_viewno(L, 3, page); double selectDistance = luaL_checknumber(L, 4); bool nonDestructive = lua_toboolean(L, 5); SelectTool *tool = new SelectTool(canvas, page, view, selectDistance, nonDestructive); canvas->setTool(tool); return 0; } static int appui_transformtool(lua_State *L) { static const char * const option_names[] = { "translate", "scale", "stretch", "rotate", "shear", nullptr }; CanvasBase *canvas = check_canvas(L, 1); Page *page = check_page(L, 2)->page; int view = check_viewno(L, 3, page); int type = luaL_checkoption(L, 4, nullptr, option_names); bool withShift = lua_toboolean(L, 5); lua_pushvalue(L, 6); int method = luaL_ref(L, LUA_REGISTRYINDEX); IpeTransformTool *tool = new IpeTransformTool(canvas, page, view, TransformTool::TType(type), withShift, L, method); if (tool->isValid()) { canvas->setTool(tool); lua_pushboolean(L, true); return 1; } else { delete tool; return 0; } } static int luatool_setcolor(lua_State *L) { LuaTool *tool = (LuaTool *) lua_touserdata(L, lua_upvalueindex(1)); int r, g, b; check_rgb(L, 1, r, g, b); tool->setColor(Color(r, g, b)); return 0; } static int shapetool_setshape(lua_State *L) { ShapeTool *tool = (ShapeTool *) lua_touserdata(L, lua_upvalueindex(1)); Shape shape = check_shape(L, 1); int which = 0; if (!lua_isnoneornil(L, 2)) which = (int)luaL_checkinteger(L, 2); double pen = 1.0; if (lua_isnumber(L, 3)) pen = luaL_checknumber(L, 3); tool->setShape(shape, which, pen); return 0; } static int shapetool_setsnapping(lua_State *L) { ShapeTool *tool = (ShapeTool *) lua_touserdata(L, lua_upvalueindex(1)); bool snap = lua_toboolean(L, 1); bool skipLast = lua_toboolean(L, 2); tool->setSnapping(snap, skipLast); return 0; } static int shapetool_setmarks(lua_State *L) { ShapeTool *tool = (ShapeTool *) lua_touserdata(L, lua_upvalueindex(1)); luaL_argcheck(L, lua_istable(L, 1), 1, "argument is not a table"); int no = lua_rawlen(L, 1); tool->clearMarks(); for (int i = 1; i + 1 <= no; i += 2) { lua_rawgeti(L, 1, i); luaL_argcheck(L, is_type(L, -1, "Ipe.vector"), 1, "element is not a vector"); Vector *v = check_vector(L, -1); lua_rawgeti(L, 1, i+1); luaL_argcheck(L, lua_isnumber(L, -1), 1, "element is not a number"); int t = lua_tointegerx(L, -1, nullptr); luaL_argcheck(L, ShapeTool::EVertex <= t && t < ShapeTool::ENumMarkTypes, 1, "number is not a mark type"); lua_pop(L, 2); // v, t tool->addMark(*v, ShapeTool::TMarkType(t)); } return 0; } static int pastetool_setmatrix(lua_State *L) { PasteTool *tool = (PasteTool *) lua_touserdata(L, lua_upvalueindex(1)); Matrix *m = check_matrix(L, 1); tool->setMatrix(*m); return 0; } static int appui_shapetool(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); lua_pushvalue(L, 2); int luatool = luaL_ref(L, LUA_REGISTRYINDEX); ShapeTool *tool = new ShapeTool(canvas, L, luatool); // add methods to Lua tool lua_rawgeti(L, LUA_REGISTRYINDEX, luatool); lua_pushlightuserdata(L, tool); lua_pushcclosure(L, luatool_setcolor, 1); lua_setfield(L, -2, "setColor"); lua_pushlightuserdata(L, tool); lua_pushcclosure(L, shapetool_setshape, 1); lua_setfield(L, -2, "setShape"); lua_pushlightuserdata(L, tool); lua_pushcclosure(L, shapetool_setmarks, 1); lua_setfield(L, -2, "setMarks"); lua_pushlightuserdata(L, tool); lua_pushcclosure(L, shapetool_setsnapping, 1); lua_setfield(L, -2, "setSnapping"); canvas->setTool(tool); return 0; } static int appui_pastetool(lua_State *L) { CanvasBase *canvas = check_canvas(L, 1); Object *obj = check_object(L, 2)->obj; lua_pushvalue(L, 3); int luatool = luaL_ref(L, LUA_REGISTRYINDEX); PasteTool *tool = new PasteTool(canvas, L, luatool, obj->clone()); // add methods to Lua tool lua_rawgeti(L, LUA_REGISTRYINDEX, luatool); lua_pushlightuserdata(L, tool); lua_pushcclosure(L, luatool_setcolor, 1); lua_setfield(L, -2, "setColor"); lua_pushlightuserdata(L, tool); lua_pushcclosure(L, pastetool_setmatrix, 1); lua_setfield(L, -2, "setMatrix"); canvas->setTool(tool); return 0; } // -------------------------------------------------------------------- static int appui_win(lua_State *L) { AppUiBase **ui = check_appui(L, 1); push_winid(L, (*ui)->windowId()); return 1; } static int appui_close(lua_State *L) { AppUiBase **ui = check_appui(L, 1); (*ui)->closeWindow(); return 0; } static int appui_clipboard(lua_State *L) { AppUiBase **ui = check_appui(L, 1); return (*ui)->clipboard(L); } static int appui_setClipboard(lua_State *L) { AppUiBase **ui = check_appui(L, 1); return (*ui)->setClipboard(L); } // This is only used on Windows to compute the shortcuts... static int appui_actionInfo(lua_State *L) { AppUiBase **ui = check_appui(L, 1); return (*ui)->actionInfo(L); } static int appui_actionState(lua_State *L) { AppUiBase **ui = check_appui(L, 1); const char *name = luaL_checklstring(L, 2, nullptr); lua_pushboolean(L, (*ui)->actionState(name)); return 1; } static int appui_setActionState(lua_State *L) { AppUiBase **ui = check_appui(L, 1); const char *name = luaL_checklstring(L, 2, nullptr); bool val = lua_toboolean(L, 3); (*ui)->setActionState(name, val); return 0; } static int appui_setupSymbolicNames(lua_State *L) { AppUiBase **ui = check_appui(L, 1); Cascade *sheets = check_cascade(L, 2)->cascade; (*ui)->setupSymbolicNames(sheets); return 0; } static int appui_setAttributes(lua_State *L) { AppUiBase **ui = check_appui(L, 1); Cascade *sheets = check_cascade(L, 2)->cascade; AllAttributes all; check_allattributes(L, 3, all); (*ui)->setAttributes(all, sheets); return 0; } static int appui_setGridAngleSize(lua_State *L) { AppUiBase **ui = check_appui(L, 1); Attribute gs = check_number_attribute(L, 2); Attribute as = check_number_attribute(L, 3); (*ui)->setGridAngleSize(gs, as); return 0; } static int appui_setLayers(lua_State *L) { AppUiBase **ui = check_appui(L, 1); Page *page = check_page(L, 2)->page; int view = check_viewno(L, 3, page); (*ui)->setLayers(page, view); return 0; } static int appui_setNumbers(lua_State *L) { AppUiBase **ui = check_appui(L, 1); String vno; String pno; if (!lua_isnil(L, 2)) vno = luaL_checklstring(L, 2, nullptr); bool vm = lua_toboolean(L, 3); if (!lua_isnil(L, 4)) pno = luaL_checklstring(L, 4, nullptr); bool pm = lua_toboolean(L, 5); (*ui)->setNumbers(vno, vm, pno, pm); return 0; } static int appui_setBookmarks(lua_State *L) { AppUiBase **ui = check_appui(L, 1); luaL_argcheck(L, lua_istable(L, 2), 2, "argument is not a table"); int no = lua_rawlen(L, 2); std::vector bm; for (int i = 1; i <= no; ++i) { lua_rawgeti(L, 2, i); luaL_argcheck(L, lua_isstring(L, -1), 2, "item is not a string"); bm.push_back(String(lua_tolstring(L, -1, nullptr))); lua_pop(L, 1); } (*ui)->setBookmarks(no, &bm[0]); return 0; } static int appui_setWindowTitle(lua_State *L) { AppUiBase **ui = check_appui(L, 1); bool mod = lua_toboolean(L, 2); const char *s = luaL_checklstring(L, 3, nullptr); (*ui)->setWindowCaption(mod, s); return 0; } static int appui_setNotes(lua_State *L) { AppUiBase **ui = check_appui(L, 1); const char *s = luaL_checklstring(L, 2, nullptr); (*ui)->setNotes(s); return 0; } static int appui_showTool(lua_State *L) { static const char * const option_names[] = { "properties", "bookmarks", "notes", "layers", nullptr }; AppUiBase **ui = check_appui(L, 1); int m = luaL_checkoption(L, 2, nullptr, option_names); bool s = lua_toboolean(L, 3); (*ui)->setToolVisible(m, s); return 0; } static int appui_explain(lua_State *L) { AppUiBase **ui = check_appui(L, 1); const char *s = luaL_checklstring(L, 2, nullptr); int t = 4000; if (lua_isnumber(L, 3)) t = lua_tointegerx(L, 3, nullptr); (*ui)->explain(s, t); return 0; } // -------------------------------------------------------------------- void get_page_sorter_size(lua_State *L, int &width, int &height, int &thumbWidth) { thumbWidth = 300; width = 600; height = 480; lua_getglobal(L, "prefs"); lua_getfield(L, -1, "page_sorter_size"); if (lua_istable(L, -1)) { lua_rawgeti(L, -1, 1); if (lua_isnumber(L, -1)) width = lua_tointegerx(L, -1, nullptr); lua_rawgeti(L, -2, 2); if (lua_isnumber(L, -1)) height = lua_tointegerx(L, -1, nullptr); lua_pop(L, 2); } lua_pop(L, 1); // page_sorter_size lua_getfield(L, -1, "thumbnail_width"); if (lua_isnumber(L, -1)) thumbWidth = lua_tointegerx(L, -1, nullptr); lua_pop(L, 1); // thumbnail_width, prefs } static int appui_selectPage(lua_State *L) { check_appui(L, 1); // not actually used now Document **doc = check_document(L, 2); int page = -1; if (lua_isnumber(L, 3)) { page = lua_tointegerx(L, 3, nullptr); luaL_argcheck(L, 1 <= page && page <= (*doc)->countPages(), 3, "invalid page number"); } int startIndex = 1; if (lua_isnumber(L, 4)) { startIndex = lua_tointegerx(L, 4, nullptr); int maxIndex = (page < 0) ? (*doc)->countPages() : (*doc)->page(page-1)->countViews(); luaL_argcheck(L, 1 <= startIndex && startIndex <= maxIndex, 4, "invalid start index"); } int width, height, thumbWidth; get_page_sorter_size(L, width, height, thumbWidth); int sel = CanvasBase::selectPageOrView(*doc, page - 1, startIndex - 1, thumbWidth, width, height); if (sel >= 0) { lua_pushinteger(L, sel + 1); return 1; } else return 0; } static int appui_pageSorter(lua_State *L) { AppUiBase **ui = check_appui(L, 1); Document **doc = check_document(L, 2); int width, height, thumbWidth; get_page_sorter_size(L, width, height, thumbWidth); return (*ui)->pageSorter(L, *doc, width, height, thumbWidth); } static const char *const render_formats[] = {"svg", "png", "eps", "pdf", nullptr }; static int appui_renderPage(lua_State *L) { // AppUiBase **ui = check_appui(L, 1); // not used Document **doc = check_document(L, 2); int pageno = luaL_checkinteger(L, 3); int viewno = luaL_checkinteger(L, 4); Thumbnail::TargetFormat fm = Thumbnail::TargetFormat(luaL_checkoption(L, 5, nullptr, render_formats)); const char *dst = luaL_checklstring(L, 6, nullptr); double zoom = luaL_checknumber(L, 7); bool transparent = lua_toboolean(L, 8); bool nocrop = lua_toboolean(L, 9); Thumbnail tn(*doc, 0); const Page *page = (*doc)->page(pageno - 1); tn.saveRender(fm, dst, page, viewno - 1, zoom, transparent, nocrop); return 0; } // -------------------------------------------------------------------- static const struct luaL_Reg appui_methods[] = { { "__tostring", appui_tostring }, { "__gc", appui_destructor }, // -------------------------------------------------------------------- { "setPage", appui_setPage}, { "pan", appui_pan}, { "setPan", appui_setPan}, { "zoom", appui_zoom}, { "setZoom", appui_setZoom}, { "setResources", appui_setResources}, { "pos", appui_pos}, { "globalPos", appui_globalPos}, { "unsnappedPos", appui_unsnappedPos}, { "simpleSnapPos", appui_simpleSnapPos }, { "setFifiVisible", appui_setFifiVisible}, { "setInkMode", appui_setInkMode }, { "setSelectionVisible", appui_setSelectionVisible}, { "setSnap", appui_setSnap}, { "setSnapIndicator", appui_setSnapIndicator}, { "setAutoOrigin", appui_setAutoOrigin }, { "update", appui_update}, { "finishTool", appui_finishTool}, { "canvasSize", appui_canvasSize }, { "setCursor", appui_setCursor }, { "setNumbering", appui_setNumbering }, { "setPretty", appui_setPretty }, // -------------------------------------------------------------------- { "panTool", appui_pantool }, { "selectTool", appui_selecttool }, { "transformTool", appui_transformtool }, { "shapeTool", appui_shapetool }, { "pasteTool", appui_pastetool }, // -------------------------------------------------------------------- { "win", appui_win}, { "close", appui_close}, { "setClipboard", appui_setClipboard }, { "clipboard", appui_clipboard }, { "setActionState", appui_setActionState }, { "actionState", appui_actionState }, { "actionInfo", appui_actionInfo }, { "explain", appui_explain }, { "setWindowTitle", appui_setWindowTitle }, { "setupSymbolicNames", appui_setupSymbolicNames }, { "setAttributes", appui_setAttributes }, { "setGridAngleSize", appui_setGridAngleSize }, { "setLayers", appui_setLayers }, { "setNumbers", appui_setNumbers }, { "setBookmarks", appui_setBookmarks }, { "setNotes", appui_setNotes }, { "showTool", appui_showTool }, { "selectPage", appui_selectPage }, { "pageSorter", appui_pageSorter }, { "renderPage", appui_renderPage }, { nullptr, nullptr } }; // -------------------------------------------------------------------- static int appui_constructor(lua_State *L) { luaL_checktype(L, 1, LUA_TTABLE); // this is the model AppUiBase **ui = (AppUiBase **) lua_newuserdata(L, sizeof(AppUiBase *)); *ui = nullptr; luaL_getmetatable(L, "Ipe.appui"); lua_setmetatable(L, -2); lua_pushvalue(L, 1); int model = luaL_ref(L, LUA_REGISTRYINDEX); *ui = createAppUi(L, model); CanvasBase::Style style; style.pretty = false; style.paperColor = Color(1000,1000,1000); style.primarySelectionColor = Color(1000,0,0); style.secondarySelectionColor = Color(1000,0,1000); style.classicGrid = false; style.thinLine = 0.2; style.thickLine = 0.9; style.thinStep = 1; style.thickStep = 4; style.paperClip = false; style.numberPages = false; lua_getglobal(L, "prefs"); lua_getfield(L, -1, "canvas_style"); if (!lua_isnil(L, -1)) { lua_getfield(L, -1, "paper_color"); if (!lua_isnil(L, -1)) style.paperColor = check_color(L, lua_gettop(L)); lua_pop(L, 1); // paper_color lua_getfield(L, -1, "primary_color"); if (!lua_isnil(L, -1)) style.primarySelectionColor = check_color(L, lua_gettop(L)); lua_pop(L, 1); // primary_color lua_getfield(L, -1, "secondary_color"); if (!lua_isnil(L, -1)) style.secondarySelectionColor = check_color(L, lua_gettop(L)); lua_pop(L, 1); // secondary_color lua_getfield(L, -1, "classic_grid"); style.classicGrid = lua_toboolean(L, -1); lua_pop(L, 1); // classic_grid lua_getfield(L, -1, "thin_grid_line"); if (lua_isnumber(L, -1)) style.thinLine = lua_tonumberx(L, -1, nullptr); lua_pop(L, 1); // thin_grid_line lua_getfield(L, -1, "thick_grid_line"); if (lua_isnumber(L, -1)) style.thickLine = lua_tonumberx(L, -1, nullptr); lua_pop(L, 1); // thick_grid_line lua_getfield(L, -1, "thin_step"); if (lua_isnumber(L, -1)) style.thinStep = lua_tointegerx(L, -1, nullptr); lua_pop(L, 1); // thin_step lua_getfield(L, -1, "thick_step"); if (lua_isnumber(L, -1)) style.thickStep = lua_tointegerx(L, -1, nullptr); lua_pop(L, 1); // thick_step } lua_pop(L, 1); // canvas_style int width = -1, height = -1; lua_getfield(L, -1, "window_size"); if (lua_istable(L, -1)) { lua_rawgeti(L, -1, 1); if (lua_isnumber(L, -1)) width = lua_tointegerx(L, -1, nullptr); lua_rawgeti(L, -2, 2); if (lua_isnumber(L, -1)) height = lua_tointegerx(L, -1, nullptr); lua_pop(L, 2); } lua_pop(L, 1); // window_size lua_pop(L, 1); // prefs (*ui)->canvas()->setCanvasStyle(style); (*ui)->showWindow(width, height); return 1; } // -------------------------------------------------------------------- int luaopen_appui(lua_State *L) { lua_pushcfunction(L, appui_constructor); lua_setglobal(L, "AppUi"); make_metatable(L, "Ipe.appui", appui_methods); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/appui_qt.cpp0000644000175000017500000007241213561570220016134 0ustar otfriedotfried// -------------------------------------------------------------------- // AppUi for QT // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "appui_qt.h" #include "ipecanvas_qt.h" #include "controls_qt.h" #include "ipelua.h" #include #include #include #include #include #include #include #include #include #include #include #include #include using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- #define SIZE 16 inline QSize adapt_size(const QSize &size, int factor) { return QSize(factor * size.width() / 100, factor * size.height() / 100); } static bool add_bitmap(QIcon &icon, String base, const char *ext) { if (Platform::fileExists(base + ext)) { icon.addFile(QIpe(base + ext)); return true; } return false; } QIcon prefsIcon(String name) { String dir = ipeIconDirectory(); String base = dir + name; if (Platform::fileExists(base + ".png")) { QIcon icon(QIpe(base + ".png")); if (!add_bitmap(icon, base, "@2x.png")) icon.addPixmap(icon.pixmap(QSize(24, 24)).scaledToHeight(48)); add_bitmap(icon, base, "_32x32.png"); add_bitmap(icon, base, "_32x32@2x.png"); add_bitmap(icon, base, "128.png"); // for application icon add_bitmap(icon, base, "512.png"); // for application icon /* auto l = icon.availableSizes(); for (int i = 0; i < l.size(); ++i) ipeDebug("Icon %s has size %d x %d", name.z(), l[i].width(), l[i].height()); */ return icon; } else return QIcon(); } QPixmap AppUi::prefsPixmap(String name) { QIcon icon = prefsIcon(name); int size = iUiScale * 24 / 100; return icon.pixmap(QSize(size, size)); } QIcon AppUi::prefsColorIcon(Color color) { int size = iUiScale * SIZE / 100; QPixmap pixmap(size, size); pixmap.fill(QIpe(color)); return QIcon(pixmap); } // -------------------------------------------------------------------- QAction *AppUi::findAction(const char *name) const { std::map::const_iterator it = iActions.find(name); if (it != iActions.end()) return it->second; else return nullptr; } void AppUi::addItem(QMenu *m, const QString &title, const char *name) { if (name[0] == '@') { // canUseWhileDrawing = true; name = name + 1; } bool checkable = (m == iMenu[EModeMenu]) || (String(name).find('|') >= 0); if (name[0] == '*') { checkable = true; name = name + 1; } QAction *a = new QAction(title, this); a->setIconVisibleInMenu(false); if (checkable) a->setCheckable(true); lua_getglobal(L, "shortcuts"); lua_getfield(L, -1, name); if (lua_isstring(L, -1)) { QString s = lua_tostring(L, -1); a->setShortcut(QKeySequence(s)); QString tt = title + " [" + s + "]"; a->setToolTip(tt); } a->setIcon(prefsIcon(name)); lua_pop(L, 2); m->addAction(a); if (m == iMenu[EModeMenu]) { a->setActionGroup(iModeActionGroup); iObjectTools->addAction(a); } connect(a, SIGNAL(triggered()), iActionMap, SLOT(map())); iActionMap->setMapping(a, name); iActions[name] = a; } void AppUi::addSnap(const char *name) { QAction *a = findAction(name); assert(a); a->setCheckable(true); iSnapTools->addAction(a); } void AppUi::addEdit(const char *name) { QAction *a = findAction(name); assert(a); iEditTools->addAction(a); } void AppUi::addRootMenu(int id, const char *name) { iMenu[id] = menuBar()->addMenu(name); } // if title and name == 0, add separator (default) void AppUi::addItem(int id, const char *title, const char *name) { if (title == nullptr) iMenu[id]->addSeparator(); else addItem(iMenu[id], QString::fromUtf8(title), name); } static QMenu *submenu = nullptr; static int submenuId = 0; void AppUi::startSubMenu(int id, const char *name, int tag) { submenuId = id; submenu = new QMenu(name); } void AppUi::addSubItem(const char *title, const char *name) { addItem(submenu, title, name); } MENUHANDLE AppUi::endSubMenu() { iMenu[submenuId]->addMenu(submenu); return submenu; } Qt::DockWidgetArea getDockSide(lua_State *L, const char *name, Qt::DockWidgetArea deflt) { Qt::DockWidgetArea r = deflt; lua_getglobal(L, "prefs"); lua_getfield(L, -1, "tools_placement"); if (lua_istable(L, -1)) { lua_getfield(L, -1, name); const char *s = lua_tolstring(L, -1, nullptr); if (!strcmp(s, "left")) r = Qt::LeftDockWidgetArea; else if (!strcmp(s, "right")) r = Qt::RightDockWidgetArea; lua_pop(L, 1); // left or right } lua_pop(L, 2); // prefs, tools_placement return r; } static void set_toolbar_size(QToolBar *bar, int factor) { QSize size = bar->iconSize(); QSize size1 = adapt_size(size, factor); bar->setIconSize(size1); /* ipeDebug("toolbar %s has size %d x %d, changed to %d x %d", bar->windowTitle().toUtf8().constData(), size.width(), size.height(), size1.width(), size1.height()); */ } // -------------------------------------------------------------------- #if QT_VERSION < 0x050000 AppUi::AppUi(lua_State *L0, int model, Qt::WFlags f) #else AppUi::AppUi(lua_State *L0, int model, Qt::WindowFlags f) #endif : QMainWindow(nullptr, f), AppUiBase(L0, model) { setWindowIcon(prefsIcon("ipe")); QMainWindow::setAttribute(Qt::WA_DeleteOnClose); qApp->setAttribute(Qt::AA_UseHighDpiPixmaps); setDockOptions(AnimatedDocks); // do not allow stacking properties and layers Canvas *canvas = new Canvas(this); iCanvas = canvas; setCentralWidget(canvas); iSnapTools = addToolBar("Snap"); iEditTools = addToolBar("Edit"); addToolBarBreak(); iObjectTools = addToolBar("Objects"); ipeDebug("devicePixelRatio: %g", qApp->devicePixelRatio()); set_toolbar_size(iEditTools, iToolbarScale); set_toolbar_size(iSnapTools, iToolbarScale); set_toolbar_size(iObjectTools, iToolbarScale); iActionMap = new QSignalMapper(this); connect(iActionMap, SIGNAL(mapped(const QString &)), SLOT(qAction(const QString &))); iModeActionGroup = new QActionGroup(this); iModeActionGroup->setExclusive(true); QActionGroup *cg = new QActionGroup(this); cg->setExclusive(true); QActionGroup *cs = new QActionGroup(this); cs->setExclusive(true); buildMenus(); findAction("coordinates|points")->setActionGroup(cg); findAction("coordinates|mm")->setActionGroup(cg); findAction("coordinates|m")->setActionGroup(cg); findAction("coordinates|inch")->setActionGroup(cg); for (uint i = 0; i < iScalings.size(); ++i) { char action[32]; sprintf(action, "scaling|%d", iScalings[i]); findAction(action)->setActionGroup(cs); } connect(iSelectLayerMenu, SIGNAL(triggered(QAction *)), SLOT(selectLayerAction(QAction *))); connect(iMoveToLayerMenu, SIGNAL(triggered(QAction *)), SLOT(moveToLayerAction(QAction *))); connect(iTextStyleMenu, SIGNAL(triggered(QAction *)), SLOT(textStyleAction(QAction *))); connect(iLabelStyleMenu, SIGNAL(triggered(QAction *)), SLOT(labelStyleAction(QAction *))); connect(iGridSizeMenu, SIGNAL(triggered(QAction *)), SLOT(gridSizeAction(QAction *))); connect(iAngleSizeMenu, SIGNAL(triggered(QAction *)), SLOT(angleSizeAction(QAction *))); QSignalMapper *comboMap = new QSignalMapper(this); iSelector[EUiGridSize] = new QComboBox(); iSelector[EUiAngleSize] = new QComboBox(); iSelector[EUiGridSize]->setFocusPolicy(Qt::NoFocus); iSelector[EUiAngleSize]->setFocusPolicy(Qt::NoFocus); connect(iSelector[EUiGridSize], SIGNAL(activated(int)), comboMap, SLOT(map())); connect(iSelector[EUiAngleSize], SIGNAL(activated(int)), comboMap, SLOT(map())); comboMap->setMapping(iSelector[EUiGridSize], EUiGridSize); comboMap->setMapping(iSelector[EUiAngleSize], EUiAngleSize); addSnap("snapvtx"); addSnap("snapctl"); addSnap("snapbd"); addSnap("snapint"); addSnap("snapgrid"); iSnapTools->addWidget(iSelector[EUiGridSize]); addSnap("snapangle"); iSnapTools->addWidget(iSelector[EUiAngleSize]); addSnap("snapauto"); addEdit("copy"); addEdit("cut"); addEdit("paste"); addEdit("delete"); addEdit("undo"); addEdit("redo"); addEdit("zoom_in"); addEdit("zoom_out"); addEdit("fit_objects"); addEdit("fit_page"); addEdit("fit_width"); addEdit("keyboard"); iShiftKey = new QAction("shift_key", this); iShiftKey->setCheckable(true); iShiftKey->setIcon(prefsIcon("shift_key")); iEditTools->addAction(iShiftKey); iEditTools->addAction(findAction("grid_visible")); iAbortButton = new QAction("stop", this); iAbortButton->setIcon(prefsIcon("stop")); iEditTools->addAction(iAbortButton); connect(iShiftKey, SIGNAL(triggered()), SLOT(toolbarModifiersChanged())); connect(iAbortButton, SIGNAL(triggered()), SLOT(abortDrawing())); iPropertiesTools = new QDockWidget("Properties", this); addDockWidget(getDockSide(L, "properties", Qt::LeftDockWidgetArea), iPropertiesTools); iPropertiesTools->setAllowedAreas(Qt::LeftDockWidgetArea| Qt::RightDockWidgetArea); iBookmarkTools = new QDockWidget("Bookmarks", this); addDockWidget(getDockSide(L, "bookmarks", Qt::RightDockWidgetArea), iBookmarkTools); iBookmarkTools->setAllowedAreas(Qt::LeftDockWidgetArea| Qt::RightDockWidgetArea); iMenu[EPageMenu]->addAction(iBookmarkTools->toggleViewAction()); iNotesTools = new QDockWidget("Notes", this); addDockWidget(getDockSide(L, "notes", Qt::RightDockWidgetArea), iNotesTools); iNotesTools->setAllowedAreas(Qt::LeftDockWidgetArea| Qt::RightDockWidgetArea); iMenu[EPageMenu]->addAction(iNotesTools->toggleViewAction()); iLayerTools = new QDockWidget("Layers", this); addDockWidget(getDockSide(L, "layers", Qt::LeftDockWidgetArea), iLayerTools); iLayerTools->setAllowedAreas(Qt::LeftDockWidgetArea|Qt::RightDockWidgetArea); // object names are used for saving toolbar state iSnapTools->setObjectName(QLatin1String("SnapTools")); iObjectTools->setObjectName(QLatin1String("ObjectTools")); iPropertiesTools->setObjectName(QLatin1String("PropertiesTools")); iLayerTools->setObjectName(QLatin1String("LayerTools")); iNotesTools->setObjectName(QLatin1String("NotesTools")); iBookmarkTools->setObjectName(QLatin1String("BookmarkTools")); QWidget *wg = new QFrame(); QGridLayout *lo = new QGridLayout(); wg->setLayout(lo); int m = iUiScale * 2 / 100; lo->setSpacing(1); lo->setContentsMargins(m, m, m, m); // l t r b // wg->setMaximumWidth(150); lo->setSizeConstraint(QLayout::SetFixedSize); QButtonGroup *bg = new QButtonGroup(wg); bg->setExclusive(false); connect(bg, SIGNAL(buttonClicked(int)), this, SLOT(absoluteButton(int))); iButton[EUiMarkShape] = nullptr; // no such button for (int i = 0; i <= EUiSymbolSize; ++i) { if (i != EUiMarkShape) { iButton[i] = new QToolButton(); iButton[i]->setFocusPolicy(Qt::NoFocus); bg->addButton(iButton[i], i); lo->addWidget(iButton[i], i > 2 ? i+1 : i, 0); iButton[i]->setIconSize(adapt_size(iButton[i]->iconSize(), iUiScale)); } iSelector[i] = new QComboBox(); iSelector[i]->setFocusPolicy(Qt::NoFocus); lo->addWidget(iSelector[i], i > 2 ? i+1 : i, 1); connect(iSelector[i], SIGNAL(activated(int)), comboMap, SLOT(map())); comboMap->setMapping(iSelector[i], i); } iButton[EUiStroke]->setIcon(prefsColorIcon(Color(1000, 0, 0))); iButton[EUiFill]->setIcon(prefsColorIcon(Color(1000, 1000, 0))); iButton[EUiPen]->setIcon(prefsIcon("pen")); iButton[EUiTextSize]->setIcon(prefsIcon("mode_label")); iButton[EUiSymbolSize]->setIcon(prefsIcon("mode_marks")); iButton[EUiStroke]->setToolTip("Absolute stroke color"); iButton[EUiFill]->setToolTip("Absolute fill color"); iButton[EUiPen]->setToolTip("Absolute pen width"); iButton[EUiTextSize]->setToolTip("Absolute text size"); iButton[EUiSymbolSize]->setToolTip("Absolute symbol size"); iSelector[EUiStroke]->setToolTip("Symbolic stroke color"); iSelector[EUiFill]->setToolTip("Symbolic fill color"); iSelector[EUiPen]->setToolTip("Symbolic pen width"); iSelector[EUiTextSize]->setToolTip("Symbolic text size"); iSelector[EUiMarkShape]->setToolTip("Mark shape"); iSelector[EUiSymbolSize]->setToolTip("Symbolic symbol size"); iSelector[EUiGridSize]->setToolTip("Grid size"); iSelector[EUiAngleSize]->setToolTip("Angle for angular snap"); connect(comboMap, SIGNAL(mapped(int)), this, SLOT(comboSelector(int))); QLabel *msl = new QLabel(); msl->setPixmap(prefsPixmap("mode_marks")); lo->addWidget(msl, EUiMarkShape + 1, 0); iPathView = new PathView(); connect(iPathView, SIGNAL(activated(String)), SLOT(action(String))); connect(iPathView, SIGNAL(showPathStylePopup(Vector)), SLOT(showPathStylePopup(Vector))); lo->addWidget(iPathView, 3, 1, 1, 1); // lo->setRowStretch(3, 1); iPropertiesTools->setWidget(wg); iModeIndicator = new QLabel(); iModeIndicator->setPixmap(prefsPixmap("mode_select")); lo->addWidget(iModeIndicator, 3, 0); QHBoxLayout *hol = new QHBoxLayout(); iViewNumber = new QToolButton(); iPageNumber = new QToolButton(); iViewNumber->setFocusPolicy(Qt::NoFocus); iPageNumber->setFocusPolicy(Qt::NoFocus); iViewNumber->setText("View 1/1"); iViewNumber->setToolTip("Current view number"); iPageNumber->setText("Page 1/1"); iPageNumber->setToolTip("Current page number"); iViewMarked = new QCheckBox(); iPageMarked = new QCheckBox(); iViewMarked->setFocusPolicy(Qt::NoFocus); iPageMarked->setFocusPolicy(Qt::NoFocus); bg->addButton(iViewNumber, EUiView); bg->addButton(iPageNumber, EUiPage); bg->addButton(iViewMarked, EUiViewMarked); bg->addButton(iPageMarked, EUiPageMarked); hol->setSpacing(0); hol->addWidget(iViewMarked); hol->addWidget(iViewNumber); hol->addStretch(1); hol->addWidget(iPageMarked); hol->addWidget(iPageNumber); lo->addLayout(hol, EUiSymbolSize + 2, 0, 1, -1); iPageNotes = new QTextEdit(); iPageNotes->setAcceptRichText(false); iPageNotes->setReadOnly(true); iPageNotes->setFocusPolicy(Qt::NoFocus); iNotesTools->setWidget(iPageNotes); iBookmarks = new QListWidget(); iBookmarks->setToolTip("Bookmarks of this document"); iBookmarks->setFocusPolicy(Qt::NoFocus); connect(iBookmarks, SIGNAL(itemActivated(QListWidgetItem *)), this, SLOT(bookmarkSelected(QListWidgetItem *))); iBookmarkTools->setWidget(iBookmarks); iLayerList = new LayerBox(); iLayerList->setToolTip("Layers of this page"); iLayerTools->setWidget(iLayerList); connect(iLayerList, SIGNAL(activated(String, String)), this, SLOT(layerAction(String, String))); connect(iLayerList, SIGNAL(showLayerBoxPopup(Vector, String)), SLOT(showLayerBoxPopup(Vector, String))); connect(iSelectLayerMenu, SIGNAL(aboutToShow()), this, SLOT(aboutToShowSelectLayerMenu())); connect(iMoveToLayerMenu, SIGNAL(aboutToShow()), this, SLOT(aboutToShowMoveToLayerMenu())); connect(iTextStyleMenu, SIGNAL(aboutToShow()), this, SLOT(aboutToShowTextStyleMenu())); connect(iLabelStyleMenu, SIGNAL(aboutToShow()), this, SLOT(aboutToShowLabelStyleMenu())); connect(iGridSizeMenu, SIGNAL(aboutToShow()), this, SLOT(aboutToShowGridSizeMenu())); connect(iAngleSizeMenu, SIGNAL(aboutToShow()), this, SLOT(aboutToShowAngleSizeMenu())); iSnapIndicator = new QLabel(statusBar()); statusBar()->addPermanentWidget(iSnapIndicator, 0); QFont font = iSnapIndicator->font(); font.setFamily("Monospace"); iSnapIndicator->setFont(font); iMouse = new QLabel(statusBar()); findAction("coordinates|points")->setChecked(true); findAction("scaling|1")->setChecked(true); statusBar()->addPermanentWidget(iMouse, 0); iMouse->setFont(font); iResolution = new QLabel(statusBar()); statusBar()->addPermanentWidget(iResolution, 0); iCanvas->setObserver(this); } AppUi::~AppUi() { ipeDebug("AppUi C++ destructor"); } // -------------------------------------------------------------------- static void populateLayerMenu(LayerBox *layerList, QMenu *menu) { menu->clear(); for (int i = 0; i < layerList->count(); ++i) { LayerItem *item = dynamic_cast(layerList->item(i)); if (item) { QAction *a = new QAction(QIpe(item->ipeLayerName), menu); menu->addAction(a); } } } void AppUi::aboutToShowSelectLayerMenu() { populateLayerMenu(iLayerList, iSelectLayerMenu); } void AppUi::selectLayerAction(QAction *a) { action(String("selectinlayer-") + IpeQ(a->text())); } void AppUi::aboutToShowMoveToLayerMenu() { populateLayerMenu(iLayerList, iMoveToLayerMenu); } void AppUi::moveToLayerAction(QAction *a) { action(String("movetolayer-") + IpeQ(a->text())); } void AppUi::aboutToShowStyleMenu(Kind kind, MENUHANDLE menu, String current) { AttributeSeq seq; iCascade->allNames(kind, seq); menu->clear(); for (uint i = 0; i < seq.size(); ++i) { String s = seq[i].string(); QAction *a = new QAction(QIpe(s), menu); a->setCheckable(true); if (s == current) a->setChecked(true); menu->addAction(a); } } void AppUi::aboutToShowTextStyleMenu() { aboutToShowStyleMenu(ETextStyle, iTextStyleMenu, iAll.iTextStyle.string()); } void AppUi::aboutToShowLabelStyleMenu() { aboutToShowStyleMenu(ELabelStyle, iLabelStyleMenu, iAll.iLabelStyle.string()); } void AppUi::aboutToShowGridSizeMenu() { iGridSizeMenu->clear(); for (auto &name : iComboContents[EUiGridSize]) { QString s = QIpe(name); QAction *a = new QAction(s, iGridSizeMenu); a->setCheckable(true); if (s == iSelector[EUiGridSize]->currentText()) a->setChecked(true); iGridSizeMenu->addAction(a); } } void AppUi::aboutToShowAngleSizeMenu() { iAngleSizeMenu->clear(); for (auto &name : iComboContents[EUiAngleSize]) { QString s = QIpe(name); QAction *a = new QAction(s, iAngleSizeMenu); a->setCheckable(true); if (s == iSelector[EUiAngleSize]->currentText()) a->setChecked(true); iAngleSizeMenu->addAction(a); } } void AppUi::textStyleAction(QAction *a) { action(String("textstyle|") + IpeQ(a->text())); } void AppUi::labelStyleAction(QAction *a) { action(String("labelstyle|") + IpeQ(a->text())); } void AppUi::gridSizeAction(QAction *a) { action(String("gridsize|") + IpeQ(a->text())); } void AppUi::angleSizeAction(QAction *a) { action(String("anglesize|") + IpeQ(a->text())); } void AppUi::toolbarModifiersChanged() { if (iCanvas) { int mod = 0; if (iShiftKey->isChecked()) mod |= CanvasBase::EShift; iCanvas->setAdditionalModifiers(mod); } } void AppUi::abortDrawing() { action("stop"); } // -------------------------------------------------------------------- void AppUi::resetCombos() { for (int i = 0; i < EUiView; ++i) iSelector[i]->clear(); } void AppUi::addComboColors(AttributeSeq &sym, AttributeSeq &abs) { for (uint i = 0; i < sym.size(); ++i) { Color color = abs[i].color(); String s = sym[i].string(); QIcon icon = prefsColorIcon(color); iSelector[EUiStroke]->addItem(icon, QIpe(s)); iSelector[EUiFill]->addItem(icon, QIpe(s)); iComboContents[EUiStroke].push_back(s); iComboContents[EUiFill].push_back(s); } } void AppUi::addCombo(int sel, String s) { iSelector[sel]->addItem(QIpe(s)); } void AppUi::setComboCurrent(int sel, int idx) { iSelector[sel]->setCurrentIndex(idx); } void AppUi::setButtonColor(int sel, Color color) { iButton[sel]->setIcon(prefsColorIcon(color)); } void AppUi::setPathView(const AllAttributes &all, Cascade *sheet) { iPathView->set(all, sheet); } void AppUi::setCheckMark(String name, Attribute a) { String sa = name + "|"; int na = sa.size(); String sb = sa + a.string(); for (std::map::iterator it = iActions.begin(); it != iActions.end(); ++it) { if (it->first.left(na) == sa) it->second->setChecked(it->first == sb); } } void AppUi::setNumbers(String vno, bool vm, String pno, bool pm) { if (vno.empty()) { iViewNumber->hide(); iViewMarked->hide(); } else { iViewNumber->setText(QIpe(vno)); iViewNumber->show(); iViewMarked->setCheckState(vm ? Qt::Checked : Qt::Unchecked); iViewMarked->show(); } if (pno.empty()) { iPageNumber->hide(); iPageMarked->hide(); } else { iPageNumber->show(); iPageMarked->show(); iPageNumber->setText(QIpe(pno)); iPageMarked->setCheckState(pm ? Qt::Checked : Qt::Unchecked); } } void AppUi::setNotes(String notes) { iPageNotes->setPlainText(QIpe(notes)); } void AppUi::setLayers(const Page *page, int view) { iLayerList->set(page, view); } void AppUi::setBookmarks(int no, const String *s) { iBookmarks->clear(); for (int i = 0; i < no; ++i) { QListWidgetItem *item = new QListWidgetItem(QIpe(s[i])); if (s[i][0] == ' ') item->setTextColor(Qt::blue); iBookmarks->addItem(item); } } void AppUi::bookmarkSelected(QListWidgetItem *item) { int index = iBookmarks->row(item); luaBookmarkSelected(index); } void AppUi::setToolVisible(int m, bool vis) { QWidget *tool = nullptr; switch (m) { case 0: tool = iPropertiesTools; break; case 1: tool = iBookmarkTools; break; case 2: tool = iNotesTools; break; case 3: tool = iLayerTools; break; default: break; } if (vis) tool->show(); else tool->hide(); } void AppUi::setZoom(double zoom) { QString s; s.sprintf("(%dppi)", int(72.0 * zoom)); iResolution->setText(s); iCanvas->setZoom(zoom); } // -------------------------------------------------------------------- static void enableActions(QMenu *menu, bool mode) { menu->setEnabled(mode); QListIterator it(menu->actions()); while (it.hasNext()) it.next()->setEnabled(mode); } void AppUi::setActionsEnabled(bool mode) { enableActions(iMenu[EFileMenu], mode); enableActions(iMenu[EEditMenu], mode); enableActions(iMenu[EModeMenu], mode); enableActions(iMenu[EPropertiesMenu], mode); enableActions(iMenu[ELayerMenu], mode); enableActions(iMenu[EViewMenu], mode); enableActions(iMenu[EPageMenu], mode); enableActions(iMenu[EIpeletMenu], mode); iModeActionGroup->setEnabled(mode); iPropertiesTools->setEnabled(mode); iLayerTools->setEnabled(mode); iBookmarkTools->setEnabled(mode); } // -------------------------------------------------------------------- //! Window has been closed void AppUi::closeEvent(QCloseEvent* ce) { // calls model lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "closeEvent"); lua_pushvalue(L, -2); // model lua_remove(L, -3); lua_call(L, 1, 1); bool result = lua_toboolean(L, -1); if (result) ce->accept(); else ce->ignore(); } // -------------------------------------------------------------------- // Determine if action is checked // Used for snapXXX, grid_visible, viewmarked, and pagemarked bool AppUi::actionState(const char *name) { if (!strcmp(name, "viewmarked")) return (iViewMarked->checkState() == Qt::Checked); if (!strcmp(name, "pagemarked")) return (iPageMarked->checkState() == Qt::Checked); QAction *a = findAction(name); if (a) return a->isChecked(); else return 0; } // Check/uncheck an action // Used for snapXXX, grid_visible, to initialize mode_select void AppUi::setActionState(const char *name, bool value) { QAction *a = findAction(name); if (a) a->setChecked(value); } void AppUi::absoluteButton(int id) { luaAbsoluteButton(selectorNames[id]); } void AppUi::selector(int id, String value) { luaSelector(String(selectorNames[id]), value); } void AppUi::comboSelector(int id) { luaSelector(String(selectorNames[id]), IpeQ(iSelector[id]->currentText())); } // -------------------------------------------------------------------- static const char * const aboutText = "

Ipe %d.%d.%d

" "

Copyright (c) 1993-%d Otfried Cheong

" "

The extensible drawing editor Ipe creates figures " "in Postscript and PDF format, " "using LaTeX to format the text in the figures.

" "

Ipe is released under the GNU Public License.

" "

See the Ipe homepage" " for further information.

" "

You can \"like\" Ipe and follow Ipe announcements on " "Facebook.

" "

If you are an Ipe fan and want to show others, have a look at the " "Ipe T-shirts.

" "

Platinum sponsors

" "
  • Hee-Kap Ahn
  • " "
  • Martin Ziegler
" "

If you enjoy Ipe, you can become a member of the exclusive community of " "Ipe patrons. " "For the price of a cup of coffee per month you can make a meaningful contribution " "to the continuing development of Ipe.

" "
"; void AppUi::aboutIpe() { std::vector buf(strlen(aboutText) + 100); sprintf(&buf[0], aboutText, IPELIB_VERSION / 10000, (IPELIB_VERSION / 100) % 100, IPELIB_VERSION % 100, COPYRIGHT_YEAR); QMessageBox msgBox(this); msgBox.setWindowTitle("About Ipe"); msgBox.setWindowIcon(prefsIcon("ipe")); msgBox.setInformativeText(&buf[0]); msgBox.setIconPixmap(prefsPixmap("ipe")); msgBox.setStandardButtons(QMessageBox::Ok); msgBox.exec(); } void AppUi::qAction(const QString &name) { action(IpeQ(name)); } void AppUi::action(String name) { if (name == "fullscreen") { setWindowState(windowState() ^ Qt::WindowFullScreen); } else if (name == "about") { aboutIpe(); } else { if (name.left(5) == "mode_") iModeIndicator->setPixmap(prefsPixmap(name)); luaAction(name); } } // -------------------------------------------------------------------- int AppUi::pageSorter(lua_State *L, Document *doc, int width, int height, int thumbWidth) { QDialog *d = new QDialog(); d->setWindowTitle("Ipe Page Sorter"); QLayout *lo = new QVBoxLayout; PageSorter *p = new PageSorter(doc, thumbWidth); QDialogButtonBox *buttonBox = new QDialogButtonBox(QDialogButtonBox::Ok|QDialogButtonBox::Cancel); lo->addWidget(p); lo->addWidget(buttonBox); d->setLayout(lo); d->connect(buttonBox, SIGNAL(accepted()), SLOT(accept())); d->connect(buttonBox, SIGNAL(rejected()), SLOT(reject())); d->resize(width, height); if (d->exec() == QDialog::Rejected) { delete d; return 0; } lua_createtable(L, p->count(), 0); for (int i = 1; i <= p->count(); ++i) { lua_pushinteger(L, p->pageAt(i-1) + 1); lua_rawseti(L, -2, i); } delete d; return 1; } // -------------------------------------------------------------------- void AppUi::showPathStylePopup(Vector v) { luaShowPathStylePopup(v); } void AppUi::showLayerBoxPopup(Vector v, String layer) { luaShowLayerBoxPopup(v, layer); } void AppUi::layerAction(String name, String layer) { luaLayerAction(name, layer); } // -------------------------------------------------------------------- WINID AppUi::windowId() { return this; } void AppUi::closeWindow() { close(); } void AppUi::setWindowCaption(bool mod, const char *s) { setWindowModified(mod); setWindowTitle(QString::fromUtf8(s)); } void AppUi::setMouseIndicator(const char *s) { iMouse->setText(s); } void AppUi::setSnapIndicator(const char *s) { iSnapIndicator->setText(s); } void AppUi::explain(const char *s, int t) { statusBar()->showMessage(QString::fromUtf8(s), t); } void AppUi::showWindow(int width, int height) { if (width > 0 && height > 0) resize(width, height); show(); } int AppUi::setClipboard(lua_State *L) { QString data = QString::fromUtf8(luaL_checkstring(L, 2)); QClipboard *cb = QApplication::clipboard(); cb->setText(data); return 0; } static int getImage(lua_State *L, QImage &img) { QImage im1 = img.convertToFormat(QImage::Format_ARGB32); int w = im1.width(); int h = im1.height(); Buffer data(w * h * sizeof(uint32_t)); uint32_t *d = (uint32_t *) data.data(); for (int y = 0; y < h; ++y) { uint32_t *p = (uint32_t *) im1.scanLine(y); for (int x = 0; x < w; ++x) { *d++ = *p++; } } Bitmap bitmap(w, h, Bitmap::ENative, data); Rect r(Vector::ZERO, Vector(w, h)); Image *im = new Image(r, bitmap); push_object(L, im); return 1; } int AppUi::clipboard(lua_State *L) { bool allow_bitmap = lua_toboolean(L, 2); QClipboard *cb = QApplication::clipboard(); if (allow_bitmap) { QImage img = cb->image(); if (!img.isNull()) { return getImage(L, img); } } QString data = cb->text(); lua_pushstring(L, data.toUtf8()); return 1; } AppUiBase *createAppUi(lua_State *L0, int model) { return new AppUi(L0, model); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/appui_cocoa.h0000644000175000017500000001244213561570220016236 0ustar otfriedotfried// -*- objc -*- // -------------------------------------------------------------------- // Appui for Cocoa // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef APPUI_COCOA_H #define APPUI_COCOA_H #include "appui.h" using namespace ipe; // -------------------------------------------------------------------- @class IpeCanvasView; @class IpeWindowDelegate; @class IpeAction; @class IpePathView; @class IpeLayerView; @class IpeBookmarksView; class AppUi : public AppUiBase { public: AppUi(lua_State *L0, int model); ~AppUi(); virtual void action(String name) override; virtual void setLayers(const Page *page, int view) override; virtual void setZoom(double zoom) override; virtual void setActionsEnabled(bool mode) override; virtual void setNumbers(String vno, bool vm, String pno, bool pm) override; virtual void setNotes(String notes) override; virtual WINID windowId() override; virtual void closeWindow() override; virtual bool actionState(const char *name) override; virtual void setActionState(const char *name, bool value) override; virtual void setWindowCaption(bool mod, const char *s) override; virtual void explain(const char *s, int t) override; virtual void showWindow(int width, int height) override; virtual void setBookmarks(int no, const String *s) override; virtual void setToolVisible(int m, bool vis) override; virtual int pageSorter(lua_State *L, Document *doc, int width, int height, int thumbWidth) override; virtual int clipboard(lua_State *L) override; virtual int setClipboard(lua_State *L) override; IpeAction *findAction(NSString *name) const; bool actionsEnabled() const { return iActionsEnabled; } BOOL isModified(); BOOL closeRequested(); void absoluteButton(int sel); void snapButton(int sel); void selectorChanged(int sel); void layerMenu(NSPoint p, NSString *layer); void layerAction(NSString *actionName, NSString *layer); void layerToggle(NSString *layer); BOOL validateMenuItem(NSMenuItem *item, NSString *name); void toggleSnapbarShown(); void fillDynamicSubmenu(NSMenuItem *item); private: void createAction(String name, String tooltip, bool canWhileDrawing, bool toggles); void addItem(NSMenu *menu, const char *title, const char *name); void setCheckMark(String name, String value); void makePropertiesTool(); void makeSnapBar(); virtual void addRootMenu(int id, const char *name) override; virtual void addItem(int id, const char *title, const char *name) override; virtual void startSubMenu(int id, const char *name, int tag) override; virtual void addSubItem(const char *title, const char *name) override; virtual MENUHANDLE endSubMenu() override; virtual void setSnapIndicator(const char *s) override; virtual void setMouseIndicator(const char *s) override; virtual void addCombo(int sel, String s) override; virtual void resetCombos() override; virtual void addComboColors(AttributeSeq &sym, AttributeSeq &abs) override; virtual void setComboCurrent(int sel, int idx) override; virtual void setCheckMark(String name, Attribute a) override; virtual void setPathView(const AllAttributes &all, Cascade *sheet) override; virtual void setButtonColor(int sel, Color color) override; private: NSMutableDictionary *iActions; bool iActionsEnabled; bool iInUiUpdate; NSWindow *iWindow; IpeWindowDelegate *iDelegate; NSView *iContent; NSBox *iPropertiesBox; NSBox *iLayerBox; IpeCanvasView *iView; NSTimer *iIndicatorTimer; NSTextField *iStatus; NSTextField *iSnapIndicator; NSTextField *iMouseIndicator; NSTextField *iZoomIndicator; IpePathView *iPathView; IpeLayerView *iLayerView; std::vector iLayerNames; NSButton *iButton[EUiGridSize]; NSPopUpButton *iSelector[EUiView]; NSImageView *iModeIndicator; NSButton *iViewNumber; NSButton *iPageNumber; NSButton *iViewMarked; NSButton *iPageMarked; NSView *iSnapBar; NSButton *iSnapButton[8]; NSLayoutConstraint *iViewToTop; NSLayoutConstraint *iViewToSnapBar; NSPanel *iNotesPanel; NSTextView *iNotesField; NSPanel *iBookmarksPanel; IpeBookmarksView *iBookmarksView; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipe/pagesorter_cocoa.cpp0000644000175000017500000002320113561570220017621 0ustar otfriedotfried// -*- objc -*- // pagesorter_cocoa.cpp /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "appui_cocoa.h" #include "ipethumbs.h" #include "ipelua.h" #include "ipeselector_cocoa.h" #include "ipeuilayout_cocoa.h" using namespace ipe; extern NSSize thumbnail_size; // in ipeselector_cocoa.cpp // -------------------------------------------------------------------- @interface IpePageSorterView : NSBox @property (assign) NSImageView *image; @property (assign) NSTextField *ititle; - (void) ipeSet:(IpeSelectorItem *) item; @end @interface IpePageSorterPrototype : NSCollectionViewItem @end // -------------------------------------------------------------------- @implementation IpePageSorterView - (id) initWithFrame:(NSRect) frameRect { NSSize size = { thumbnail_size.width + 16, thumbnail_size.height + 24 }; self = [super initWithFrame:(NSRect){frameRect.origin, size}]; if (self) { self.titlePosition = NSNoTitle; self.boxType = NSBoxCustom; self.cornerRadius= 8.0; self.borderType = NSLineBorder; NSImageView *v = [[NSImageView alloc] initWithFrame:NSMakeRect(2., 16., thumbnail_size.width, thumbnail_size.height)]; [self addSubview:v]; self.image = v; NSTextField *t = [[NSTextField alloc] initWithFrame:NSMakeRect(2., 0., thumbnail_size.width, 18.)]; t.editable = NO; t.selectable = NO; t.bordered= NO; t.drawsBackground = NO; t.alignment = NSCenterTextAlignment; [self addSubview:t]; self.ititle = t; } return self; } - (void) ipeSet:(IpeSelectorItem *) item { if (!item) return; self.image.image = [item.provider image:item.index]; self.ititle.stringValue = [item.provider title:item.index]; } @end // -------------------------------------------------------------------- @implementation IpePageSorterPrototype - (void) loadView { self.view = [[IpePageSorterView alloc] initWithFrame:NSZeroRect]; } - (void) setRepresentedObject:(id) representedObject { [super setRepresentedObject:representedObject]; [(IpePageSorterView *)[self view] ipeSet:representedObject]; } - (void) setSelected:(BOOL) flag { [super setSelected: flag]; NSBox *view = (NSBox*) [self view]; if (flag) { view.fillColor = [NSColor selectedControlColor]; view.borderColor = [NSColor blackColor]; } else { view.fillColor = [NSColor controlBackgroundColor]; view.borderColor = [NSColor controlBackgroundColor]; } } @end // -------------------------------------------------------------------- @interface IpePageSorterDelegate : NSObject @property NSMutableArray *pages; @property (assign) NSCollectionView *cv; - (void) ipeAccept; - (void) ipeReject; - (void) ipeDelete; @end @implementation IpePageSorterDelegate - (void) ipeAccept { [NSApp stopModalWithCode:1]; } - (void) ipeReject { [NSApp stopModalWithCode:0]; } - (void) ipeDelete { NSIndexSet *idx = [self.cv selectionIndexes]; NSMutableArray *els= [self mutableArrayValueForKey:@"pages"]; [els removeObjectsAtIndexes:idx]; self.cv.selectionIndexes = [NSIndexSet indexSet]; } - (BOOL) windowShouldClose:(id) sender { [NSApp stopModalWithCode:0]; return YES; } - (BOOL) collectionView:(NSCollectionView *) cv writeItemsAtIndexes:(NSIndexSet *) indexes toPasteboard:(NSPasteboard *)pasteboard { NSData *indexData = [NSKeyedArchiver archivedDataWithRootObject:indexes]; [pasteboard setData:indexData forType:@"ipePageSelectorDragId"]; return YES; } - (BOOL) collectionView:(NSCollectionView *) cv canDragItemsAtIndexes:(NSIndexSet *) indexes withEvent:(NSEvent *) event { return YES; } - (BOOL) collectionView:(NSCollectionView *) cv acceptDrop:(id) draggingInfo index:(NSInteger) index dropOperation:(NSCollectionViewDropOperation) dropOperation { NSPasteboard *pBoard = [draggingInfo draggingPasteboard]; NSData *indexData = [pBoard dataForType:@"ipePageSelectorDragId"]; NSIndexSet *idx = [NSKeyedUnarchiver unarchiveObjectWithData:indexData]; NSMutableArray *els= [self mutableArrayValueForKey:@"pages"]; int dest = index - [idx countOfIndexesInRange:NSMakeRange(0, index)]; NSArray *move = [els objectsAtIndexes:idx]; [els removeObjectsAtIndexes:idx]; NSMutableIndexSet *nIdx = [NSMutableIndexSet new]; for (size_t i = 0; i < [move count]; ++i) [nIdx addIndex:dest++]; [els insertObjects:move atIndexes:nIdx]; return YES; } - (NSDragOperation) collectionView:(NSCollectionView *) cv validateDrop:(id) draggingInfo proposedIndex:(NSInteger *) proposedDropIndex dropOperation:(NSCollectionViewDropOperation *) pdo { return NSDragOperationMove; } @end // -------------------------------------------------------------------- int AppUi::pageSorter(lua_State *L, Document *doc, int width, int height, int thumbWidth) { // double the resolution for retina displays Thumbnail thumbs(doc, 2 * thumbWidth); thumbnail_size.width = thumbs.width() / 2.0; thumbnail_size.height = thumbs.height() / 2.0; NSPanel *panel = [[NSPanel alloc] initWithContentRect:NSMakeRect(200., 100., width, height) styleMask:NSTitledWindowMask| NSResizableWindowMask|NSClosableWindowMask backing:NSBackingStoreBuffered defer:YES]; panel.title = @"Ipe: Page sorter"; IpePageSorterDelegate *delegate = [IpePageSorterDelegate new]; panel.delegate = delegate; IpeSelectorProvider *provider = [IpeSelectorProvider new]; provider.doc = doc; provider.thumb = &thumbs; provider.page = -1; delegate.pages = [NSMutableArray arrayWithCapacity:[provider count]]; for (int i = 0; i < [provider count]; ++i) { IpeSelectorItem *item = [IpeSelectorItem new]; item.index = i; item.provider = provider; [delegate.pages addObject:item]; } NSScrollView *scroll = [[NSScrollView alloc] initWithFrame:[panel.contentView frame]]; scroll.autoresizingMask = NSViewWidthSizable|NSViewHeightSizable; scroll.hasVerticalScroller = YES; NSCollectionView *cv = [[NSCollectionView alloc] initWithFrame:NSZeroRect]; cv.autoresizingMask = NSViewWidthSizable|NSViewHeightSizable; scroll.documentView = cv; delegate.cv = cv; cv.itemPrototype = [IpePageSorterPrototype new]; // cv.content = delegate.pages; cv.selectable = YES; cv.allowsMultipleSelection = YES; [cv bind:NSContentBinding toObject:delegate withKeyPath:@"pages" options:nullptr]; cv.delegate = delegate; [cv registerForDraggedTypes:@[@"ipePageSelectorDragId"]]; NSButton *bOk = [[NSButton alloc] initWithFrame:NSZeroRect]; bOk.buttonType = NSMomentaryPushInButton; bOk.title = @"Ok"; bOk.imagePosition = NSNoImage; bOk.bezelStyle = NSRoundedBezelStyle; bOk.action = @selector(ipeAccept); bOk.target = delegate; NSButton *bCancel = [[NSButton alloc] initWithFrame:NSZeroRect]; bCancel.buttonType = NSMomentaryPushInButton; bCancel.title = @"Cancel"; bCancel.imagePosition = NSNoImage; bCancel.bezelStyle = NSRoundedBezelStyle; bCancel.action = @selector(ipeReject); bCancel.target = delegate; NSButton *bDelete = [[NSButton alloc] initWithFrame:NSZeroRect]; bDelete.buttonType = NSMomentaryPushInButton; bDelete.title = @"Delete"; bDelete.imagePosition = NSNoImage; bDelete.bezelStyle = NSRoundedBezelStyle; bDelete.action = @selector(ipeDelete); bDelete.target = delegate; NSView *content = [[NSView alloc] initWithFrame:NSZeroRect]; content.autoresizingMask = NSViewWidthSizable|NSViewHeightSizable; panel.contentView = content; addToLayout(content, scroll); layout(scroll, content, "t=t", 12.0); layout(scroll, content, "l=l", 12.0); layout(content, scroll, "r=r", 12.0); addToLayout(content, bOk); addToLayout(content, bCancel); addToLayout(content, bDelete); layout(content, bOk, "r=r", 12.0); layout(bOk, scroll, "t=b", 12.0); layout(content, bOk, "b=b", 12.0); layout(bOk, bCancel, "l=r", 12.0); layout(bCancel, scroll, "t=b", 12.0); layout(content, bCancel, "b=b", 12.0); layout(bDelete, content, "l=l", 12.0); layout(bDelete, scroll, "t=b", 12.0); layout(content, bDelete, "b=b", 12.0); layout(bCancel, bDelete, "l>r", 12.0); layout(bOk, bCancel, "w=w"); layout(bOk, bDelete, "w=w"); [panel setDefaultButtonCell:[bOk cell]]; // changed rendering int result = [NSApp runModalForWindow:panel]; if (result) { int n = [delegate.pages count]; lua_createtable(L, n, 0); for (int i = 1; i <= n; ++i) { lua_pushinteger(L, delegate.pages[i-1].index + 1); lua_rawseti(L, -2, i); } return 1; } else return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/pagesorter_win.cpp0000644000175000017500000002041713561570220017340 0ustar otfriedotfried// -------------------------------------------------------------------- // Page sorter for Win32 // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "appui_win.h" #include "ipecanvas_win.h" #include "ipethumbs.h" #include "ipeui_wstring.h" #include "ipelua.h" #include #include using namespace ipe; extern HBITMAP createBitmap(uint32_t *p, int w, int h); // -------------------------------------------------------------------- #define IDBASE 9000 #define PAD 3 #define BORDER 6 #define BUTTONHEIGHT 14 static void buildFlags(std::vector &t, DWORD flags) { union { DWORD dw; short s[2]; } a; a.dw = flags; t.push_back(a.s[0]); t.push_back(a.s[1]); t.push_back(0); t.push_back(0); } static void buildString(std::vector &t, const char *s) { const char *p = s; while (*p) t.push_back(*p++); t.push_back(0); } static void buildButton(std::vector &t, UINT flags, int id, int h, int x, const char *s) { if (t.size() % 2 != 0) t.push_back(0); buildFlags(t, flags|WS_CHILD|WS_VISIBLE|BS_TEXT|WS_TABSTOP|BS_FLAT); t.push_back(x); t.push_back(h - BORDER - BUTTONHEIGHT); t.push_back(64); t.push_back(BUTTONHEIGHT); t.push_back(IDBASE + id); t.push_back(0xffff); t.push_back(0x0080); buildString(t, s); t.push_back(0); } // -------------------------------------------------------------------- struct SData { HIMAGELIST hImageList; Document *doc; std::vector pages; std::vector cutlist; }; static void insertItem(HWND h, SData *d, int index, int page) { LVITEM lvI; lvI.mask = LVIF_TEXT | LVIF_IMAGE; lvI.iItem = index; lvI.iImage = page; lvI.iSubItem = 0; Page *p = d->doc->page(page); char buf[16]; String t = p->title(); if (t != "") sprintf(buf, "%d: ", page+1); else sprintf(buf, "Page %d", page+1); WString ws(String(buf) + t); lvI.pszText = ws.data(); (void) ListView_InsertItem(h, &lvI); } static void populateView(HWND lv, SData *d) { // TODO send WM_SETREDRAW (void) ListView_DeleteAllItems(lv); for (int i = 0; i < int(d->pages.size()); ++i) { insertItem(lv, d, i, d->pages[i]); } } static void deleteItems(HWND lv, SData *d, bool cut) { int n = d->pages.size(); if (cut) d->cutlist.clear(); for (int i = n-1; i >= 0; --i) { if (ListView_GetItemState(lv, i, LVIS_SELECTED) & LVIS_SELECTED) { if (cut) d->cutlist.insert(d->cutlist.begin(), d->pages[i]); d->pages.erase(d->pages.begin() + i); } } } static void insertItems(HWND lv, SData *d, int index) { while (!d->cutlist.empty()) { int p = d->cutlist.back(); d->cutlist.pop_back(); d->pages.insert(d->pages.begin() + index, p); } } static void showPopup(HWND parent, POINT pt, int index, SData *d, HWND lv) { int selcnt = ListView_GetSelectedCount(lv); ipeDebug("Index %d, selected %d", index, selcnt); if (index < 0 || selcnt == 0) return; ClientToScreen(parent, &pt); HMENU hMenu = CreatePopupMenu(); if (selcnt > 0) { AppendMenuA(hMenu, MF_STRING, 1, "Delete"); AppendMenuA(hMenu, MF_STRING, 2, "Cut"); } if (!d->cutlist.empty()) { char buf[32]; sprintf(buf, "Insert before page %d", d->pages[index] + 1); AppendMenuA(hMenu, MF_STRING, 3, buf); sprintf(buf, "Insert after page %d", d->pages[index] + 1); AppendMenuA(hMenu, MF_STRING, 4, buf); } int result = TrackPopupMenu(hMenu, TPM_NONOTIFY | TPM_RETURNCMD | TPM_RIGHTBUTTON, pt.x, pt.y, 0, parent, nullptr); DestroyMenu(hMenu); switch (result) { case 1: // Delete deleteItems(lv, d, false); populateView(lv, d); break; case 2: // Cut deleteItems(lv, d, true); populateView(lv, d); break; case 3: // Insert before insertItems(lv, d, index); populateView(lv, d); break; case 4: // Insert after insertItems(lv, d, index+1); populateView(lv, d); break; default: // Menu canceled break; } } static INT_PTR CALLBACK dialogProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { SData *d = (SData *) GetWindowLongPtr(hwnd, GWLP_USERDATA); HWND h = GetDlgItem(hwnd, IDBASE); switch (message) { case WM_INITDIALOG: { d = (SData *) lParam; SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR) d); SendMessage(h, LVM_SETIMAGELIST, (WPARAM) LVSIL_NORMAL, (LPARAM) d->hImageList); populateView(h, d); return TRUE; } case WM_COMMAND: switch (LOWORD(wParam)) { case IDBASE + 1: // Ok EndDialog(hwnd, 1); return TRUE; case IDBASE + 2: // Cancel EndDialog(hwnd, -1); return TRUE; default: return FALSE; } case WM_NOTIFY: switch (((LPNMHDR)lParam)->code) { case NM_RCLICK: showPopup(hwnd, ((LPNMITEMACTIVATE) lParam)->ptAction, ((LPNMITEMACTIVATE) lParam)->iItem, d, h); return TRUE; default: return FALSE; } case WM_CLOSE: EndDialog(hwnd, -1); return TRUE; default: return FALSE; } } // -------------------------------------------------------------------- int AppUi::pageSorter(lua_State *L, Document *doc, int width, int height, int thumbWidth) { SData sData; sData.doc = doc; // Create image list Thumbnail r(doc, thumbWidth); // Image list will be destroyed when ListView is destroyed sData.hImageList = ImageList_Create(thumbWidth, r.height(), ILC_COLOR32, doc->countPages(), 4); for (int i = 0; i < doc->countPages(); ++i) { sData.pages.push_back(i); Page *p = doc->page(i); Buffer bx = r.render(p, p->countViews() - 1); HBITMAP b = createBitmap((uint32_t *) bx.data(), thumbWidth, r.height()); ImageList_Add(sData.hImageList, b, nullptr); } // Convert to dialog units: LONG base = GetDialogBaseUnits(); int baseX = LOWORD(base); int baseY = HIWORD(base); int w = width * 4 / baseX; int h = height * 8 / baseY; std::vector t; // Dialog flags buildFlags(t, WS_POPUP | WS_BORDER | DS_SHELLFONT | WS_SYSMENU | DS_MODALFRAME | WS_CAPTION); t.push_back(3); // no of elements t.push_back(100); // position of popup-window t.push_back(30); t.push_back(w); t.push_back(h); // menu t.push_back(0); // class t.push_back(0); // title buildString(t, "Page sorter"); // for DS_SHELLFONT t.push_back(10); buildString(t,"MS Shell Dlg"); // Page sorter control if (t.size() % 2 != 0) t.push_back(0); buildFlags(t, WS_CHILD|WS_VISIBLE|LVS_ICON|LVS_AUTOARRANGE| WS_VSCROLL|WS_BORDER); t.push_back(BORDER); t.push_back(BORDER); t.push_back(w - 2 * BORDER); t.push_back(h - 2 * BORDER - PAD - BUTTONHEIGHT); t.push_back(IDBASE); buildString(t, WC_LISTVIEWA); t.push_back(0); t.push_back(0); buildButton(t, BS_DEFPUSHBUTTON, 1, h, w - BORDER - 128 - PAD, "Ok"); buildButton(t, BS_PUSHBUTTON, 2, h, w - BORDER - 64, "Cancel"); int res = DialogBoxIndirectParamW(nullptr, (LPCDLGTEMPLATE) &t[0], nullptr, dialogProc, (LPARAM) &sData); if (res == 1) { int n = sData.pages.size(); lua_createtable(L, n, 0); for (int i = 1; i <= n; ++i) { lua_pushinteger(L, sData.pages[i-1] + 1); lua_rawseti(L, -2, i); } return 1; } else return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/tools.h0000644000175000017500000000632613561570220015120 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Canvas tools // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef TOOLS_H #define TOOLS_H #include "ipetool.h" #include "ipecanvas.h" // avoid including Lua headers here typedef struct lua_State lua_State; // -------------------------------------------------------------------- using namespace ipe; extern void push_button(lua_State *L, int button); class IpeTransformTool : public TransformTool { public: IpeTransformTool(CanvasBase *canvas, Page *page, int view, TType type, bool withShift, lua_State *L0, int method); ~IpeTransformTool(); virtual void report(); private: lua_State *L; int iMethod; }; class LuaTool : public Tool { public: LuaTool(CanvasBase *canvas, lua_State *L0, int luatool); ~LuaTool(); void setColor(Color color) { iColor = color; } virtual void mouseButton(int button, bool press); virtual void mouseMove(); virtual bool key(String text, int modifiers); protected: lua_State *L; int iLuaTool; Color iColor; }; class ShapeTool : public LuaTool { public: enum TMarkType { EVertex = 1, ESplineCP, ECenter, ERadius, EMinor, ECurrent, EScissor, ENumMarkTypes }; ShapeTool(CanvasBase *canvas, lua_State *L0, int luatool); void setShape(Shape shape, int which = 0, double pen=1.0); void setSnapping(bool snap, bool skipLast); void clearMarks(); void addMark(const Vector &v, TMarkType t); virtual void draw(Painter &painter) const; virtual void snapVtx(const Vector &mouse, Vector &pos, double &bound, bool cp) const; private: double iPen; Shape iShape; Shape iAuxShape; struct SMark { Vector v; TMarkType t; }; std::vector iMarks; bool iSnap; bool iSkipLast; }; class PasteTool : public LuaTool { public: PasteTool(CanvasBase *canvas, lua_State *L0, int luatool, Object *obj); ~PasteTool(); void setMatrix(Matrix m) { iMatrix = m; } virtual void draw(Painter &painter) const; private: Object *iObject; Matrix iMatrix; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipe/ipe.rc0000644000175000017500000000141713561570220014706 0ustar otfriedotfried#include #define IDI_MYICON 1 IDI_MYICON ICON DISCARDABLE "ipe.ico" VS_VERSION_INFO VERSIONINFO FILEVERSION 7,2,13,1 PRODUCTVERSION 7,2,13,1 FILEFLAGSMASK VS_FF_PRERELEASE FILEFLAGS VS_FF_PRERELEASE FILEOS VOS__WINDOWS32 FILETYPE VFT_APP FILESUBTYPE 0x0L BEGIN BLOCK "StringFileInfo" BEGIN BLOCK "040904B0" BEGIN VALUE "CompanyName", "Otfried Cheong\0" VALUE "FileDescription", "Ipe drawing editor\0" VALUE "FileVersion", "7.2.13\0" VALUE "InternalName", "Ipe\0" VALUE "LegalCopyright", "Copyright (c) 1993-2019\0" VALUE "OriginalFilename", "Ipe.exe\0" VALUE "ProductName", "Ipe\0" VALUE "ProductVersion", "7.2.13\0" END END END CREATEPROCESS_MANIFEST_RESOURCE_ID RT_MANIFEST "ipe.exe.manifest" ipe-7.2.13/src/ipe/appui_gtk.h0000644000175000017500000000721313561570220015737 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Appui for GTK // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef APPUI_GTK_H #define APPUI_GTK_H #include "appui.h" using namespace ipe; // -------------------------------------------------------------------- class AppUi : public AppUiBase { public: AppUi(lua_State *L0, int model); ~AppUi(); virtual void action(String name); virtual void setLayers(const Page *page, int view); virtual void setZoom(double zoom); virtual void setActionsEnabled(bool mode); virtual void setNumbers(String vno, bool vm, String pno, bool pm); virtual void setNotes(String notes); virtual WINID windowId(); virtual void closeWindow(); virtual bool actionState(const char *name); virtual void setActionState(const char *name, bool value); virtual void setWindowCaption(bool mod, const char *s); virtual void explain(const char *s, int t); virtual void showWindow(int width, int height); virtual void setBookmarks(int no, const String *s); virtual void setToolVisible(int m, bool vis); virtual int pageSorter(lua_State *L, Document *doc, int width, int height, int thumbWidth); virtual int clipboard(lua_State *L); virtual int setClipboard(lua_State *L); private: int actionId(const char *name) const; virtual void addRootMenu(int id, const char *name); void addItem(GtkMenuShell *shell, const char *title, const char *name); virtual void addItem(int id, const char *title, const char *name); virtual void startSubMenu(int id, const char *name); virtual void addSubItem(const char *title, const char *name); virtual MENUHANDLE endSubMenu(); virtual void setMouseIndicator(const char *s); virtual void addCombo(int sel, String s); virtual void resetCombos(); virtual void addComboColors(AttributeSeq &sym, AttributeSeq &abs); virtual void setComboCurrent(int sel, int idx); virtual void setCheckMark(String name, Attribute a); virtual void setPathView(const AllAttributes &all, Cascade *sheet); virtual void setButtonColor(int sel, Color color); static void menuitem_cb(GtkWidget *item, gpointer data); private: struct SAction { String name; GtkWidget *menuItem; }; std::vector iActions; GtkWidget *iWindow; GtkWidget *iRootMenu[ENumMenu]; GtkWidget *iSubMenu[ENumMenu]; GtkWidget *iStatusBar; int iStatusBarContextid; GtkWidget *iMousePosition; GtkWidget *iResolution; GtkAccelGroup *iAccelGroup; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipe/controls_cocoa.cpp0000644000175000017500000003020713561570220017315 0ustar otfriedotfried// -*- objc -*- // controls_cocoa.cpp /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "controls_cocoa.h" #include "ipecairopainter.h" #include "ipeuilayout_cocoa.h" #include #include #include @implementation IpePathView { Cascade *iCascade; AllAttributes iAll; } - (instancetype) initWithFrame:(NSRect) rect { self = [super initWithFrame:rect]; if (self) { iCascade = nullptr; } return self; } - (void) setAttributes:(const AllAttributes *) all cascade:(Cascade *) sheet { iCascade = sheet; iAll = *all; [self setNeedsDisplayInRect:[self bounds]]; } - (void) drawRect:(NSRect) rect { NSRect bounds = [self bounds]; int w = bounds.size.width; int h = bounds.size.height; CGContextRef myContext = [[NSGraphicsContext currentContext] CGContext]; cairo_surface_t *sf = cairo_quartz_surface_create_for_cg_context(myContext, w, h); cairo_t *cc = cairo_create(sf); cairo_set_source_rgb(cc, 1, 1, 0.8); cairo_rectangle(cc, 0, 0, w, h); cairo_fill(cc); if (iCascade) { cairo_translate(cc, 0, h); double zoom = 2.0; cairo_scale(cc, zoom, -zoom); Vector v0 = (1.0/zoom) * Vector(0.1 * w, 0.5 * h); Vector v1 = (1.0/zoom) * Vector(0.7 * w, 0.5 * h); Vector u1 = (1.0/zoom) * Vector(0.88 * w, 0.8 * h); Vector u2 = (1.0/zoom) * Vector(0.80 * w, 0.5 * h); Vector u3 = (1.0/zoom) * Vector(0.88 * w, 0.2 * h); Vector u4 = (1.0/zoom) * Vector(0.96 * w, 0.5 * h); CairoPainter painter(iCascade, nullptr, cc, 3.0, false); painter.setPen(iAll.iPen); painter.setDashStyle(iAll.iDashStyle); painter.setStroke(iAll.iStroke); painter.setFill(iAll.iFill); painter.pushMatrix(); painter.newPath(); painter.moveTo(v0); painter.lineTo(v1); painter.drawPath(EStrokedOnly); if (iAll.iFArrow) Path::drawArrow(painter, v1, Angle(0), iAll.iFArrowShape, iAll.iFArrowSize, 100.0); if (iAll.iRArrow) Path::drawArrow(painter, v0, Angle(IpePi), iAll.iRArrowShape, iAll.iRArrowSize, 100.0); painter.setDashStyle(Attribute::NORMAL()); painter.setTiling(iAll.iTiling); painter.newPath(); painter.moveTo(u1); painter.lineTo(u2); painter.lineTo(u3); painter.lineTo(u4); painter.closePath(); painter.drawPath(iAll.iPathMode); painter.popMatrix(); } cairo_destroy(cc); cairo_surface_finish(sf); cairo_surface_destroy(sf); } - (void) mouseDown:(NSEvent *) event { if ([event modifierFlags] & NSControlKeyMask) { [self rightMouseDown:event]; return; } double w = [self bounds].size.width; NSPoint p = [self convertPoint:[event locationInWindow] fromView:nil]; if (p.x < w * 3 / 10) { [self.delegate pathViewAttributeChanged:(iAll.iRArrow ? "rarrow|false" : "rarrow|true")]; } else if (p.x > w * 4 / 10 && p.x < w * 72 / 100) { [self.delegate pathViewAttributeChanged:(iAll.iFArrow ? "farrow|false" : "farrow|true")]; } else if (p.x > w * 78 / 100) { switch (iAll.iPathMode) { case EStrokedOnly: [self.delegate pathViewAttributeChanged:"pathmode|strokedfilled"]; break; case EStrokedAndFilled: [self.delegate pathViewAttributeChanged:"pathmode|filled"]; break; case EFilledOnly: [self.delegate pathViewAttributeChanged:"pathmode|stroked"]; break; } } } - (void) rightMouseDown:(NSEvent *) event { NSRect rw = { [event locationInWindow], { 100.0, 100.0 }}; NSRect rs = [[self window] convertRectToScreen:rw]; [self.delegate pathViewPopup:rs.origin]; } @end // -------------------------------------------------------------------- @interface IpeLayerItem : NSObject @property (copy) NSString *name; @property (copy) NSString *text; @property BOOL checked; @property BOOL active; @property BOOL locked; @property BOOL nosnap; @end @implementation IpeLayerItem @end @interface IpeTableView : NSTableView @end @implementation IpeTableView - (BOOL) acceptsFirstResponder { return NO; } @end @interface IpeLayerField : NSTextField - (void) setItem:(IpeLayerItem *) item inRow:(int) row; @end @implementation IpeLayerField - (void) setItem:(IpeLayerItem *) item inRow:(int) row { self.tag = row; self.editable = NO; self.bordered = NO; self.stringValue = item.text; self.drawsBackground = (item.active || item.locked); if (item.active) self.backgroundColor = [NSColor colorWithRed:1.0 green:1.0 blue:0.0 alpha:1.0]; else if (item.locked) self.backgroundColor = [NSColor colorWithRed:1.0 green:0.85 blue:0.85 alpha:1.0]; if (item.nosnap) self.textColor = [NSColor colorWithRed:0.5 green:0.5 blue:0.5 alpha:1.0]; else if (item.active || item.locked) self.textColor = [NSColor colorWithRed:0 green:0 blue:0 alpha:1.0]; else self.textColor = [NSColor textColor]; } - (void) mouseDown:(NSEvent *) event { [self.target ipeLayerClicked:self.tag]; } - (void) rightMouseDown:(NSEvent *) event { NSRect rw = { [event locationInWindow], { 100.0, 100.0 }}; NSRect rs = [[self window] convertRectToScreen:rw]; [self.target ipeLayerMenuAt:rs.origin forRow:self.tag]; } @end // -------------------------------------------------------------------- @implementation IpeLayerView { NSTableView *iTV; NSMutableArray *iLayers; } - (instancetype) initWithFrame:(NSRect) rect { self = [super initWithFrame:rect]; if (self) { [self setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable]; iLayers = [NSMutableArray arrayWithCapacity:20]; iTV = [[IpeTableView alloc] initWithFrame:rect]; NSTableColumn *column1 = [[NSTableColumn alloc] initWithIdentifier:@"checks"]; [iTV addTableColumn:column1]; NSTableColumn *column2 = [[NSTableColumn alloc] initWithIdentifier:@"names"]; [iTV addTableColumn:column2]; [iTV setHeaderView:nil]; [iTV setSelectionHighlightStyle:NSTableViewSelectionHighlightStyleNone]; [iTV setDataSource:self]; [iTV setDelegate:self]; [iTV setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable]; [self setDocumentView:iTV]; [self setHasVerticalScroller:YES]; layout(self, nil, "h>0", 80.0); layout(self, nil, "w>0", 80.0); } return self; } - (void) setPage:(const Page *) page view:(int) view { std::vector objCounts; page->objectsPerLayer(objCounts); [iLayers removeAllObjects]; int active = -1; for (int i = 0; i < page->countLayers(); ++i) { IpeLayerItem *item = [[IpeLayerItem alloc] init]; item.name = I2N(page->layer(i)); item.text = [NSString stringWithFormat:@"%@ (%d)", I2N(page->layer(i)), objCounts[i]]; item.checked = page->visible(view, i); item.active = (page->layer(i) == page->active(view)); item.locked = page->isLocked(i); item.nosnap = !page->hasSnapping(i); if (page->layer(i) == page->active(view)) active = i; [iLayers addObject:item]; } [iTV reloadData]; [[iTV tableColumnWithIdentifier:@"checks"] sizeToFit]; if (active >= 0) [iTV selectRowIndexes:[NSIndexSet indexSetWithIndex:active] byExtendingSelection:NO]; } - (void) ipeLayerToggled:(id) sender { int row = [sender tag]; if (iLayers[row].checked) [self.delegate layerAction:@"selectoff" forLayer:iLayers[row].name]; else [self.delegate layerAction:@"selecton" forLayer:iLayers[row].name]; } - (void) ipeLayerClicked:(int) row { [self.delegate layerAction:@"active" forLayer:iLayers[row].name]; } - (void) ipeLayerMenuAt:(NSPoint) p forRow:(int) row { [self.delegate layerMenuAt:p forLayer:iLayers[row].name]; } - (NSInteger) numberOfRowsInTableView:(NSTableView *) tv { return [iLayers count]; } - (id) tableView:(NSTableView *) tv objectValueForTableColumn:(NSTableColumn *) col row:(NSInteger)row { if ([[col identifier] isEqualToString:@"checks"]) return [NSNumber numberWithBool:iLayers[row].checked]; else return iLayers[row].text; } - (NSView *) tableView:(NSTableView *) tv viewForTableColumn:(NSTableColumn *) col row:(NSInteger) row { if ([[col identifier] isEqualToString:@"checks"]) { NSButton *result = [tv makeViewWithIdentifier:@"LayerCheck" owner:self]; if (result == nil) { result = [[NSButton alloc] initWithFrame:NSMakeRect(0.,0.,20.,20.)]; [result setButtonType:NSSwitchButton]; [result setImagePosition:NSImageOnly]; } [result setAction:@selector(ipeLayerToggled:)]; [result setTarget:self]; [result setTag:row]; [result setState:iLayers[row].checked]; return result; } else { IpeLayerField *result = [tv makeViewWithIdentifier:@"LayerName" owner:self]; if (result == nil) { result = [[IpeLayerField alloc] initWithFrame:NSMakeRect(0., 0., 200., 20.)]; result.identifier = @"LayerName"; auto cell = [result cell]; [cell setLineBreakMode:NSLineBreakByCharWrapping]; [cell setTruncatesLastVisibleLine:YES]; } [result setItem:iLayers[row] inRow:row]; [result setTarget:self]; return result; } } @end // -------------------------------------------------------------------- @implementation IpeBookmarksView { NSTableView *iTV; NSMutableArray *iBookmarks; } - (instancetype) initWithFrame:(NSRect) rect { self = [super initWithFrame:rect]; if (self) { [self setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable]; iBookmarks = [NSMutableArray arrayWithCapacity:20]; iTV = [[IpeTableView alloc] initWithFrame:rect]; NSTableColumn *column = [[NSTableColumn alloc] initWithIdentifier:@"bookmarks"]; [iTV addTableColumn:column]; [iTV setHeaderView:nil]; [iTV setSelectionHighlightStyle:NSTableViewSelectionHighlightStyleNone]; [iTV setDataSource:self]; [iTV setDelegate:self]; [iTV setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable]; [iTV setUsesAlternatingRowBackgroundColors:YES]; [iTV setAction:@selector(ipeSelectedBookmark:)]; [iTV setTarget:self]; [self setDocumentView:iTV]; [self setHasVerticalScroller:YES]; layout(self, nil, "h>0", 100.0); layout(self, nil, "w>0", 160.0); } return self; } - (void) ipeSelectedBookmark:(id) sender { int row = [sender clickedRow]; if (self.delegate && row >= 0) [self.delegate bookmarkSelected:row]; } - (void) setBookmarks:(int) no fromStrings:(const String *) s { [iBookmarks removeAllObjects]; for (int i = 0; i < no; ++i) [iBookmarks addObject:I2N(s[i].z())]; [iTV reloadData]; } - (NSInteger) numberOfRowsInTableView:(NSTableView *) tv { return [iBookmarks count]; } - (id) tableView:(NSTableView *) tv objectValueForTableColumn:(NSTableColumn *) col row:(NSInteger)row { return iBookmarks[row]; } - (NSView *) tableView:(NSTableView *) tv viewForTableColumn:(NSTableColumn *) col row:(NSInteger) row { NSTextField *result = [tv makeViewWithIdentifier:@"Bookmarks" owner:self]; if (result == nil) { result = [[NSTextField alloc] initWithFrame:NSMakeRect(0., 0., 200., 20.)]; result.identifier = @"Bookmarks"; result.editable = NO; result.bordered = NO; result.drawsBackground = NO; } [result setStringValue:iBookmarks[row]]; return result; } @end // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/pathview_win.cpp0000644000175000017500000001464313561570220017020 0ustar otfriedotfried// -------------------------------------------------------------------- // PathView widget for Win32 // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "controls_win.h" #include "ipecairopainter.h" #include #include using namespace ipe; const wchar_t PathView::className[] = L"ipePathViewClass"; // -------------------------------------------------------------------- PathView::PathView(HWND parent, int id) { iCascade = nullptr; idBase = id; HWND hwnd = CreateWindowExW(WS_EX_CLIENTEDGE, className, L"", WS_CHILD | WS_VISIBLE, 0, 0, 0, 0, parent, nullptr, (HINSTANCE) GetWindowLongPtr(parent, GWLP_HINSTANCE), this); if (hwnd == nullptr) { MessageBoxA(nullptr, "PathView creation failed!", "Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } assert(GetWindowLongPtr(hwnd, GWLP_USERDATA)); } void PathView::set(const AllAttributes &all, Cascade *sheet) { iCascade = sheet; iAll = all; InvalidateRect(hwnd, nullptr, FALSE); } LRESULT CALLBACK PathView::wndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { PathView *pv = (PathView *) GetWindowLongPtr(hwnd, GWLP_USERDATA); switch (message) { case WM_CREATE: { assert(pv == nullptr); LPCREATESTRUCT p = (LPCREATESTRUCT) lParam; pv = (PathView *) p->lpCreateParams; pv->hwnd = hwnd; SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR) pv); } break; case WM_PAINT: if (pv) pv->wndPaint(); return 0; case WM_LBUTTONDOWN: if (pv) pv->button(LOWORD(lParam), HIWORD(lParam)); break; case WM_RBUTTONUP: if (pv) { pv->pos.x = LOWORD(lParam); pv->pos.y = HIWORD(lParam); ClientToScreen(pv->hwnd, (LPPOINT) &pv->pos); SendMessage(GetParent(hwnd), WM_COMMAND, pv->idBase, (LPARAM) hwnd); } break; case WM_DESTROY: delete pv; break; default: break; } return DefWindowProc(hwnd, message, wParam, lParam); } void PathView::wndPaint() { InvalidateRect(hwnd, nullptr, FALSE); RECT rc; GetClientRect(hwnd, &rc); int w = rc.right; int h = rc.bottom; PAINTSTRUCT ps; HDC hdc = BeginPaint(hwnd, &ps); cairo_surface_t *surface = cairo_win32_surface_create(hdc); cairo_t *cc = cairo_create(surface); cairo_set_source_rgb(cc, 1, 1, 0.8); cairo_rectangle(cc, 0, 0, w, h); cairo_fill(cc); if (iCascade) { cairo_translate(cc, 0, h); double zoom = w / 100.0; cairo_scale(cc, zoom, -zoom); Vector v0 = (1.0/zoom) * Vector(0.1 * w, 0.5 * h); Vector v1 = (1.0/zoom) * Vector(0.7 * w, 0.5 * h); Vector u1 = (1.0/zoom) * Vector(0.88 * w, 0.8 * h); Vector u2 = (1.0/zoom) * Vector(0.80 * w, 0.5 * h); Vector u3 = (1.0/zoom) * Vector(0.88 * w, 0.2 * h); Vector u4 = (1.0/zoom) * Vector(0.96 * w, 0.5 * h); CairoPainter painter(iCascade, nullptr, cc, 3.0, false); painter.setPen(iAll.iPen); painter.setDashStyle(iAll.iDashStyle); painter.setStroke(iAll.iStroke); painter.setFill(iAll.iFill); painter.pushMatrix(); painter.newPath(); painter.moveTo(v0); painter.lineTo(v1); painter.drawPath(EStrokedOnly); if (iAll.iFArrow) Path::drawArrow(painter, v1, Angle(0), iAll.iFArrowShape, iAll.iFArrowSize, 80.0); if (iAll.iRArrow) Path::drawArrow(painter, v0, Angle(IpePi), iAll.iRArrowShape, iAll.iRArrowSize, -80.0); painter.setDashStyle(Attribute::NORMAL()); painter.setTiling(iAll.iTiling); painter.newPath(); painter.moveTo(u1); painter.lineTo(u2); painter.lineTo(u3); painter.lineTo(u4); painter.closePath(); painter.drawPath(iAll.iPathMode); painter.popMatrix(); } cairo_surface_flush(surface); cairo_destroy(cc); cairo_surface_destroy(surface); EndPaint(hwnd, &ps); } void PathView::button(int x, int y) { RECT rc; GetClientRect(hwnd, &rc); int w = rc.right; if (x < w * 3 / 10) { iAction = iAll.iRArrow ? "rarrow|false" : "rarrow|true"; SendMessage(GetParent(hwnd), WM_COMMAND, idBase+1, (LPARAM) hwnd); } else if (x > w * 4 / 10 && x < w * 72 / 100) { iAction = iAll.iFArrow ? "farrow|false" : "farrow|true"; SendMessage(GetParent(hwnd), WM_COMMAND, idBase+1, (LPARAM) hwnd); } else if (x > w * 78 / 100) { switch (iAll.iPathMode) { case EStrokedOnly: iAction = "pathmode|strokedfilled"; break; case EStrokedAndFilled: iAction = "pathmode|filled"; break; case EFilledOnly: iAction = "pathmode|stroked"; break; } SendMessage(GetParent(hwnd), WM_COMMAND, idBase+1, (LPARAM) hwnd); } // show new status InvalidateRect(hwnd, nullptr, FALSE); } void PathView::init(HINSTANCE hInstance) { WNDCLASSEX wc; wc.cbSize = sizeof(WNDCLASSEX); wc.style = 0; // CS_VREDRAW | CS_HREDRAW; wc.lpfnWndProc = wndProc; wc.cbClsExtra = 0; wc.cbWndExtra = 0; wc.hInstance = hInstance; wc.hCursor = LoadCursor(nullptr, IDC_ARROW); wc.hbrBackground = (HBRUSH) GetStockObject(NULL_BRUSH); wc.lpszMenuName = nullptr; // actually child id wc.lpszClassName = className; wc.hIcon = nullptr; wc.hIconSm = nullptr; if (!RegisterClassEx(&wc)) { MessageBoxA(nullptr, "PathView control registration failed!", "Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/controls_qt.h0000644000175000017500000000664313561570220016331 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Special widgets for QT // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef CONTROLS_QT_H #define CONTROLS_QT_H #include "ipelib.h" #include using namespace ipe; // -------------------------------------------------------------------- class LayerItem: public QListWidgetItem { public: LayerItem(const QString &text, String name, QListWidget *parent) : QListWidgetItem(text, parent), ipeLayerName(name) { // nothing } String ipeLayerName; }; class LayerBox : public QListWidget { Q_OBJECT public: LayerBox(QWidget *parent = nullptr); void set(const Page *page, int view); signals: void activated(String name, String layer); void showLayerBoxPopup(Vector v, String layer); public slots: void layerChanged(QListWidgetItem *item); protected: virtual void mouseReleaseEvent(QMouseEvent *e); virtual void mousePressEvent(QMouseEvent *e); void addAction(QMenu *m, QListWidgetItem *item, String name, const QString &text); private: bool iInSet; }; // -------------------------------------------------------------------- class PathView : public QWidget { Q_OBJECT public: #if QT_VERSION < 0x050000 PathView(QWidget* parent = nullptr, Qt::WFlags f = nullptr); #else PathView(QWidget* parent = nullptr, Qt::WindowFlags f = nullptr); #endif void set(const AllAttributes &all, Cascade *sheet); virtual QSize sizeHint() const; signals: void activated(String name); void showPathStylePopup(Vector v); protected: virtual void paintEvent(QPaintEvent *ev); virtual void mouseReleaseEvent(QMouseEvent *e); virtual void mousePressEvent(QMouseEvent *e); virtual bool event(QEvent *ev); private: Cascade *iCascade; AllAttributes iAll; }; // -------------------------------------------------------------------- class PageSorter : public QListWidget { Q_OBJECT public: PageSorter(Document *doc, int width, QWidget *parent = nullptr); int pageAt(int r) const; public slots: void deletePages(); void cutPages(); void insertPages(); private: virtual void contextMenuEvent(QContextMenuEvent *event); private: Document *iDoc; QList iCutList; int iActionRow; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipe/appui_cocoa.cpp0000644000175000017500000012332113561570220016570 0ustar otfriedotfried// -*- objc -*- // appui_cocoa.cpp /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "appui_cocoa.h" #include "ipecanvas_cocoa.h" #include "controls_cocoa.h" #include "ipelua.h" #include #include using namespace ipe; using namespace ipelua; #include "ipeuilayout_cocoa.h" // in ipeui_cocoa: extern NSImage *colorIcon(double red, double green, double blue, int pixels); // -------------------------------------------------------------------- static const char * const snapbutton_action[] = { "snapvtx", "snapctl", "snapbd", "snapint", "snapgrid", "snapangle", "snapauto", "grid_visible" }; static const char * const touchbar_action[] = { "escape", "set_origin", "set_direction", "set_line", "show_axes", "reset_direction", "set_tangent_direction", "snapvtx", "snapctl", "snapbd", "snapint", "snapgrid", "snapangle", "snapauto" }; #if MAC_OS_X_VERSION_MAX_ALLOWED >= 101202 static const char * const touchbar_titles[] = { "esc", "org", "dir", "line", "axes", "reset", "tangent", nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr }; static const char * const touchbar_customization_label[] = { "Escape", "Set origin", "Set direction", "Set to edge", "Show axes", "Reset direction", "Set to tangent direction", "Snap to vertex", "Snap to control point", "Snap to boundary", "Snap to intersection", "Snap to grid", "Angular snap", "Automatic snap" }; #endif @interface IpeAction : NSObject @property NSString *name; @property NSString *title; @property BOOL alwaysOn; @property BOOL toggles; // This is the base reference for the state of toggling actions: @property BOOL state; + (instancetype) ipeAction:(NSString *) aName title:(NSString *) aTitle alwaysOn:(BOOL) aAlways toggles:(BOOL) aToggles; @end @implementation IpeAction + (instancetype) ipeAction:(NSString *) aName title:(NSString *) aTitle alwaysOn:(BOOL) aAlways toggles:(BOOL) aToggles { IpeAction *Self = [[IpeAction alloc] init]; Self.name = aName; Self.title = aTitle; Self.alwaysOn = aAlways; Self.toggles = aToggles; Self.state = NO; return Self; } @end // -------------------------------------------------------------------- @implementation IpeMenuItem - (instancetype) initWithTitle:(NSString *) aTitle ipeAction:(NSString *) anIpeAction keyEquivalent:(NSString *) aKey { self = [super initWithTitle:aTitle action:@selector(ipeMenuAction:) keyEquivalent:aKey]; if (self) { _ipeAction = anIpeAction; // make sure these operations work in NSTextField and NSTextView if ([_ipeAction isEqualToString:@"copy"]) self.action = @selector(copy:); else if ([_ipeAction isEqualToString:@"cut"]) self.action = @selector(cut:); else if ([_ipeAction isEqualToString:@"paste"]) self.action = @selector(paste:); else if ([_ipeAction isEqualToString:@"paste_at_cursor"]) self.action = @selector(paste:); else if ([_ipeAction isEqualToString:@"delete"]) self.action = @selector(delete:); else if ([_ipeAction isEqualToString:@"select_all"]) self.action = @selector(selectAll:); else if ([_ipeAction isEqualToString:@"fullscreen"]) self.action = @selector(toggleFullScreen:); // make sure these work when no window exists else if ([@[@"show_configuration", @"new_window", @"open", @"manual", @"about_ipelets"] containsObject:anIpeAction]) self.action = @selector(ipeAlwaysAction:); } return self; } @end // -------------------------------------------------------------------- static NSImage *colorIcon(Color color, int pixels = 24) { double red = color.iRed.toDouble(); double green = color.iGreen.toDouble(); double blue = color.iBlue.toDouble(); return colorIcon(red, green, blue, pixels); } static NSImage *loadIcon(String action) { String dir = ipeIconDirectory(); String fname = dir + action + ".tiff"; if (!Platform::fileExists(fname)) { fname = dir + action + ".png"; if (!Platform::fileExists(fname)) return nil; } return [[NSImage alloc] initWithContentsOfFile:I2N(fname)]; } // -------------------------------------------------------------------- #if MAC_OS_X_VERSION_MAX_ALLOWED < 101202 @protocol NSTouchBarDelegate @end #endif // Window delegate is also an NSWindowController object to handle touch bar @interface IpeWindowDelegate : NSWindowController @end @implementation IpeWindowDelegate { AppUi * appui; } - (instancetype) initFor:(AppUi *) ui { self = [super initWithWindow:nil]; if (self) { appui = ui; } return self; } - (void) ipeSubmenu:(id) sender { NSLog(@"ipeSubmenu: %@", sender); } - (BOOL) validateMenuItem:(NSMenuItem *) item { if ([item respondsToSelector:@selector(ipeAction)]) { NSString *name = [item performSelector:@selector(ipeAction)]; return appui->validateMenuItem(item, name); } if (item.action == @selector(toggleSnapbarShown:)) return appui->validateMenuItem(item, @"snapbar"); if (item.tag >= AppUi::ESubmenuGridSize && item.tag < AppUi::ESubmenuFin) appui->fillDynamicSubmenu(item); return YES; } - (BOOL) ipeIsModified:(id) sender { return appui->isModified(); } - (BOOL) windowShouldClose:(id) sender { return appui->closeRequested(); } // -------------------------------------------------------------------- // These are needed to enable them in other first responders // like NSTextField and NSTextView // Unfortunately undo and redo cannot be handled this way, // as Cocoa would pick up the actions "undo" and "redo" and // reroute them to the applications NSUndoManager. - (void) copy:(id) sender { [self ipeMenuAction:sender]; } - (void) cut:(id) sender { [self ipeMenuAction:sender]; } - (void) paste:(id) sender { [self ipeMenuAction:sender]; } - (void) delete:(id) sender { [self ipeMenuAction:sender]; } - (void) selectAll:(id) sender { [self ipeMenuAction:sender]; } // -------------------------------------------------------------------- - (void) indicatorFired:(NSTimer *) timer { appui->explain("", 0); } - (void) ipeMenuAction:(id) sender { appui->action(N2I([sender ipeAction])); } - (void) ipeToolbarAction:(id) sender { appui->action(N2I([sender itemIdentifier])); } - (void) ipeAbsoluteButton:(id) sender { appui->absoluteButton([sender tag]); } - (void) ipeSnapButton:(id) sender { appui->snapButton([sender tag]); } - (void) ipeSelectorChanged:(id) sender { appui->selectorChanged([sender tag]); } - (void) toggleSnapbarShown:(id) sender { appui->toggleSnapbarShown(); } // -------------------------------------------------------------------- - (void) pathViewAttributeChanged:(String) attr { appui->action(attr); } - (void) pathViewPopup:(NSPoint) p { appui->luaShowPathStylePopup(Vector(p.x, p.y)); } - (void) bookmarkSelected:(int) index { appui->luaBookmarkSelected(index); } - (void) layerMenuAt:(NSPoint) p forLayer:(NSString *) layer; { appui->layerMenu(p, layer); } - (void) layerAction:(NSString *) actionName forLayer:(NSString *) layer { appui->layerAction(actionName, layer); } // -------------------------------------------------------------------- - (void) windowDidEndLiveResize:(NSNotification *) notification { appui->canvas()->update(); } // -------------------------------------------------------------------- - (NSToolbarItem *) toolbar:(NSToolbar *) toolbar itemForItemIdentifier:(NSString *) itemIdentifier willBeInsertedIntoToolbar:(BOOL) flag { NSToolbarItem *t = [[NSToolbarItem alloc] initWithItemIdentifier:itemIdentifier]; t.image = loadIcon(N2I(itemIdentifier)); if (![itemIdentifier hasPrefix:@"mode_"]) t.visibilityPriority = NSToolbarItemVisibilityPriorityLow; t.action = @selector(ipeToolbarAction:); IpeAction *s = appui->findAction(itemIdentifier); if (s) t.toolTip = s.title; return t; } - (NSArray *) toolbarAllowedItemIdentifiers:(NSToolbar *) toolbar { return @[ @"copy", @"cut", @"paste", @"delete", @"undo", @"redo", @"zoom_in", @"zoom_out", @"fit_objects", @"fit_page", @"fit_width", @"keyboard", @"mode_select", @"mode_translate", @"mode_rotate", @"mode_stretch", @"mode_shear", @"mode_graph", @"mode_pan", @"mode_shredder", @"mode_label", @"mode_math", @"mode_paragraph", @"mode_marks", @"mode_rectangles1", @"mode_rectangles2", @"mode_rectangles3", @"mode_parallelogram", @"mode_lines", @"mode_polygons", @"mode_splines", @"mode_splinegons", @"mode_arc1", @"mode_arc2", @"mode_arc3", @"mode_circle1", @"mode_circle2", @"mode_circle3", @"mode_ink", NSToolbarSpaceItemIdentifier, NSToolbarFlexibleSpaceItemIdentifier, ]; } - (NSArray *) toolbarDefaultItemIdentifiers:(NSToolbar *) toolbar { return @[ @"mode_select", @"mode_translate", @"mode_rotate", @"mode_stretch", @"mode_shear", @"mode_graph", @"mode_pan", @"mode_shredder", @"mode_label", @"mode_math", @"mode_paragraph", @"mode_marks", @"mode_rectangles1", @"mode_rectangles2", @"mode_rectangles3", @"mode_parallelogram", @"mode_lines", @"mode_polygons", @"mode_splines", @"mode_splinegons", @"mode_arc1", @"mode_arc2", @"mode_arc3", @"mode_circle1", @"mode_circle2", @"mode_circle3", @"mode_ink", ]; } - (NSArray *) toolbarSelectableItemIdentifiers: (NSToolbar *) toolbar { return @[ @"mode_select", @"mode_translate", @"mode_rotate", @"mode_stretch", @"mode_shear", @"mode_graph", @"mode_pan", @"mode_shredder", @"mode_label", @"mode_math", @"mode_paragraph", @"mode_marks", @"mode_rectangles1", @"mode_rectangles2", @"mode_rectangles2", @"mode_rectangles3", @"mode_parallelogram", @"mode_lines", @"mode_polygons", @"mode_splines", @"mode_splinegons", @"mode_arc1", @"mode_arc2", @"mode_arc3", @"mode_circle1", @"mode_circle2", @"mode_circle3", @"mode_ink" ]; } #if MAC_OS_X_VERSION_MAX_ALLOWED >= 101202 #pragma clang diagnostic push #pragma clang diagnostic ignored "-Wdeprecated-declarations" - (NSTouchBar *) makeTouchBar { NSTouchBar *bar = [[NSTouchBar alloc] init]; bar.delegate = self; bar.defaultItemIdentifiers = @[ @"show_axes", @"set_origin", @"set_direction", @"snapvtx", @"snapctl", @"snapbd", @"snapint", @"snapgrid" ]; bar.customizationIdentifier = @"org.otfried.ipe.mainbar7_2_11"; bar.customizationAllowedItemIdentifiers = @[ @"show_axes", @"set_origin", @"set_direction", @"reset_direction", @"set_line", @"set_tangent_direction", @"snapvtx", @"snapctl", @"snapbd", @"snapint", @"snapgrid", @"snapangle", @"snapauto" ]; bar.escapeKeyReplacementItemIdentifier = @"escape"; return bar; } - (NSTouchBarItem *) touchBar: (NSTouchBar *) bar makeItemForIdentifier: (NSTouchBarItemIdentifier) identifier { String idf = N2I(identifier); for (size_t tag = 0; tag < (sizeof(touchbar_action)/sizeof(const char *)); ++tag) { if (idf == touchbar_action[tag]) { NSCustomTouchBarItem *item = [[NSCustomTouchBarItem alloc] initWithIdentifier:identifier]; auto title = touchbar_titles[tag]; NSButton *b; if (title == nullptr) { auto image = loadIcon(touchbar_action[tag]); b = [NSButton buttonWithTitle:identifier image:image target:self action:@selector(ipeTouchBar:)]; b.buttonType = NSPushOnPushOffButton; b.imagePosition = NSImageOnly; } else { b = [NSButton buttonWithTitle:C2N(title) target:self action:@selector(ipeTouchBar:)]; if (idf == "show_axes") b.buttonType = NSPushOnPushOffButton; } b.tag = tag; item.view = b; item.customizationLabel = C2N(touchbar_customization_label[tag]); return item; } } return nil; } #pragma clang diagnostic pop #endif - (void) ipeTouchBar:(id) sender { appui->action(touchbar_action[[sender tag]]); } @end // -------------------------------------------------------------------- static bool build_menus = true; void AppUi::addRootMenu(int id, const char *name) { // menus are already in mainmenu.xib } void AppUi::addItem(NSMenu *menu, const char *title, const char *name) { if (title == nullptr) { if (build_menus) [menu addItem:[NSMenuItem separatorItem]]; } else { bool canUseWhileDrawing = false; bool toggles = false; if (name[0] == '@') { canUseWhileDrawing = true; name = name + 1; } if (name[0] == '*') { toggles = true; name += 1; } // check for shortcut lua_getglobal(L, "shortcuts"); lua_getfield(L, -1, name); String sc; if (lua_isstring(L, -1)) sc = lua_tostring(L, -1); lua_pop(L, 2); // shortcuts, shortcuts[name] String tooltip = title; if (!sc.empty()) tooltip = tooltip + " [" + sc + "]"; NSString *nsName = C2N(name); IpeAction *s = [IpeAction ipeAction:nsName title:I2N(tooltip) alwaysOn:canUseWhileDrawing toggles:toggles]; iActions[nsName] = s; if (!build_menus) return; uint mask = 0; if (sc.hasPrefix("Control+")) { sc = sc.substr(8); mask |= NSControlKeyMask; } if (sc.hasPrefix("Ctrl+")) { sc = sc.substr(5); mask |= NSCommandKeyMask; } if (sc.hasPrefix("Command+")) { sc = sc.substr(8); mask |= NSCommandKeyMask; } if (sc.hasPrefix("Shift+")) { sc = sc.substr(6); mask |= NSShiftKeyMask; } if (sc.hasPrefix("Alt+")) { sc = sc.substr(4); mask |= NSAlternateKeyMask; } unichar code = 0; if (sc.size() == 1) { if ('A' <= sc[0] && sc[0] <= 'Z') code = sc[0] + 0x20; else code = sc[0]; } else if (!sc.empty()) { if (sc[0] == 'F') code = 0xf703 + Lex(sc.substr(1)).getInt(); else if (sc == "backspace") code = 8; else if (sc == "delete") code = 127; else if (sc == "Up") code = NSUpArrowFunctionKey; else if (sc == "Down") code = NSDownArrowFunctionKey; else if (sc == "Left") code = NSLeftArrowFunctionKey; else if (sc == "Right") code = NSRightArrowFunctionKey; else if (sc == "End") code = NSEndFunctionKey; else if (sc == "Home") code = NSHomeFunctionKey; else if (sc == "PgUp") code = NSPageUpFunctionKey; else if (sc == "PgDown") code = NSPageDownFunctionKey; } NSString *keyEq = @""; if (code) keyEq = [NSString stringWithFormat:@"%C", code]; NSMenuItem *item = [[IpeMenuItem alloc] initWithTitle:ipeui_set_mnemonic(I2N(title), nil) ipeAction:C2N(name) keyEquivalent:keyEq]; [item setKeyEquivalentModifierMask:mask]; [menu addItem:item]; } } void AppUi::addItem(int id, const char *title, const char *name) { NSMenu *menu = [[[NSApp mainMenu] itemAtIndex:(id + 1)] submenu]; addItem(menu, title, name); } static NSMenu * __unsafe_unretained current_submenu = nullptr; void AppUi::startSubMenu(int id, const char *name, int tag) { if (!build_menus) return; NSMenu *menu = [[[NSApp mainMenu] itemAtIndex:(id + 1)] submenu]; NSString *title = ipeui_set_mnemonic(C2N(name), nil); NSMenuItem *item = [[NSMenuItem alloc] initWithTitle:title action:nullptr keyEquivalent:@""]; NSMenu *submenu = [[NSMenu alloc] initWithTitle:title]; item.submenu = submenu; if (tag) { item.tag = tag; item.action = @selector(ipeSubmenu:); } [menu addItem:item]; current_submenu = submenu; } void AppUi::addSubItem(const char *title, const char *name) { addItem(current_submenu, title, name); } MENUHANDLE AppUi::endSubMenu() { return current_submenu; } // -------------------------------------------------------------------- AppUi::AppUi(lua_State *L0, int model) : AppUiBase(L0, model) { NSRect e = [[NSScreen mainScreen] frame]; auto h = e.size.height; auto w = e.size.width; NSRect contentRect = NSMakeRect(0.125 * w, 0.125 * h, 0.75 * w, 0.75 * h); NSRect subRect = NSMakeRect(0., 0., 100., 100.); iIndicatorTimer = nil; iActionsEnabled = true; iWindow = [[NSWindow alloc] initWithContentRect:contentRect styleMask:NSTitledWindowMask|NSClosableWindowMask| NSResizableWindowMask|NSMiniaturizableWindowMask backing:NSBackingStoreBuffered defer:YES]; iView = [[IpeCanvasView alloc] initWithFrame:subRect]; iCanvas = iView.canvas; iCanvas->setObserver(this); iDelegate = [[IpeWindowDelegate alloc] initFor:this]; [iWindow setDelegate:iDelegate]; [iWindow setAcceptsMouseMovedEvents:YES]; iActions = [NSMutableDictionary dictionaryWithCapacity:100]; buildMenus(); build_menus = false; // all Windows share the same main menu NSToolbar *tb = [[NSToolbar alloc] initWithIdentifier:@"Tools"]; [tb setDelegate:iDelegate]; [tb setDisplayMode:NSToolbarDisplayModeIconOnly]; [tb setAllowsUserCustomization:YES]; [tb setAutosavesConfiguration:YES]; [tb setSizeMode:NSToolbarSizeModeSmall]; [iWindow setToolbar:tb]; [iWindow setWindowController:iDelegate]; iContent = [[NSView alloc] initWithFrame:contentRect]; makePropertiesTool(); iLayerBox = [[NSBox alloc] initWithFrame:subRect]; iLayerBox.title = @"Layers"; NSRect layerFrame = [iLayerBox.contentView frame]; iLayerView = [[IpeLayerView alloc] initWithFrame:layerFrame]; iLayerView.delegate = iDelegate; iLayerView.toolTip = @"Layers of this page"; iLayerBox.contentView = iLayerView; iStatus = [[NSTextField alloc] initWithFrame:NSZeroRect]; iStatus.editable = NO; iStatus.selectable = NO; iStatus.drawsBackground = NO; iSnapIndicator = [[NSTextField alloc] initWithFrame:NSZeroRect]; iSnapIndicator.editable = NO; iSnapIndicator.selectable = NO; iSnapIndicator.drawsBackground = NO; iSnapIndicator.font = [NSFont userFixedPitchFontOfSize:11.0]; iMouseIndicator = [[NSTextField alloc] initWithFrame:NSZeroRect]; iMouseIndicator.editable = NO; iMouseIndicator.selectable = NO; iMouseIndicator.drawsBackground = NO; iMouseIndicator.font = [NSFont userFixedPitchFontOfSize:11.0]; iZoomIndicator = [[NSTextField alloc] initWithFrame:NSZeroRect]; iZoomIndicator.editable = NO; iZoomIndicator.selectable = NO; iZoomIndicator.drawsBackground = NO; makeSnapBar(); addToLayout(iContent, iView); addToLayout(iContent, iPropertiesBox); addToLayout(iContent, iLayerBox); addToLayout(iContent, iSnapBar); addToLayout(iContent, iStatus); addToLayout(iContent, iSnapIndicator); addToLayout(iContent, iMouseIndicator); addToLayout(iContent, iZoomIndicator); layout(iSnapBar, iContent, "t=t"); layout(iSnapBar, iContent, "r=r"); layout(iSnapBar, iView, "l=l"); layout(iPropertiesBox, iContent, "l=l"); layout(iPropertiesBox, iContent, "t=t"); layout(iPropertiesBox, iView, "r=l"); layout(iView, iContent, "r=r"); layout(iView, iStatus, "b=t"); layout(iLayerBox, iContent, "l=l"); layout(iLayerBox, iView, "r=l"); layout(iLayerBox, iPropertiesBox, "t=b"); layout(iLayerBox, iStatus, "b=t"); layout(iStatus, iContent, "l=l"); layout(iStatus, iContent, "b=b"); layout(iStatus, iSnapIndicator, "r=l"); layout(iSnapIndicator, iMouseIndicator, "r=l"); layout(iMouseIndicator, iZoomIndicator, "r=l"); layout(iZoomIndicator, iContent, "r=r"); iViewToSnapBar = layout(iView, iSnapBar, "t=b", 0.0, 1.0, NO); iViewToTop = layout(iView, iContent, "t=t", 0.0, 1.0, NO); activateConstraint(iViewToSnapBar, YES); [iStatus setContentHuggingPriority:NSLayoutPriorityDefaultLow forOrientation:NSLayoutConstraintOrientationHorizontal]; [iSnapIndicator setContentHuggingPriority:NSLayoutPriorityDefaultHigh forOrientation:NSLayoutConstraintOrientationHorizontal]; [iMouseIndicator setContentHuggingPriority:NSLayoutPriorityDefaultHigh forOrientation:NSLayoutConstraintOrientationHorizontal]; [iZoomIndicator setContentHuggingPriority:NSLayoutPriorityDefaultHigh forOrientation:NSLayoutConstraintOrientationHorizontal]; [iWindow setContentView:iContent]; setCheckMark("coordinates|", "points"); setCheckMark("scaling|", "1"); } AppUi::~AppUi() { NSLog(@"~AppUi"); } // -------------------------------------------------------------------- void AppUi::makePropertiesTool() { iPropertiesBox = [[NSBox alloc] initWithFrame:NSMakeRect(0.,0.,50.,300.)]; [iPropertiesBox setTitle:@"Properties"]; for (int i = 0; i <= EUiSymbolSize; ++i) { iButton[i] = [[NSButton alloc] initWithFrame:NSMakeRect(0., 0., 20., 20.)]; [iButton[i] setButtonType:NSMomentaryPushInButton]; [iButton[i] setImagePosition:NSImageOnly]; [iButton[i] setBezelStyle:NSRegularSquareBezelStyle]; iButton[i].action = @selector(ipeAbsoluteButton:); iButton[i].tag = i; addToLayout(iPropertiesBox, iButton[i]); iSelector[i] = [[NSPopUpButton alloc] initWithFrame:NSMakeRect(0., 0., 50., 20.) pullsDown:NO]; iSelector[i].target = iDelegate; iSelector[i].action = @selector(ipeSelectorChanged:); iSelector[i].tag = i; addToLayout(iPropertiesBox, iSelector[i]); } iButton[EUiMarkShape].enabled = NO; // [iButton[EUiMarkShape] setImageDimsWhenDisabled:NO]; iModeIndicator = [[NSImageView alloc] initWithFrame:NSMakeRect(0, 0, 20, 20)]; iModeIndicator.editable = NO; iModeIndicator.image = loadIcon("mode_select"); addToLayout(iPropertiesBox, iModeIndicator); [iButton[EUiStroke] setImage:colorIcon(Color(1000, 0, 0))]; [iButton[EUiFill] setImage:colorIcon(Color(1000, 1000, 0))]; [iButton[EUiPen] setImage:loadIcon("pen")]; [iButton[EUiTextSize] setImage:loadIcon("mode_label")]; [iButton[EUiMarkShape] setImage:loadIcon("mode_marks")]; [iButton[EUiSymbolSize] setImage:loadIcon("mode_marks")]; [iButton[EUiStroke] setToolTip:@"Absolute stroke color"]; [iButton[EUiFill] setToolTip:@"Absolute fill color"]; [iButton[EUiPen] setToolTip:@"Absolute pen width"]; [iButton[EUiTextSize] setToolTip:@"Absolute text size"]; [iButton[EUiSymbolSize] setToolTip:@"Absolute symbol size"]; [iSelector[EUiStroke] setToolTip:@"Symbolic stroke color"]; [iSelector[EUiFill] setToolTip:@"Symbolic fill color"]; [iSelector[EUiPen] setToolTip:@"Symbolic pen width"]; [iSelector[EUiTextSize] setToolTip:@"Symbolic text size"]; [iSelector[EUiMarkShape] setToolTip:@"Mark shape"]; [iSelector[EUiSymbolSize] setToolTip:@"Symbolic symbol size"]; iViewNumber = [[NSButton alloc] initWithFrame:NSMakeRect(0, 0, 10, 20)]; [iViewNumber setButtonType:NSMomentaryPushInButton]; [iViewNumber setTitle:@""]; [iViewNumber setToolTip:@"Current view number"]; [iViewNumber setImagePosition:NSNoImage]; [iViewNumber setBezelStyle:NSRoundedBezelStyle]; [iViewNumber setAction:@selector(ipeAbsoluteButton:)]; [iViewNumber setTag:EUiView]; addToLayout(iPropertiesBox, iViewNumber); iPageNumber = [[NSButton alloc] initWithFrame:NSMakeRect(0, 0, 10, 20)]; [iPageNumber setButtonType:NSMomentaryPushInButton]; [iPageNumber setTitle:@""]; [iPageNumber setToolTip:@"Current page number"]; [iPageNumber setImagePosition:NSNoImage]; [iPageNumber setBezelStyle:NSRoundedBezelStyle]; [iPageNumber setAction:@selector(ipeAbsoluteButton:)]; [iPageNumber setTag:EUiPage]; addToLayout(iPropertiesBox, iPageNumber); iPathView = [[IpePathView alloc] initWithFrame:NSMakeRect(0, 0, 150, 30)]; iPathView.delegate = iDelegate; iPathView.toolTip = @"Toggle arrows, toggle fill mode, right-click for path style"; addToLayout(iPropertiesBox, iPathView); iViewMarked = [[NSButton alloc] initWithFrame:NSMakeRect(0, 0, 10, 10)]; [iViewMarked setButtonType:NSSwitchButton]; [iViewMarked setTitle:@"Mark view"]; [iViewMarked setToolTip:@"Current view marked"]; [iViewMarked setAction:@selector(ipeAbsoluteButton:)]; [iViewMarked setTag:EUiViewMarked]; iViewMarked.font = [NSFont labelFontOfSize:9.0]; addToLayout(iPropertiesBox, iViewMarked); iPageMarked = [[NSButton alloc] initWithFrame:NSMakeRect(0, 0, 10, 10)]; [iPageMarked setButtonType:NSSwitchButton]; [iPageMarked setTitle:@"Mark page"]; [iPageMarked setToolTip:@"Current page marked"]; [iPageMarked setAction:@selector(ipeAbsoluteButton:)]; [iPageMarked setTag:EUiPageMarked]; iPageMarked.font = [NSFont labelFontOfSize:9.0]; addToLayout(iPropertiesBox, iPageMarked); NSView *inside = [iPropertiesBox contentView]; id guide = layoutGuide(iPropertiesBox); layout(iButton[EUiStroke], inside, "t=t", 2.0); for (int i = 0; i <= EUiSymbolSize; ++i) { layout(iButton[i], iButton[i], "w=h"); layout(iButton[i], inside, "l=l"); layout(iButton[i], guide, "r=l"); layout(guide, iSelector[i], "r=l"); layout(iSelector[i], inside, "r=r"); layout(iSelector[i], iButton[i], "y=y"); if (i != EUiStroke && i != EUiTextSize) layout(iButton[i], iButton[i-1], "t=b", 2.0); } layout(guide, inside, "t=t"); layout(guide, inside, "b=b"); layout(iPathView, iButton[EUiPen], "t=b", 2.0); layout(iButton[EUiTextSize], iPathView, "t=b", 2.0); layout(iPathView, guide, "l=r"); layout(iPathView, inside, "r=r"); layout(iModeIndicator, iPathView, "t=t"); layout(iModeIndicator, iPathView, "b=b"); layout(iModeIndicator, inside, "l=l"); layout(iModeIndicator, guide, "r=l"); layout(iViewNumber, iButton[EUiSymbolSize], "t=b", 2.0); layout(iViewNumber, inside, "l=l"); layout(iPageNumber, iViewNumber, "l=r", 2.0); layout(iPageNumber, iViewNumber, "t=t"); layout(iPageNumber, inside, "r=r"); layout(iViewMarked, iViewNumber, "t=b", 2.0); layout(iViewMarked, inside, "l=l"); layout(iPageMarked, iViewMarked, "t=t"); layout(iPageMarked, iViewMarked, "l>r", 2.0); layout(iPageMarked, inside, "r=r"); layout(inside, iViewMarked, "b=b", 5.0); layout(guide, nil, "w=0", 5.0); layout(iPathView, iPathView, "h=w", 0.0, 0.3); layout(iViewNumber, iPageNumber, "w=w"); layout(iModeIndicator, iModeIndicator, "w=h"); } void AppUi::makeSnapBar() { const auto MARGIN = 3.0; const auto PAD = 2.0; iSnapBar = [[NSView alloc] initWithFrame:NSMakeRect(0., 0., 600., 32.)]; for (int i = 0; i < 8; ++i) { iSnapButton[i] = [[NSButton alloc] initWithFrame:NSMakeRect(0, 0, 32, 32)]; iSnapButton[i].buttonType = NSPushOnPushOffButton; iSnapButton[i].imagePosition = NSImageOnly; iSnapButton[i].image = loadIcon(snapbutton_action[i]); iSnapButton[i].bezelStyle = NSRegularSquareBezelStyle; iSnapButton[i].action = @selector(ipeSnapButton:); iSnapButton[i].tag = i; IpeAction *s = findAction(C2N(snapbutton_action[i])); if (s) iSnapButton[i].toolTip = s.title; addToLayout(iSnapBar, iSnapButton[i]); } iSelector[EUiGridSize] = [[NSPopUpButton alloc] initWithFrame:NSMakeRect(0, 0, 100, 40) pullsDown:NO]; iSelector[EUiGridSize].toolTip = @"Grid size"; iSelector[EUiGridSize].target = iDelegate; iSelector[EUiGridSize].action = @selector(ipeSelectorChanged:); iSelector[EUiGridSize].tag = EUiGridSize; addToLayout(iSnapBar, iSelector[EUiGridSize]); iSelector[EUiAngleSize] = [[NSPopUpButton alloc] initWithFrame:NSMakeRect(0, 0, 100, 40) pullsDown:NO]; iSelector[EUiAngleSize].toolTip = @"Angle for angular snap"; iSelector[EUiAngleSize].target = iDelegate; iSelector[EUiAngleSize].action = @selector(ipeSelectorChanged:); iSelector[EUiAngleSize].tag = EUiAngleSize; addToLayout(iSnapBar, iSelector[EUiAngleSize]); for (int i = 0; i < 8; ++i) { layout(iSnapButton[i], iSnapBar, "t=t", MARGIN); layout(iSnapBar, iSnapButton[i], "b=b", MARGIN); if (0 < i && i < 5) layout(iSnapButton[i], iSnapButton[i-1], "l=r", PAD); } layout(iSelector[EUiGridSize], iSnapBar, "t=t", MARGIN); layout(iSelector[EUiAngleSize], iSnapBar, "t=t", MARGIN); layout(iSnapBar, iSelector[EUiGridSize], "b>b", MARGIN); layout(iSnapBar, iSelector[EUiAngleSize], "b>b", MARGIN); layout(iSelector[EUiGridSize], nil, "w>0", 160); layout(iSelector[EUiAngleSize], nil, "w>0", 100); layout(iSnapButton[0], iSnapBar, "l=l", MARGIN); layout(iSelector[EUiGridSize], iSnapButton[4], "l=r", PAD); layout(iSnapButton[5], iSelector[EUiGridSize], "l=r", PAD); layout(iSelector[EUiAngleSize], iSnapButton[5], "l=r", PAD); layout(iSnapButton[6], iSelector[EUiAngleSize], "l=r", PAD); layout(iSnapButton[7], iSnapButton[6], "l>r", PAD); layout(iSnapBar, iSnapButton[7], "r=r", MARGIN); } // -------------------------------------------------------------------- void AppUi::resetCombos() { iInUiUpdate = true; for (int i = 0; i < EUiView; ++i) [iSelector[i] removeAllItems]; iInUiUpdate = false; } void AppUi::addComboColors(AttributeSeq &sym, AttributeSeq &abs) { iInUiUpdate = true; for (uint i = 0; i < sym.size(); ++i) { Color color = abs[i].color(); NSImage *im = colorIcon(color, 12); String s = sym[i].string(); [iSelector[EUiStroke] addItemWithTitle:I2N(s)]; [iSelector[EUiFill] addItemWithTitle:I2N(s)]; [iSelector[EUiStroke] lastItem].image = im; [iSelector[EUiFill] lastItem].image = im; iComboContents[EUiStroke].push_back(s); iComboContents[EUiFill].push_back(s); } iInUiUpdate = false; } void AppUi::addCombo(int sel, String s) { iInUiUpdate = true; [iSelector[sel] addItemWithTitle:I2N(s)]; iInUiUpdate = false; } void AppUi::setComboCurrent(int sel, int idx) { iInUiUpdate = true; [iSelector[sel] selectItemAtIndex:idx]; iInUiUpdate = false; } void AppUi::setButtonColor(int sel, Color color) { [iButton[sel] setImage:colorIcon(color)]; } void AppUi::setPathView(const AllAttributes &all, Cascade *sheet) { [iPathView setAttributes:&all cascade:sheet]; } void AppUi::setCheckMark(String name, Attribute a) { setCheckMark(name + "|", a.string()); } void AppUi::setCheckMark(String name, String value) { // deselect all from category NSString *prefix = I2N(name); for (NSString *action in iActions) { if ([action hasPrefix:prefix]) iActions[action].state = NO; } iActions[I2N(name + value)].state = YES; } void AppUi::setLayers(const Page *page, int view) { iLayerNames.clear(); for (int i = 0; i < page->countLayers(); ++i) iLayerNames.push_back(page->layer(i)); [iLayerView setPage:page view:view]; } void AppUi::setActionsEnabled(bool mode) { iActionsEnabled = mode; } void AppUi::setNumbers(String vno, bool vm, String pno, bool pm) { iViewNumber.title = I2N(vno); iPageNumber.title = I2N(pno); iViewMarked.state = vm ? NSOnState : NSOffState; iPageMarked.state = pm ? NSOnState : NSOffState; iViewNumber.enabled = !vno.empty(); iViewMarked.enabled = !vno.empty(); iPageNumber.enabled = !pno.empty(); iPageMarked.enabled = !pno.empty(); } BOOL AppUi::validateMenuItem(NSMenuItem *item, NSString *name) { if ([name isEqualToString:@"snapbar"]) { item.title = [iSnapBar isHidden] ? @"Show Snap Toolbar" : @"Hide Snap Toolbar"; return YES; } IpeAction *s = findAction(name); if (s) { if ([name isEqualToString:@"toggle_notes"]) s.state = (iNotesPanel && [iNotesPanel isVisible]); else if ([name isEqualToString:@"toggle_bookmarks"]) s.state = (iBookmarksPanel && [iBookmarksPanel isVisible]); [item setState:(s.state ? NSOnState : NSOffState)]; return actionsEnabled() || s.alwaysOn; } return YES; } void AppUi::fillDynamicSubmenu(NSMenuItem *item) { NSMenu *sm = item.submenu; [sm removeAllItems]; if (item.tag == ESubmenuSelectLayer || item.tag == ESubmenuMoveLayer) { String cmd = (item.tag == ESubmenuSelectLayer) ? "selectinlayer-" : "movetolayer-"; for (auto &name : iLayerNames) { NSMenuItem *mi = [[IpeMenuItem alloc] initWithTitle:I2N(name) ipeAction:I2N(cmd + name) keyEquivalent:@""]; [sm addItem:mi]; } } else if (item.tag == ESubmenuTextStyle) { AttributeSeq seq; iCascade->allNames(ETextStyle, seq); String cmd { "textstyle|" }; for (auto &attr : seq) { NSMenuItem *mi = [[IpeMenuItem alloc] initWithTitle:I2N(attr.string()) ipeAction:I2N(cmd + attr.string()) keyEquivalent:@""]; if (attr == iAll.iTextStyle) mi.state = NSOnState; [sm addItem:mi]; } } else if (item.tag == ESubmenuGridSize || item.tag == ESubmenuAngleSize) { auto uisel = EUiGridSize; auto sel = EGridSize; String cmd = "gridsize|"; if (item.tag == ESubmenuAngleSize) { uisel = EUiAngleSize; sel = EAngleSize; cmd = "anglesize|"; } auto curr = iSelector[uisel].indexOfSelectedItem; auto count = 0; for (auto &name : iComboContents[uisel]) { NSMenuItem *mi = [[IpeMenuItem alloc] initWithTitle:I2N(name) ipeAction:I2N(cmd + name) keyEquivalent:@""]; if (count == curr) mi.state = NSOnState; ++count; [sm addItem:mi]; } } } void AppUi::toggleSnapbarShown() { iSnapBar.hidden = ![iSnapBar isHidden]; if ([iSnapBar isHidden]) { activateConstraint(iViewToSnapBar, NO); activateConstraint(iViewToTop, YES); } else { activateConstraint(iViewToTop, NO); activateConstraint(iViewToSnapBar, YES); } iCanvas->update(); } // -------------------------------------------------------------------- void AppUi::setNotes(String notes) { if (iNotesField) { NSTextStorage *s = [iNotesField textStorage]; NSAttributedString *n = [[NSAttributedString alloc] initWithString:I2N(notes)]; [s setAttributedString:n]; [iNotesField setTextColor: [NSColor textColor]]; } } void AppUi::setBookmarks(int no, const String *s) { [iBookmarksView setBookmarks:no fromStrings:s]; } void AppUi::setToolVisible(int m, bool vis) { if (m == 1) { if (vis && iBookmarksPanel == nil) { iBookmarksPanel = [[NSPanel alloc] initWithContentRect:NSMakeRect(400.,800.,240.,480.) styleMask:NSTitledWindowMask|NSClosableWindowMask| NSResizableWindowMask|NSMiniaturizableWindowMask backing:NSBackingStoreBuffered defer:YES]; NSRect cFrame =[[iBookmarksPanel contentView] frame]; iBookmarksView = [[IpeBookmarksView alloc] initWithFrame:cFrame]; [iBookmarksView setDelegate:iDelegate]; [iBookmarksPanel setContentView:iBookmarksView]; [iBookmarksPanel setTitle:@"Ipe bookmarks"]; } if (vis) [iBookmarksPanel orderFront:iWindow]; else [iBookmarksPanel orderOut:iWindow]; } else if (m == 2) { if (vis && iNotesPanel == nil) { iNotesPanel = [[NSPanel alloc] initWithContentRect:NSMakeRect(400.,800.,240.,480.) styleMask:NSTitledWindowMask|NSClosableWindowMask| NSResizableWindowMask|NSMiniaturizableWindowMask backing:NSBackingStoreBuffered defer:YES]; NSRect cFrame =[[iNotesPanel contentView] frame]; NSScrollView *scroll = [[NSScrollView alloc] initWithFrame:cFrame]; iNotesField = [[NSTextView alloc] initWithFrame:cFrame]; [iNotesField setEditable:NO]; [iNotesField setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable]; [scroll setDocumentView:iNotesField]; [scroll setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable]; [scroll setHasVerticalScroller:YES]; [iNotesPanel setContentView:scroll]; [iNotesPanel setTitle:@"Ipe page notes"]; } if (vis) [iNotesPanel orderFront:iWindow]; else [iNotesPanel orderOut:iWindow]; } } // -------------------------------------------------------------------- void AppUi::layerMenu(NSPoint p, NSString *layer) { luaShowLayerBoxPopup(Vector(p.x, p.y), N2I(layer)); } void AppUi::layerAction(NSString *actionName, NSString *layer) { luaLayerAction(N2I(actionName), N2I(layer)); } // -------------------------------------------------------------------- void AppUi::absoluteButton(int sel) { luaAbsoluteButton(selectorNames[sel]); } void AppUi::snapButton(int sel) { NSString *a = C2N(snapbutton_action[sel]); IpeAction *s = findAction(a); if (s) { s.state = (iSnapButton[sel].state == NSOnState); luaAction(N2I(a)); } } void AppUi::selectorChanged(int sel) { if (iInUiUpdate) return; int idx = [iSelector[sel] indexOfSelectedItem]; luaSelector(String(selectorNames[sel]), iComboContents[sel][idx]); } IpeAction *AppUi::findAction(NSString *name) const { return iActions[name]; } // Determine if an action is checked. // Used for viewmarked, pagemarked, snapXXX, grid_visible, show_axes, // pretty_display, toggle_notes, toggle_bookmarks. bool AppUi::actionState(const char *name) { if (!strcmp(name, "viewmarked")) return iViewMarked.state == NSOnState; if (!strcmp(name, "pagemarked")) return iPageMarked.state == NSOnState; IpeAction *s = findAction(C2N(name)); if (s) return s.state; return false; } // Check/uncheck an action. // Used by Lua for snapangle and grid_visible // Also to initialize mode_select void AppUi::setActionState(const char *name, bool value) { NSString *a = C2N(name); IpeAction *s = findAction(a); if (s && s.toggles) s.state = value; if ([a hasPrefix:@"mode_"]) { if (value) { iModeIndicator.image = loadIcon(name); iWindow.toolbar.selectedItemIdentifier = a; } } else if ([a hasPrefix:@"snap"] || [a isEqualToString:@"grid_visible"] || [a isEqualToString:@"show_axes"]) { for (int i = 0; i < 8; ++i) { if ([a isEqualToString:C2N(snapbutton_action[i])]) iSnapButton[i].state = value ? NSOnState : NSOffState; } // update touch bar if it exists #if MAC_OS_X_VERSION_MAX_ALLOWED >= 101202 #pragma clang diagnostic push #pragma clang diagnostic ignored "-Wdeprecated-declarations" if (iDelegate.touchBar != nil) { auto bar = (NSTouchBar *) iDelegate.touchBar; auto item = [bar itemForIdentifier:a]; if (item != nil) { auto b = (NSButton *) item.view; b.state = value ? NSOnState : NSOffState; } } #pragma clang diagnostic push #endif } else if ([a isEqualToString:@"shift_key"]) { int mod = s.state ? CanvasBase::EShift : 0; if (iCanvas) iCanvas->setAdditionalModifiers(mod); } } void AppUi::action(String name) { ipeDebug("action %s", name.z()); if (name == "escape") { if (iCanvas && iCanvas->tool()) iCanvas->tool()->key("\033", 0); return; } // Implement radio buttons int i = name.find("|"); if (i >= 0) setCheckMark(name.left(i+1), name.substr(i+1)); if (name.hasPrefix("mode_")) { setCheckMark("mode_", name.substr(5)); setActionState(name.z(), true); } // Implement toggle actions IpeAction *s = findAction(I2N(name)); if (s && s.toggles) setActionState(name.z(), !s.state); luaAction(name); } // -------------------------------------------------------------------- WINID AppUi::windowId() { return iWindow; } void AppUi::setWindowCaption(bool mod, const char *s) { [iWindow setTitle:[[NSString alloc] initWithUTF8String:s]]; } void AppUi::showWindow(int width, int height) { if (width > 0 && height > 0) { NSRect e = [[NSScreen mainScreen] frame]; auto wd = e.size.width - width; auto hd = e.size.height - height; NSRect winr = NSMakeRect(0.5 * wd, 0.5 * hd, width, height); [iWindow setFrame:winr display:YES]; } [iWindow makeKeyAndOrderFront:iWindow]; } // show for t milliseconds, or permanently if t == 0 void AppUi::explain(const char *s, int t) { if (iIndicatorTimer) { [iIndicatorTimer invalidate]; iIndicatorTimer = nil; } if (t) iIndicatorTimer = [NSTimer scheduledTimerWithTimeInterval:t / 1000.0 target:iDelegate selector:@selector(indicatorFired:) userInfo:nil repeats:NO]; [iStatus setStringValue:C2N(s)]; } void AppUi::setSnapIndicator(const char *s) { [iSnapIndicator setStringValue:C2N(s)]; } void AppUi::setMouseIndicator(const char *s) { [iMouseIndicator setStringValue:C2N(s)]; } void AppUi::setZoom(double zoom) { iCanvas->setZoom(zoom); [iZoomIndicator setStringValue: [NSString stringWithFormat:@"%3dppi", int(72.0 * zoom)]]; } BOOL AppUi::closeRequested() { // calls model lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "closeEvent"); lua_pushvalue(L, -2); // model lua_remove(L, -3); lua_call(L, 1, 1); bool result = lua_toboolean(L, -1); return result; } BOOL AppUi::isModified() { // calls model lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "isModified"); lua_pushvalue(L, -2); // model lua_remove(L, -3); lua_call(L, 1, 1); bool result = lua_toboolean(L, -1); return result; } void AppUi::closeWindow() { [iWindow performClose:iDelegate]; } // -------------------------------------------------------------------- int AppUi::clipboard(lua_State *L) { // bool allow_bitmap = lua_toboolean(L, 2); // NSImage can be read in the same way, but I don't // know how to convert it to a bitmap... NSPasteboard *pasteBoard = [NSPasteboard generalPasteboard]; NSArray *arr = [pasteBoard readObjectsForClasses:@[[NSString class]] options:@{ } ]; if (arr && [arr count] > 0) { lua_pushstring(L, N2C(arr[0])); return 1; } return 0; } int AppUi::setClipboard(lua_State *L) { const char *s = luaL_checkstring(L, 2); NSPasteboard *pasteBoard = [NSPasteboard generalPasteboard]; [pasteBoard clearContents]; [pasteBoard writeObjects:@[ C2N(s) ]]; return 0; } // -------------------------------------------------------------------- AppUiBase *createAppUi(lua_State *L0, int model) { return new AppUi(L0, model); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/controls_cocoa.h0000644000175000017500000000573213561570220016767 0ustar otfriedotfried// -*- objc -*- // -------------------------------------------------------------------- // Special widgets for Cocoa // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef CONTROLS_COCOA_H #define CONTROLS_COCOA_H #include "ipelib.h" #include using namespace ipe; inline String N2I(NSString *aStr) { return String(aStr.UTF8String); } inline const char *N2C(NSString *aStr) { return aStr.UTF8String; } inline NSString *I2N(String s) {return [NSString stringWithUTF8String:s.z()];} inline NSString *C2N(const char *s) {return [NSString stringWithUTF8String:s];} @interface IpeMenuItem : NSMenuItem @property NSString * ipeAction; - (instancetype) initWithTitle:(NSString *) aTitle ipeAction:(NSString *) anIpeAction keyEquivalent:(NSString *) aKey; @end @protocol IpeControlsDelegate - (void) pathViewAttributeChanged:(String) attr; - (void) pathViewPopup:(NSPoint) p; - (void) bookmarkSelected:(int) index; - (void) layerMenuAt:(NSPoint) p forLayer:(NSString *) layer; - (void) layerAction:(NSString *) actionName forLayer:(NSString *) layer; @end @interface IpePathView : NSView @property (weak) id delegate; - (void) setAttributes:(const AllAttributes *) all cascade:(Cascade *) sheet; @end @interface IpeLayerView : NSScrollView @property (weak) id delegate; - (void) setPage:(const Page *) page view:(int) view; - (void) ipeLayerClicked:(int) row; - (void) ipeLayerMenuAt:(NSPoint) p forRow:(int) row; - (void) ipeLayerToggled:(id) sender; @end @interface IpeBookmarksView : NSScrollView @property (weak) id delegate; - (void) setBookmarks:(int) no fromStrings:(const String *) s; @end // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipe/controls_qt.cpp0000644000175000017500000002441013561570220016654 0ustar otfriedotfried// -------------------------------------------------------------------- // Special widgets for QT // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "controls_qt.h" #include "ipethumbs.h" #include "ipecairopainter.h" #include "ipecanvas_qt.h" #include #include #include #include // -------------------------------------------------------------------- LayerBox::LayerBox(QWidget *parent) : QListWidget(parent) { setFocusPolicy(Qt::NoFocus); setSelectionMode(NoSelection); iInSet = false; connect(this, SIGNAL(itemChanged(QListWidgetItem *)), SLOT(layerChanged(QListWidgetItem *))); } void LayerBox::layerChanged(QListWidgetItem *item) { if (iInSet) return; LayerItem *litem = (LayerItem *) item; if (item->checkState() == Qt::Checked) emit activated("selecton", litem->ipeLayerName); else emit activated("selectoff", litem->ipeLayerName); } void LayerBox::set(const Page *page, int view) { std::vector objCounts; page->objectsPerLayer(objCounts); iInSet = true; clear(); for (int i = 0; i < page->countLayers(); ++i) { QString text = QString("%1 (%2)").arg(QIpe(page->layer(i))).arg(objCounts[i]); QListWidgetItem *item = new LayerItem(text, page->layer(i), this); item->setFlags(Qt::ItemIsUserCheckable|Qt::ItemIsEnabled); item->setCheckState(page->visible(view, i) ? Qt::Checked : Qt::Unchecked); if (page->layer(i) == page->active(view)) item->setBackgroundColor(Qt::yellow); if (page->isLocked(i)) item->setBackground(QColor(255, 220, 220)); if (!page->hasSnapping(i)) item->setForeground(Qt::gray); } iInSet = false; } void LayerBox::mousePressEvent(QMouseEvent *ev) { LayerItem *item = (LayerItem *) itemAt(ev->pos()); if (item && ev->button()== Qt::LeftButton && ev->x() > 30) { emit activated("active", item->ipeLayerName); } QListWidget::mousePressEvent(ev); } void LayerBox::mouseReleaseEvent(QMouseEvent *ev) { LayerItem *item = (LayerItem *) itemAt(ev->pos()); if (item && ev->button() == Qt::RightButton) { // make popup menu emit showLayerBoxPopup(Vector(ev->globalPos().x(), ev->globalPos().y()), item->ipeLayerName); } else QListWidget::mouseReleaseEvent(ev); } // -------------------------------------------------------------------- #if QT_VERSION < 0x050000 PathView::PathView(QWidget* parent, Qt::WFlags f) : QWidget(parent, f) #else PathView::PathView(QWidget* parent, Qt::WindowFlags f) : QWidget(parent, f) #endif { iCascade = nullptr; } void PathView::set(const AllAttributes &all, Cascade *sheet) { iCascade = sheet; iAll = all; update(); } void PathView::paintEvent(QPaintEvent *ev) { QSize s = size(); int w = s.width(); int h = s.height(); cairo_surface_t *sf = cairo_image_surface_create(CAIRO_FORMAT_RGB24, w, h); cairo_t *cc = cairo_create(sf); cairo_set_source_rgb(cc, 1, 1, 0.8); cairo_rectangle(cc, 0, 0, w, h); cairo_fill(cc); if (iCascade) { cairo_translate(cc, 0, h); double zoom = w / 70.0; cairo_scale(cc, zoom, -zoom); Vector v0 = (1.0/zoom) * Vector(0.1 * w, 0.5 * h); Vector v1 = (1.0/zoom) * Vector(0.7 * w, 0.5 * h); Vector u1 = (1.0/zoom) * Vector(0.88 * w, 0.8 * h); Vector u2 = (1.0/zoom) * Vector(0.80 * w, 0.5 * h); Vector u3 = (1.0/zoom) * Vector(0.88 * w, 0.2 * h); Vector u4 = (1.0/zoom) * Vector(0.96 * w, 0.5 * h); CairoPainter painter(iCascade, nullptr, cc, 3.0, false); painter.setPen(iAll.iPen); painter.setDashStyle(iAll.iDashStyle); painter.setStroke(iAll.iStroke); painter.setFill(iAll.iFill); painter.pushMatrix(); painter.newPath(); painter.moveTo(v0); painter.lineTo(v1); painter.drawPath(EStrokedOnly); if (iAll.iFArrow) Path::drawArrow(painter, v1, Angle(0), iAll.iFArrowShape, iAll.iFArrowSize, 100.0); if (iAll.iRArrow) Path::drawArrow(painter, v0, Angle(IpePi), iAll.iRArrowShape, iAll.iRArrowSize, 100.0); painter.setDashStyle(Attribute::NORMAL()); painter.setTiling(iAll.iTiling); painter.newPath(); painter.moveTo(u1); painter.lineTo(u2); painter.lineTo(u3); painter.lineTo(u4); painter.closePath(); painter.drawPath(iAll.iPathMode); painter.popMatrix(); } cairo_surface_flush(sf); cairo_destroy(cc); QPainter qPainter; qPainter.begin(this); QRect r = ev->rect(); QImage bits(cairo_image_surface_get_data(sf), w, h, QImage::Format_RGB32); QRect source(r.left(), r.top(), r.width(), r.height()); qPainter.drawImage(r, bits, source); qPainter.end(); cairo_surface_destroy(sf); } QSize PathView::sizeHint() const { return QSize(120, size().width() / 8.0); } void PathView::mousePressEvent(QMouseEvent *ev) { QSize s = size(); if (ev->button()== Qt::LeftButton && ev->x() < s.width() * 3 / 10) { emit activated(iAll.iRArrow ? "rarrow|false" : "rarrow|true"); } else if (ev->button()== Qt::LeftButton && ev->x() > s.width() * 4 / 10 && ev->x() < s.width() * 72 / 100) { emit activated(iAll.iFArrow ? "farrow|false" : "farrow|true"); update(); } else if (ev->button()== Qt::LeftButton && ev->x() > s.width() * 78 / 100) { switch (iAll.iPathMode) { case EStrokedOnly: emit activated("pathmode|strokedfilled"); break; case EStrokedAndFilled: emit activated("pathmode|filled"); break; case EFilledOnly: emit activated("pathmode|stroked"); break; } update(); } } void PathView::mouseReleaseEvent(QMouseEvent *ev) { if (ev->button()== Qt::RightButton) emit showPathStylePopup(Vector(ev->globalPos().x(), ev->globalPos().y())); } bool PathView::event(QEvent *ev) { if (ev->type() != QEvent::ToolTip) return QWidget::event(ev); QHelpEvent *hev = (QHelpEvent *) ev; QSize s = size(); QString tip; if (hev->x() < s.width() * 3 / 10) tip = "Toggle reverse arrow"; else if (hev->x() > s.width() * 4 / 10 && hev->x() < s.width() * 72 / 100) tip = "Toggle forward arrow"; else if (hev->x() > s.width() * 78 / 100) tip = "Toggle stroked/stroked & filled/filled"; if (!tip.isNull()) QToolTip::showText(hev->globalPos(), tip, this); return true; } // -------------------------------------------------------------------- PageSorter::PageSorter(Document *doc, int itemWidth, QWidget *parent) : QListWidget(parent) { iDoc = doc; setViewMode(QListView::IconMode); setSelectionMode(QAbstractItemView::ExtendedSelection); setResizeMode(QListView::Adjust); setWrapping(true); setUniformItemSizes(true); setFlow(QListView::LeftToRight); setSpacing(10); setMovement(QListView::Static); Thumbnail r(iDoc, itemWidth); setGridSize(QSize(itemWidth, r.height() + 50)); setIconSize(QSize(itemWidth, r.height())); for (int i = 0; i < doc->countPages(); ++i) { Page *p = doc->page(i); Buffer b = r.render(p, p->countViews() - 1); QImage bits((const uchar *) b.data(), itemWidth, r.height(), QImage::Format_RGB32); // need to copy bits since buffer b is temporary QIcon icon(QPixmap::fromImage(bits.copy())); QString s; QString t = QString::fromUtf8(p->title().z()); if (t != "") { s.sprintf("%d: ", i+1); s += t; } else { s.sprintf("Page %d", i+1); } QListWidgetItem *item = new QListWidgetItem(icon, s); item->setFlags(Qt::ItemIsSelectable|Qt::ItemIsEnabled); item->setToolTip(s); item->setData(Qt::UserRole, QVariant(i)); // page number addItem(item); } } int PageSorter::pageAt(int r) const { return item(r)->data(Qt::UserRole).toInt(); } void PageSorter::deletePages() { QList items = selectedItems(); for (int i = 0; i < items.count(); ++i) { int r = row(items[i]); QListWidgetItem *item = takeItem(r); delete item; } } void PageSorter::cutPages() { // delete items in old cut list for (int i = 0; i < iCutList.count(); ++i) delete iCutList[i]; iCutList.clear(); QList items = selectedItems(); for (int i = 0; i < items.count(); ++i) { int r = row(items[i]); QListWidgetItem *item = takeItem(r); iCutList.append(item); } } void PageSorter::insertPages() { // deselect everything for (int i = 0; i < count(); ++i) item(i)->setSelected(false); int r = (iActionRow >= 0) ? iActionRow : count(); for (int i = 0; i < iCutList.count(); ++i) { insertItem(r, iCutList[i]); item(r++)->setSelected(true); } iCutList.clear(); } void PageSorter::contextMenuEvent(QContextMenuEvent *ev) { ev->accept(); QListWidgetItem *item = itemAt(ev->pos()); iActionRow = row(item); QMenu *m = new QMenu(); QAction *action_delete = new QAction("&Delete", this); connect(action_delete, SIGNAL(triggered()), SLOT(deletePages())); QAction *action_cut = new QAction("&Cut", this); connect(action_cut, SIGNAL(triggered()), SLOT(cutPages())); QAction *action_insert = new QAction("&Insert", this); connect(action_insert, SIGNAL(triggered()), SLOT(insertPages())); if (selectedItems().count() > 0) { m->addAction(action_delete); m->addAction(action_cut); } if (iCutList.count() > 0) m->addAction(action_insert); m->exec(ev->globalPos()); delete m; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/ipe.icns0000644000175000017500000050577713561570220015260 0ustar otfriedotfriedicns‹ÿis32Õ ðÿÿüþ‘.%™ýÿ ÿþþÿ€g¾ÿdÿú·þß<ÿë³Ü}V‚ÿŒNÃéhV‚ÿý;»ékV‚ÿ0}·éi%­€ÿdøù€ §éj; MÜÿü€ –éjVÿ´‰¥v0TÊ€ „éhVÿÿÒ>ÿÿ„G€[ékVÿó‚ÿ€ éeRÿcA§¨œúÿé€ çÔÍÿ g»»·ÿÿú€ç€ÿ‡ÿþÿ€ãÿ=áÿÒ„þÿ€ ÿýÿýÿä3eúÿÿ ðÿÿüþ‘.%™ýÿ ÿþþÿ€g¾ÿdÿú·þß<ÿë³Ü}V‚ÿŒNÃéhV‚ÿý;»ékV‚ÿ0}·éi%­€ÿdøù€ §éj; MÜÿü€ –éjVÿ´‰¥v0TÊ€ „éhVÿÿÑ>ÿÿƒG€[ékVÿò‚ÿ€ éeRÿbA§¨œúÿé€ çÔÍÿ g»»·ÿÿú€ç€ÿ‡ÿþÿ€ãÿ<âÿÒ…þÿ€ ÿýÿýÿã3eúÿÿ ðÿÿüþ‘.%™ýÿ ÿþþÿ€g¾ÿdÿú·þß<ÿë³Ü}V‚ÿŒNÃéhV‚ÿý;»ékV‚ÿ0}·éi%­€ÿdøù€ §éj; MÜÿü€ –éjVÿ´‰¥v0TÌ€ „éhVÿÿÑ>ÿÿƒI€[ékVÿò‚ÿ€ éeRÿbA§¨œúÿé€ çÔÍÿ h»»·ÿÿú€ç€ÿˆÿþÿ€ãÿ<âÿÒ†þÿ€ ÿýÿýÿã3gúÿÿs8mk0D[p¡ÛòìÑÔ‰ÿÿÿÿÿÿÿÿÿÿUtÿÿÿÿÿÿÿÿÿÿ¥}ÿÿÿÿÿÿÿÿÿþäkÿÿÿÿÿÿÿÿÿÿú_ÿÿÿÿÿÿÿÿÿÿÿUÿÿÿÿÿÿÿÿÿÿÿ1Iÿÿÿÿÿÿÿÿÿÿÿc=ÿÿÿÿÿÿÿÿÿÿÿ¡4ÿÿÿÿÿÿÿÿÿÿÿì'ÿÿÿÿÿÿÿÿÿÿÿ÷ÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿ<ÿÿÿÿÿÿÿÿÿÿÿÿoþÿÿÿÿÿÿþÿÿÿÿ«óýêÕÀ°ß÷ß’=$ il32"Œ þ75{ýýÿÿ†Ôüÿýÿÿþÿº‚šÿÿ†ï†ÿ y@Ÿ÷ÓKÿ†ÿÿýׂÿI§ú€ÿø/J† þÿ÷€¶ÿÿ惃ÿÅ*=‡€ÿØ Ïÿa´‚ÿëõ†ÿVÿ ´ƒÿyÆÿ¿ˆÿXñ´ƒÿkíòÿÿk‰.ÑÕ´ƒÿg‚ÿŠ)ÿÖ´ƒÿkÿ•‡ f}³‘ˆ×´ƒÿ„îÿÿÞ4…þ€ÿ HÜ´ƒÿõqÿÿù… p‘Æ¥€×¥„ÿŒÌYÿ‰$ÿÕ }Ù‚ÿX2ÿû‡ÙÕ€ uÓÿíûÿý… üÿÿù[Ú½‚‚a€ÿþ…ÿSÛµÿö‡<3xòÛšƒ˜ãÿ„ G/ÅÕµ„ÿ£ €ˆ+ÿÕµ‚ÿú7½€ÿ–† *cž|“Öµÿ÷'ƒÿ}„ÿ Hܵÿ.ê…ÿ„ E¤Ü¼w×µ€ÿ‹Y†ÿ¿‡üÕµ€ÿ½†ÿö… åÕ´ÿÿ EMQTTOAÛ€ÿƒ‹èÿîbõLJÞÿÿPjqssqpr€ÿüƒñ€ÿOƒÿ#‡ÿýƒëÿå=·ƒÿˆÿƒßœŽ„ÿé†ÿþÿ‚ÿä‡ì…ÿSBƒÿÒN€ÿƒþ‡ÿ΀H÷ÿÿßUIÿƒ‰ÿ‡( üÿþÿÿƒ€ÿýþÿý€ÿüûÿj‰Œ þ75{ýýÿÿ†Ôüÿýÿÿþÿº‚šÿÿ†ï†ÿ y@Ÿ÷ÓKÿ†ÿÿýׂÿI§ú€ÿø/J† þÿ÷€¶ÿÿ惃ÿÅ*=‡€ÿØ Ïÿa´‚ÿëõ†ÿVÿ ´ƒÿyÆÿ¿ˆÿXñ´ƒÿkíòÿÿk‰.ÑÕ´ƒÿg‚ÿŠ)ÿÖ´ƒÿkÿ•‡ f}³‘ˆ×´ƒÿ„îÿÿÞ4…þ€ÿ HÜ´ƒÿõqÿÿù… p‘Æ¥€×¥„ÿŒÌYÿ‰$ÿÕ }Ù‚ÿX2ÿû‡ÙÕ€ uÓÿíûÿý… üÿÿù[Ú½‚‚a€ÿþ…ÿSÛµÿö‡<3xòÚšƒ˜äÿ„ G/ÅÕµ„ÿ¢ €ˆ+ÿÕµ‚ÿù5½€ÿ”ƒ *cž|“Öµÿö'ƒÿz„ÿ Hܵÿ+ë…ÿ„ E¤Ü¼w×µ€ÿˆZ†ÿ¿‡üÕµ€ÿ¾†ÿö… åÕ´ÿÿEMQTTOAÜ€ÿƒ‹èÿîbõLJÞÿÿNjqssqpr€ÿüƒñ€ÿOƒÿ$‡ÿýƒëÿå=·ƒÿˆÿƒßœŽ„ÿê†ÿþÿ‚ÿä‡ì…ÿQBƒÿÐO€ÿƒþ‡ÿÌ€H÷ÿÿÞSJÿƒ‰ÿ…( Žüÿþÿÿƒ€ÿýþÿý€ÿüûÿf‰Œ þ75{ýýÿÿ†Ôüÿýÿÿþÿº‚šÿÿ†ï†ÿ y@Ÿ÷ÓKÿ†ÿÿýׂÿI§ú€ÿø/J† þÿ÷€¶ÿÿ惃ÿÅ*=‡€ÿØ Ïÿa´‚ÿëõ†ÿVÿ ´ƒÿyÆÿ¿ˆÿXñ´ƒÿkíòÿÿk‰.ÑÕ´ƒÿg‚ÿŠ)ÿÖ´ƒÿkÿ•‡ f}³‘ˆ×´ƒÿ„îÿÿÞ4…þ€ÿ HÜ´ƒÿõqÿÿù… p‘Æ¥€×¥„ÿŒÌYÿ‰$ÿÕ }Ù‚ÿX2ÿû‡ÙÕ€ uÓÿíûÿý… üÿÿù[Ú½‚‚a€ÿþ…ÿSÛµÿö‡<3xòÚšƒ˜äÿ„ G/ÅÕµ„ÿ¡ €ˆ+ÿÕµ‚ÿù5¾€ÿ”ƒ *cž|“Öµÿö)ƒÿy„ÿ Hܵÿ+ì…ÿ„ E¤Ü¼w×µ€ÿ‡]†ÿ¿‡üÕµ€ÿÁ†ÿö… åÕ´ÿÿœEMQTTOAÞ€ÿƒ‹èÿîbõLJÞÿÿLjqssqps€ÿüƒñ€ÿOƒÿ(‡ÿýƒëÿå=·ƒÿˆÿƒßœŽ„ÿì†ÿþÿ‚ÿä‡ì…ÿOEƒÿÐQ€ÿƒþ‡ÿË€JøÿÿÞSKÿƒ‰ÿ„( ‘üÿþÿÿƒ€ÿýþÿý€ÿüûÿb€…l8mkR¿Æº€ 2Yjz‹¡¶ÈÚíÿÿÿÿÿÿÿÿÿÿÿÿrþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŸ òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿFáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿIžÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý_ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿP$Öÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ'£ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ2Åÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ_ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿНÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¶xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåmÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿù…óÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ5¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÁ |ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿI*þÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿs÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŸ ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÎóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿî çÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ$ßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùüÿ¶~iR>ÉÿÿöàË·¢ŒxbJ6C“¼È²fit32aÿÐ 3UÿÿÔëòÿžÿÿþÿí-cyõüÿØÿþ€ÿÆ?ƒ ÿjÿþþÿÿ‡ŒŒ4/àøÿÿòv‚ÿ¶f€ ÿÿ]ªÿÿþëò÷|¹ƒÿ”Í‚ÿóŒ0€“nÙöÿvð€ÿûª€ÿc‚ÿ óÑoÿÿþÿÿýÿ{çÿþÿ¢Æþ‚ÿ¨¿€ÿöÊK€Ž‚zàŽ×ÿ¦¿ÿûþ€ÿÒŠÿþþõqþÿÿþ€ÿŠÜÿþÿ°¸ƒÿ¸°ÿÿæw€‘ r±ÿ¦óÿÿ€þÿ߇ÿýÿþlüƒÿ•уÿ½«ƒÿÈ¡úÁ/Œ 8€E€AÞøîä¥ÿþ‚ÿé„ÿuòƒÿ¢Åƒÿ˃ÿ׊•Š?w¹åÛ²"†Uxr¥„ÿñv„ÿ€èƒÿ­¹ƒÿÙƒÿ×: %:WkpyƒŒ•` †­úú¥ìƒÿùn„ÿŠÞƒÿº­ƒÿçÿÿõìãÈL ;k«áËŠü‚ÿõ4„÷¥ÿýþ‚ÿmûƒÿ”ÓÿÿõëâÙ©Œ½´«¢˜„ksjr{y5Œ&5ŒÎÿðv„ÿtC„¥€ÿ$ýõëáØq¾¼³ª¡˜Žsusjs|…ŽŠyª³¼ÆÏØánðþÿóm…6[’°Ž„ÿqöƒÿ­.ƒ ¥gwrjs}†oš«´¾ÆÐÙ´õ‚ÿÞ‰„ÿ|íÿýˆ  ;c˜Òÿÿí{„ÿ…áƒÿ§¿c„§ªæö‚ÿ †âÕ‘¬×ÿ³µƒÿé}„ÿŠßÿ«„@ZXÔ‚ÿýnûƒÿšÌƒÿ’O/¯ÿýƒÿ ްLD|Ѝƒÿöq„ÿ—ÑÔ8Es¤×ê}„ÿéƒÿ°·ÿÞ†#ƒ«…ÿ–LƒCÀ‚ÿþmúƒÿ ¥¼o0|«Ú€ÿúnýƒÿ’ÖƒÿÅ¢€ÿ¸I‚­ÿüþ‚ÿ(€-…óÿyîƒÿ ³zh”„ÿyîÿúñ¯ÔËÁ¸®¥uˆ|EƒTb­…ÿ§5ƒZÝ€ÿ…âƒÿ­7‚!ÁÙ„áØÏÅ»²¨uŒ‹‚yomvux“œ¦°¹ÃÅqÔu€Üý]¬üƒÿ¯€DÙÿÿ‘ÉåÛÒÉ¿µ_‚Msj†™£¬µ¿Š®ÛåïøÿÿÍ›„ÿkw i÷ÿå*«…ÿ·«³i+† !mmju‚Œ•Ÿ©Ÿ8ƒºþnûƒÿ®¹ƒÿà‡ƒÿúF‚Äþÿÿ¾ªm›© –„zokuwq`.…Yú©¾‚ÿ¯ ºÿ|ìƒÿ¿§ƒÿôtƒÿœ ‚èÿ‹ª ?›¾ÇÑÚäîŸÿ㥀­µ±ÿór„ºÿŒÜƒÿÑ–„ÿrõÿÙCƒ6òÿõOªÿþ‚ÿÑ—‚ÿ þÓ9Á¥ÿÍ2„ºÿ̃ÿ䃄ÿ†áÿö…€Gø‚ÿß§úƒÿÙ„ÿ s#›™ÿ§…ºÿ¬¼ƒÿõr„ÿ™Ï‚ÿöfè€ÿüòèt©ùƒÿᆄÿ ަ hŽ€ÿów…ºÿ¼¬„ÿrõƒÿ­»‚ÿøÞb:‚ e„„zqlu|:¨ÿÿþÿé~„ÿ˜ÎBE€ÿÚFƒºÿÌœƒÿþÔá×Íú°‹€“Š€sloyh-‚ˆ¥äî÷€ÿæw@¥÷ÿþÿòv„ÿ¢Å}‚3v€ÿÄ…%’À¤y£™†|rjmv‡‘𤭷ª„ÔÞèõûÿÿj*y(5¯¢ƒÿüoѦÿþ‚ÿún„ÿ­»{‚*k²©Ÿg† s§©sÅÎØâëõÿ§Àƒÿ瀄ÿ b EÛäK?ÇŠ„ÿ…ߪ¦õÿþüòèßÕkÀ¸®¥›‘ˆto2o®¿É{†ºÿûnþƒÿ¸®ƒÿúoýƒÿ Xqñÿö¤Òðs„ÿžÈól¥pyqkuˆ’oŸ¯¹ÃÌÖàµv‚ €çÿô}„ºÿÿvòƒÿÊ„ÿyîƒÿO”€ÿþÿÿuñƒÿ·°ÿâ.¤ ¸êöÿÿûúÿ~éƒÿ ³ÇŒÚÿëh†ºÿÿ‡áƒÿÜ‹„ÿÛ‚ÿïH©ƒÿŒÚƒÿЖÿÿÆ£ˆ¢\'7o¬îþÿÓ<ÿ˜Ïÿå[†ºÿÿ–Òƒÿîy„ÿ È‚ÿâB´ƒÿ£Âƒÿé}ÿÿ÷£‚Iv € ¸ÿ¥ÂÿáR†ºÿÿ¦Âƒÿýnûƒÿ´´‚ÿÚ?³ƒÿµ£àÖÌÁ·­¢jŽ„ze£…ƒ bÿÿ°·ÿßM†ºÿÿ¶²„ÿ|ëƒÿÇ ùïáÚЧ,r“ˆtjqn‡‘œ¦°ºÅ€¿ãî÷¨¶ >ýÿÿ¼ªÿàN†&ºÿÿÆ¢ÿÿýóéÞÔ€¬µ¬¢—ƒujny‡—‹+uÊÔßéóýé}„ÿ¡ÆÿýÜ,µ.ò€ÿÈŸÿàO†€¦œ…r}rjtˆ“}±¼ÆÐÚåày‚ÿåJ}ƒÿýoøƒÿ»¬ÿðp¶ OÊÉ¿´˜y–z(†…ÁÌÆ|êõ‚ÿ±µƒÿýoúÿõZf„ÿ„âƒÿÔ’ü§¥3›©³­|ÒÁH†ºÿÿör„ÿä„ÿ€è‚ÿmKþƒÿœÊƒÿîxϵ ÿÿìzÿàP†º€ÿq÷ƒÿÕ’„ÿ”Ô‚ÿˆ.ëƒÿ²´ƒÿþgC¤† 3M  ÊÿùnÿàP†º€ÿçƒÿ瀄ÿ§Á‚ÿ¬˃ÿɃÿùF¤AA/&!!$#Jyµúÿ¢%€ Jÿÿo÷àP†º€ÿ‘׃ÿøoþƒÿ»­‚ÿØ: ƒÿᆃÿ´¤ ÿÿâÇ»¹Â¶‡ƒÿ ¿Óÿ|ëàP†º€ÿ È„ÿuòƒÿΙƒÿdiø‚ÿîoá×Íù•§ÿþþ‚ÿↄÿ o …ÿˆààP†º€ÿ±·„ÿ‡àƒÿá†õëá×ÍÃqƒ‘‡}sjsl‘›¥¥;©„ÿê}„ÿ»Sÿ”ÓàP†º€ÿ$Á§ÿÿõëá×Í„¢°¦œ’ˆ~sjr}†š¤™&„Öàêôþÿ’Ô€ÿŒ‚¢ÿþ‚ÿòu„ÿÅK‚9ÿ ÇàP†€¦œ’~qtjr|†š„ޏÂÌÖàéósôƒÿlDã‚ÿª¼ÿÿ½ ¨„ÿûm„ÿÊI‚%¦€€w'†…ÁËÕȃóý‚ÿ¼«„ÿ‡áƒÿÌžüÿÁ¥ÿä-„ ÿöêâÙÏÅ»k¥“‰uko5Á›ÃI†º€ÿðx„ÿΙ„ÿ›Í„ÿ;(ÕÿÙŽþ]…5 hq{…™£­q¸ÊÔÞèòü± vÿÄ£àP†º€ÿýnüƒÿà‡„ÿ®º„ÿ|<có€ÿïw’ƒÿ  øþÿêààç÷é‚ÿ â4½ÿЗàP†»ÿ{íƒÿòu„ÿÁ¦„ÿœ“ý€ÿX…8èÿ 7xYKDDIT6t¬ÝÿÿÎJ€ 5þÿÜ‹àP†»ÿ‹ÝƒÿþoùƒÿÕ’„ÿ ²µŽ¥ÿÿÿý …ׂÿwÒP1Lfwu{–¡¬¶ÁËÖ‡Êöƒÿrõÿÿà… >œÿÿþÿÿ± DÿÿùîäÙ{ž:0_ƒ•„ÿ¡Å„ÿˆÞÿÿu „ /LJÿÿþÿÿ² 0noy„Žu‚6€X¦íÿµ²„ÿžÉÿ© Óøpýÿÿþý³ ‰ÿ›³Pˆ…$R¢ìÿÈŸ„ÿ²´Ý/ Ëÿÿ|êÿÿþýÿªC„×€ÿ§¨P…N‹MŠ€„ÿÈŸS„Í€ÿ–Ѐÿýÿžƒ #v½éó¥€W€ÿ´žP†¼©ˆ HœëÿÞE †,Ûÿ°¶€ÿýÿžˆåéÔÃÂÎå̆øþÿÿý¼‚Ûÿÿ¿“P†½ÿÅ&  E™êÿ°€VìÿùîäÙ¨Œº°¥˜žÿþþÿÿâ…ƒÿ’€ ÿÿˉP†¼ÿÿêV‹ H!…@xnoy„Ž’q­¸ÂÍÉž¿ÿþ‚ÿë}ƒÿýYÿÿ×~P†¼ÿ©€š5±u×ïùÿúoüÿþþÿž…ÿóu„ÿf‚;ÿÿäsP†¼ÿÿúðå¦F—&®ûÿŽØ„ÿ€çÿÿþÿÿ…ÿül„ÿ{‚5ÿÿïiJ† azomx‚ƒv”P ‚‡„.¢ú€ÿ¦Á„ÿ™Í‚ÿÿÿþƒÿoùÿÿõêàÕD%xm]&†§î÷€ÿ åƒÿÿøž?‹8Ãþ‚ÿ ¾§üûúúùùú°°üþ€ÿËÒȾ³©ž”l}ujs}ˆ‚]åðúdL†¼‚ÿõs‚ÿêžW €  1o·×ˆÿüøõ²\tO3 (m¤Þ÷ófz‘𤭏ÃÏzÖóýÿÿùI€­€ÿoI†¼ƒÿpø„ÿ räâˆvlik6«Ðù€ÿótÿýöê§Y‹4ižmŠi\[f} nÌòûÿòa'û€ÿzE†¼ƒÿ€è„ÿ„â„ÿuò„ÿræ¿^ŒªU¨ÐAƒ ‹ÿƒA†¼ƒÿÙ„ÿ•Ò„ÿˆß‚ÿüï]1„…¥„;þÿ=†¼ƒÿ É„ÿ§¿„ÿœÌÿò·;´ #Ñ‚ÿ™9†¼ƒÿ°¸„ÿº­„ÿ¯¸ÿÿûÔ`‚ ,--,#·¶ƒÿ¤6†¼ƒÿ¿©„ÿÊœýóèÝÓȹ”ƒ‹X‚ Cz¬ÌÖº•÷ÿÿ÷Ä‚;±C„ÿ­2†¼ÿô麋ɿ´©Ÿ”‰yljuŠ•Ÿ¯¢³[‹ì‚ÿッÿü±›ƒÿ¹.†m‹€ukr~‚rž©´¾ÉÓÞÛw„ÿ êfFri„ÿúoüƒÿýdH±€¬¡–Œe!†šÝèòýÿÿïy„ÿýnû‚ÿ ýµ7¸ÿtò„ÿ}é„ÿˆÂFª„©ÆÑÛæÃ'†¼ƒÿýnü„ÿ}êÿ ü©$KØÿÿ‰Ý„ÿ•Ò„ÿ¡ÅË+ #*eŸÃk €nÿØ#†´„ÿzî„ÿŽÙ€ÿû¤‚M߀ÿžÈ„ÿ¬»„ÿº¬ÿž ž .Š€ˆ˜®¯†ÿ‰‚é€ÿà"†ª„ÿŠÞ„ÿ Æÿÿý«€?×ÿ´³„ÿä„ÿÓ’ÿìa…ÿã„‚ÿr€›€ÿà&† „ÿšÎ„ÿ²µÿÿ»&€'¿‚ÿÉž„ÿÚ„ÿìyÿÿº7œì„ÿë|‚ÿïa€ÿà*†–„ÿª¾„ÿ ãÿÐ3”ƒÿÞˆ„ÿòuýòèÝÓȽ²kœ’ƒdK=›ÿþþ‚ÿôsƒÿd?€ÿà-†Œ„ÿº®„ÿÖ‘çM€1ì€ÿþóéÔrɾ´©ž”‰~jju€Š•Ÿªµ~²Ôàêóô›â„ÿülþ‚ÿ„‚4€ÿà1†‚„ÿÉŸ„ÿç|u‚O•Šujs‰n˜©´¾ÉÔÞé‰Û„ÿ¤Â€ÿýù›Úý„ÿoø‚ÿ^A€ÿà5†xÿöëຂÀµ« •‹€tOƒNlÌÝèóý€ÿ‰Ý„ÿ£Ä„ÿ½©€ÿþÿ›Ìýþƒÿxðÿìe€ÿà9†VŒvlq|‡p§²¼ÇÒÝçØ!´ƒä„ÿŸÇ„ÿ»¬„ÿ׎€ÿþÿ›¿…ÿ€ç€ÿøV‚ f˜‚i"†\Ûæñü€ÿùoƒÿ÷z[ö–Єÿ´²„ÿÒ•„ÿñuÿýÌšQcSNR\k~p†ƒxn0‚»ÐÚåÒ?†Y…ÿuôÿþ̓•ÿª½„ÿÊœ„ÿé}…ÿvð€ÿýÿ›C’ÀQ €{ÿàD†Qþ„ÿ„äÿõS‚7Ðÿ½ª„ÿÞˆ„ÿüoú„ÿŽØÿö¤€*òÿàH†Vó„ÿ”Ô€ÿýÄ_ÿÿЖ„ÿôr…ÿƒä„ÿ§¾ÿÿþþÿ¢ƒÇ‚ÿàK†`æ„ÿ¤Ä€ÿ÷N‚ ÿÿ䃅ÿtò„ÿšÍ„ÿÁ¥‚ÿ¬fƒÿàO†jØ„ÿ´´ÿÿþÏ„)¼ÿÿ÷pþ„ÿŠÝ„ÿ±µÿÿõéÞÓȦ}¦›Ž„s]ªa‹ƒÿàP†tÊ„ÿŤÿÿújBæ€ÿvñƒÿü›·ÛÐź­£˜€rvkr~Š•Ÿ©kÁÌØãéâªWƒÿàP†~¼„ÿÔ”ÿÿï …[ëãØÌz§ª •ŠrkovŒ—¢­¹ÅÐÄñüƒÿxîÿÿþÿÿ¤  Ë‚ÿàP†ˆ¯„ÿäƒë݉† ##&+$*6=FMT\cN·€ÿ‘Ôÿÿþþ÷¡ƒ.ûÿàP† }»°¤™Žƒxlj|†2†‚2ø€ÿ¬ºÿú¢4²áGwäÙΠ5† ey¬·ÃÏÚåðúoùò„˜ xÿÅ ÿüš+m`_k„£ËĂʿ´D‚Ž™¥›;†§†…ÿé´ƒ™!ÑÿÞ‡ƒÿ™†˜„ynp{q¨³¾?‚¦€ÿõ€‚/Åx…ÿŽÙr†€ƒ„X‚ÿ÷pýÿÿþýÿ™ ˜ÊÙäïúÿÿì{ÿí hÿël0Q€RPbÌümý„ÿŸÉ8† -ˆ—§µÀÁUÅÈƒÉ |œÈÈÇÆÅÃÁžg·ôƒÿ|êÿÿþþÿ™þ„ÿõs‚ÿ\B‚ÿÖ’…ÿwò„ÿ¯·…vƒÿ}é„ÿµ±„ÿïx…ÿ–Ðÿÿþÿø™ôþƒÿülþÿƒ‚4‚ÿᆅÿ„ä„ÿ¾—„‰ƒÿׄÿÊœ„ÿþqö„ÿ®·úïãÙ²™ÿÿþƒÿp÷ÿj=‚ÿîz…ÿ’ׄÿÎq†™ƒÿ£Ã„ÿà‡ƒÿùî‚ÁËÀµ©ž“‡uknyƒŠf˜†ÿyï€ÿõ^‚ÿún…ÿ È„ÿßV†žƒÿ·°ÿÿøíâÖÊ·p©ž’†zonys€œ§³¾ÉÔàÓ„ÿýÔ˜þÿþƒÿçÿÿý…€ –ƒÿq÷„ÿ­»„ÿî@†Ôɾ³¨œszooz†‘¨rµÊÕáíøÿÿ·°„ÿùoüÿþ˜ç…ÿ‰Þÿù©‚áƒÿ}ë„ÿ»­ÿ÷ëßÒ0† T’ž©´¿ÊÀƒîùƒÿŠÜ„ÿΙ…ÿçÿÿþÿÿ˜†ÿ ‘Öå‘c„ÿˆßöéÞÓȼ±|Žƒxmq|ˆ”/† —ƒÿòu…ÿ Æ„ÿæ…ÿ™Ì‚ÿ˜Ú…ÿŠ”P¶Ç¼±¥™Žƒojq}‰”Ÿª¶ª„Ùäïúÿ6†‚„ÿqö„ÿ¶±„ÿûoü„ÿ³³ÿÿýþÿ˜ ÿÿþÿóèЦ}/„ C• ¬·ÂÏÚåšÇ„ÿä„…ÿ9‡^„ÿ„â„ÿË›…ÿ€ç„ÿÌ™ÿüÿ—nzvksuC† ys…ÿ­»„ÿòw…ÿB‡;æƒÿ—Єÿà‡…ÿ–Єÿ倃ÿ—mÛòýÿ|ƒýlý„ÿ¹¯„ÿýmý„ÿY‡¢ƒÿª¼„ÿõq…ÿ®¹„ÿûoú‚ÿ—ÿÿþÿÿ7€ 4œÿÿuó„ÿÅ£…ÿxð„ÿxˆZû‚ÿ¾¨…ÿvð„ÿÆ¡…ÿ„â€ÿþõ˜ü€ÿ;hÈ€ÿé„ÿÑ—…ÿ†â„ÿ¨†­‚ÿÒ•…ÿ‹Û„ÿÝŠ‚ÿ þ÷÷•·Ôɽ³Š˜ÿþÿÿ$e­ùÿˆÞ„ÿÝ‹…ÿ“Õ„ÿÚˆPêÿå‚…ÿ Æ€ÿ÷ìàÔÀr³§œ‚K:esv“ž©´ªf— ÿÿýÿñ@2EN»ôƒÿ“Ô„ÿé…ÿ¢Ç„ÿù ˆ „ÿøo÷ìàÔɾ³§}„ynp{‡“žr¬À˾e ¥Ï–ƒÿ—ûÿüÕÉ‹…ÿÊ„ÿõs…ÿ®º…ÿF‡oœ„yjo{†“ž©´À«ãîù‚ÿ ŽÚÿ´C²è}€ÿþÿÿ—…ÿ僅ÿ§À„ÿþmü„ÿ ¼¬ÿÿøíáÕɾk‰”×ãî‰Ý„ÿà†…ÿ¥°v2°õýo÷ÿÿþÿð—þ„ÿíz…ÿ±¶…ÿxàáÕʾ³¨‚synoz†’ž©~8‡+¶ÿÿŸÈ„ÿöqþƒÿþv*TÑ€ÿ‡Þÿö—þþƒÿõr‚ÿøíᥔ¿³¨‘…znjx†’ž©´¿Ê»Šîùƒÿ£œ† ™ý²´…ÿvð‚ÿ°M ƒèÿ Ã‚ÿ—ùÿùíâÖÊ¿²k‘…zooz†ƒ}©´¿ÊÖâîùØ„ÿ僅ÿ³°]†b©¡…ÿ ŒÚÿÿü¦L*³ö€ÿ þÿ¹¬ÿÿþÿûÿ–onoz†‘©´nÅÖâîù€ÿЗ…ÿœÌ„ÿóu…ÿÃ¥Ú†"Eã„ÿ ÆÅz3€)Ïÿþ€ÿûù¯tëÿÚÔÿ—×÷„ÿyî„ÿÚ…ÿ¨À„ÿþnü„ÿÓ•ýª‡"U“¼Ïǯ‚8‚D™ÿÿÿ ÷ýþƒÿæ„ÿ僅ÿ´´…ÿzï„ÿâ…ÿõ‹‡µþ…ÿŠÞ„ÿïy…ÿÀ¨…ÿ‡áÿþÿÿþÿÿòvÿÿímÇÿþþƒÿ’Õ„ÿùn„ÿþÍ›€ÿþÿþÿÿ‘Ë€ÿ úùöðâdÿ.Ɔÿ ›Ëÿÿþÿþÿþÿnù€ÿþþÿýÍÿúÿÿéÿÿU?‹Äðýÿÿþÿÿþÿ¢Äÿýýÿýÿüþ{Øðÿÿ Á ÿüÿüüûúÿó“‹­ÿ©ÿÐ fªÿÿÔëòÿÅÀÿÿþÿ×’-m õüÿéÀÿþ€ÿƃ ÿªÿþþÿÿ·°Œ4/àøÿÿ÷²‚ÿ¶™€ ÿÿ¡ªÿÿþëò÷µ×ƒÿÃã‚ÿó¡:€“nÙöÿ³÷€ÿûª€ÿŸª‚ÿ óä®ÿÿþÿÿýÿµñÿþÿËßþ‚ÿÎÛ€ÿöÊK€Ž‚zà¾èÿ¦¿ÿûþ€ÿå½ÿþþù°þÿÿþ€ÿ½ëÿþÿÓ׃ÿ×Óÿÿæw€‘ ŠÌÿ¦óÿÿ€þÿí¼ÿýÿþ­ýƒÿÄåƒÿÚЃÿàÊúÁ/Œ 8€E€PÞûõ瘟ÿþ‚ÿò·„ÿ²øƒÿËÞƒÿâȃÿ鸕Š ?x¿ðëÃ+†‡³¸¯¥„ÿ÷³„ÿ¸òƒÿÑØƒÿêÁƒÿàS 3Y‰¬¯´¹¿Ä†­úú¥ìƒÿü®„ÿ½ìƒÿØÑƒÿñ¹ÿÿùôïÖU $Cw¸îâ½ý‚ÿùQ„÷¥ÿýþ‚ÿ­ýƒÿÃæÿÿùôïêÏ¿ÚÕÐËÆÁº¬±¬°µ«HŒ*BŒÎÿö³„ÿ¬F„¥€ÿ$þùóîé°ÛÚÕÏÊÅÀ±²±¬±¶»À¾´ÐÕÚßäéî®÷þÿóm…6[’½À„ÿ°úƒÿÁ¼.ƒ ¥ª³°¬±¶»Á¯ÇÐÕÚßäêÈÕù‚ÿ콄ÿ¶õÿýˆ ;c˜Òÿÿõµ„ÿ»îƒÿÎÛc„§Ôñú‚ÿ »ïÕ‘¬×ÿÔÕƒÿó¶„ÿ½íÿ«„@awÔ‚ÿþ®ýƒÿÇãƒÿ©a/¯ÿýƒÿ À½LD|ŸÎƒÿú¯„ÿÅåÔ8Es¤×ó¶„ÿ¸òƒÿÓÖÿÞ†&ƒ«…ÿÅSƒ"UÀ‚ÿþ­üƒÿ ÍÕo;|«Ú€ÿü®þƒÿÂèƒÿÞË€ÿ¸J‚ ­ÿüþ‚ÿÇ-€-…óÿ´õƒÿ Õh¡©„ÿ´õÿü÷ÈÒçâÜ×ÒÍ¿²¼²iƒgt­…ÿÎ=ƒZÝ€ÿ»ïƒÿÅC‚!ÁêºîéäÞÙÔβ¿¾¹´®­³²´ÃÈÍÓØÝÞ°àz€Üý]¬üƒÿÒ—€DÙÿÿÁáñëæáÛÖ|‚}±¬»ÁÆËÑÖÛ¾ÒëñöûÿÿãÇ„ÿ§y i÷ÿå*«…ÿ×Ï·m-† 0¦­¬²¹¿ÄÉϽEƒºþ®ýƒÿÒØƒÿÿúb ‚Äþÿÿ¾ª‘ÆÏÊÅ¿ºµ®¬²¬€<…\üÏÚ‚ÿ¯ ºÿ¶ôƒÿÛ΃ÿù±ƒÿœ ‚èÿ‹ª ÇÚàåêðõÝÉÿ㥀­ÕÔÿór„ºÿ¿ëƒÿåÄ„ÿ°ùÿÙCƒMòÿõOªÿþ‚ÿåÅ‚ÿ þÓ'9ÜÍÿÍ2„ºÿÈâƒÿðº„ÿ»îÿö…€pù‚ÿß§úƒÿéÀ„ÿ £%«Æÿ§…ºÿÑÙƒÿù°„ÿÆä‚ÿöš•ò€ÿýøò‘©ùƒÿÿ À³ pÀ€ÿów…ºÿÙÑ„ÿ°ùƒÿÑÙ‚ÿûì”>‚ šººµ¯­²¸´X¨ÿÿþÿó·„ÿÆãBH¹€ÿÚFƒºÿâȃÿþ¹çîèãÞØÓ¾¸Ã½¸±­¯´¦>‚!°Íðõú€ÿñ«@¥÷ÿþÿ÷²„ÿËÞ}‚5²€ÿÄ…%¤ÜÌ´ËÆÁ»¶°¬­³¼ÁÇÌÑ×Ϻçìòùýÿÿ”,y(5È˃ÿý¯Ó¦ÿþ‚ÿü®„ÿÑÙ{‚0¬ÔÏɈ† ’ÎϱÞãéïôùÿÎ܃ÿñ¸„ÿ } EÛäK?Õ¾„ÿ»ìª¦õÿþýøòíç¬Ü×ÒÍǼ±®%>¯ÒÛᇆºÿý®þƒÿ×Òƒÿü®þƒÿ iqñÿö¤Òõ±„ÿÉàól¥­´¯¬²·½Â®ÉÒØÝãèíÕ”‚ ¸ñÿô}„ºÿÿ³÷ƒÿáÈ„ÿ´õƒÿZ”€ÿþÿÿ²÷ƒÿÖÓÿâ.¤ Óòùÿÿûúÿ·óƒÿ ÈÇ¿êÿëh†ºÿÿ¼îƒÿ뾄ÿ¿ë‚ÿïM©ƒÿ¿êƒÿåÅÿÿÆ£ˆ¢\':o¬îþÿÓ<ÿÆäÿå[†ºÿÿÅåƒÿõ´„ÿÊà‚ÿâD´ƒÿÌ݃ÿó¶ÿÿ÷£‚Iv € ¸ÿÌÝÿáR†ºÿÿÍ݃ÿþ®ýƒÿÕÕ‚ÿÚ?¶ƒÿÕÌîèâÜ×ÑˬÀºµ /£…ƒ bÿÿÓÖÿßM†ºÿÿÖÔ„ÿ¶óƒÿàÊüöîêå¼3 ‘Èý·±¬¯®¼ÂÇÍÓØÞ¸Ûïõú¨¶ >ýÿÿÚÐÿàN†&ºÿÿßËÿÿþøòíç¸ÐÖÐËÅ¿¹²¬®´¼¿Å®5“âçíòøþó¶„ÿÊßÿýÜ,µ.ò€ÿàÉÿàO†™ÍÇ»°¶°¬±·½Ã·ÀÔÙßåêðî´‚ÿåJ“ƒÿþ¯ûƒÿÙÐÿðp¶ UÜáÛÕŴĦ:†œÜâß¶óù‚ÿÔÕƒÿþ®üÿõZ„ÿºïƒÿçÂü§¥DÅÏÕѶåÎK†ºÿÿú°„ÿÝÌ„ÿ¸ò‚ÿmgþƒÿÇâƒÿõ´Ïµ ÿÿôµÿàP†º€ÿ°úƒÿç„ÿÃç‚ÿˆFëƒÿÔÕƒÿþ D¤† 3M  Êÿû®ÿàP†º€ÿ¹ñƒÿñ¸„ÿÎÜ‚ÿ¬$σÿáȃÿù`¤AA/&!!$&(Jyµúÿ¢%€ Jÿÿ¯ûàP†º€ÿÁéƒÿû®þƒÿÙÑ‚ÿØ:ªƒÿÿ´¤ ÿÿâÇ»¹Â÷ƒÿ ¿Óÿ¶ôàP†º€ÿÊà„ÿ²÷ƒÿãÆƒÿduø‚ÿõ¯îèãÝØ³§ÿþþ‚ÿﻄÿ „ …ÿ¼íàP†º€ÿÓׄÿ¼íƒÿî»ùóîéãÞƒ&¨Â¼·±¬±­¹ÁÇÌÈE©„ÿó·„ÿÙ&SÿÃæàP†º€ÿ$ÜÎÿÿùôîéãºËÓÍǼ·±¬°·»ÁÇ̹0’èíóùþÿÂç€ÿŒ‚¢ÿþ‚ÿø²„ÿß^‚9ÿÊààP†™ÍÈ·¯±¬°¶»ÁǺÀ×Ýâèíóø±ùƒÿsDã‚ÿÐÙÿÿ½ ¨„ÿý­„ÿáa‚,͸¸¦9†œÜâçà¹øþ‚ÿÙЄÿ¼îƒÿÑ#žüÿÜÍÿä-„ ÿúòïéäÞÙ¬ÍÈý¸²¬¯.>ÜÈÇÐK†º€ÿ÷³„ÿãÆ„ÿÇã„ÿ[(ÕÿéÀþ]…5 «°µ»ÀÆËѯ×âçíòøý» vÿÞÌàP†º€ÿþ®ýƒÿí¼„ÿÒØ„ÿ­@có€ÿö³’ƒÿ  øþÿêààç÷·ò‚ÿ â5½ÿäÅàP†»ÿµõƒÿ÷²„ÿÜÍ„ÿȤý€ÿˆ…8èÿ 7xYKDDITK{¬ÝÿÿÎJ€ 5þÿë¾àP†»ÿ¾ìƒÿþ®ûƒÿç„ÿ ÔÕŽ¥ÿÿï)‡”ÿý …ׂÿ³ØP&Hv£³²µÅÊÐÖÜâè¼áúƒÿ°ùÿÿà… FÄÿÿþÿÿ± Dÿÿûõðêµ»C0_“½„ÿÊß„ÿ¼íÿÿu „ /Ó¼ÿÿþÿÿ² H®®´ºÀ²«A€X¦íÿÕÔ„ÿÈáÿ© Óû¯þÿÿþý³ ‹ÿÇÇPˆ…$R¢ìÿàÉ„ÿÔÕÝ/ Ëÿÿ¶óÿÿþýÿªC„×€ÿÎÁP…N‹M“¯„ÿàÉS„Í€ÿÄå€ÿýÿžƒ .v½éó¥€W€ÿÕ»P†¼©ˆ Hœëÿì` †,ÛÿÓÖ€ÿýÿžˆåéÔÃÂÎåÛ¶øþÿÿý¼‚ÛÿÿÛ´P†½ÿÅ&  E™êÿ´€VìÿûõðêοØÓÌÅ·žÿþþÿÿﻃÿ’€ ÿÿâ®P†¼ÿÿêV‹ H"…g´´®®´ºÀ°Ñ×Üãáž¿ÿþ‚ÿó¶ƒÿý Yÿÿé©P†¼ÿ©€‘…<°èöüÿü¯ýÿþþÿž…ÿø²„ÿk‚;ÿÿð£P†¼ÿÿüöñÈ] —&®ûÿÀé„ÿ¸ñÿÿþÿÿ…ÿý­„ÿ~‚5ÿÿöL† ‰µ¯­³¹¹²ºa ‚‡„.¢ú€ÿÍÜ„ÿÆã‚ÿÿÿþƒÿ®ûÿÿùóíçL3¹³­—8†°õû€ÿ ðºÿÿøž?‹GÃþ‚ÿ ÚÍüûúúùùúÐÐüþ€ÿâæàÚÕÏÉí¶²¬±·¼­dñöüšN†¼‚ÿù±‚ÿêžX €  1o·å½ÿüøõ¿yrN3 #6n¥ßøó™³¿ÂÇÍÓÚâµèøþÿÿùI€­€ÿ K†¼ƒÿ¯û„ÿ °èâˆvlilT«Ðù€ÿø±ÿýöè¤VŠ7m mŠi\[f} ˜Øòûÿòa'û€ÿ¦J†¼ƒÿ¸ò„ÿºï„ÿ²ø„ÿ®ë¼[Œ€¤U¨ÐAƒ ‹ÿ­G†¼ƒÿÁé„ÿÄå„ÿ¼í‚ÿüî}1„…  „;þÿ²E†¼ƒÿÊá„ÿÎÛ„ÿÇâÿò´6€‹£ #Ñ‚ÿ¸C†¼ƒÿÓׄÿØÑ„ÿÒ×ÿÿúÑ[ƒ ';EFC6) ‰©¶ƒÿ¾A†¼ƒÿÛÏ„ÿâÈþøòìæàØÃºÈ·t‚ "T‘ÆâèØÄúÿÿöÂ9…§Q„ÿÃ?†¼ÿùóؾáÛÕÏÉý´­¬²¸¾ÄÉÒ˸Ä] (í‚ÿﺃÿû!„ 3§›ƒÿÊ=†¾¸²¬°·¹°ÉÏÕÛáæí별ÿ óŽBx¤„ÿü®ýƒÿþ”Cƒ©–ÑÊÅ¿¹›5†©ìòøþÿÿö´„ÿþ®ý‚ÿ ü±9»ÿ±ø„ÿ·ò„ÿ¼ËA„¢&„ÄßåëñÐ9†¼ƒÿþ®ý„ÿ¶óÿ û¤ NÚÿÿ½ì„ÿÄå„ÿÊÞÇ(€ ˜  +:m§Él €nÿÛ6†·„ÿµõ„ÿÀé€ÿû Oà€ÿÉà„ÿÐÙ„ÿØÑÿ™€˜ .Š€ˆ˜®¼¶ÿ‰‚é€ÿà6†±„ÿ¾í„ÿÊßÿÿü¦€BÚÿÕÕ„ÿÝÌ„ÿæÂÿé[€™…ÿﺂÿr€›€ÿà8†¬„ÿÇã„ÿÔÕÿÿ¶!€)‚ÿáÈ„ÿê¿„ÿô´ÿÿ¶3 šì„ÿô¶‚ÿïa€ÿà:†¦„ÿÏÛ„ÿ ÞÌÿÌ/ ˜ƒÿí½„ÿ÷²þøòìæàÚԬȳvi›ÿþþ‚ÿù±ƒÿd?€ÿà<† „ÿØÒ„ÿèÁåH€Iî€ÿþøòç°áÛÕÏÉý·¬¬²¸¾ÄÉÏÕ·Ôçíóøô›â„ÿý­þ‚ÿ„‚4€ÿà?†›„ÿáÉ„ÿñ±q‚Ľ¸²¬±·½®ÆÏÕÛáçíò½ë„ÿÌÝ€ÿýù›Úý„ÿ¯û‚ÿ^A€ÿà@†•ÿúôîØ¹ÜÖÐÊľ¸°v‚^«ãìòøþ€ÿ½ì„ÿËÞ„ÿÚÏ€ÿþÿ›Ìýþƒÿ³öÿìe€ÿàC†ƒ¿¹³­°¶¼¿¯ÎÔÚàåìñÙ#¸ºð„ÿÉà„ÿÙÑ„ÿéÀ€ÿþÿ›¿…ÿ¸ñ€ÿûY‚ €Å¿¹6††ëñ÷ý€ÿü¯ƒÿöq‚^ùÅå„ÿÕÔ„ÿæÄ„ÿ÷²ÿýÌšUhYV^k‚¬»º´®L‚ÔäêñØF†……ÿ²ùÿþǃ˜ÿÏÚ„ÿáÈ„ÿó·…ÿ²÷€ÿýÿ› "MšÅR €{ÿàI†€þ„ÿºðÿõL‚:ÔÿÚЄÿí¼„ÿý®ü„ÿÀéÿö¤€*òÿàK†ƒø„ÿÃç€ÿýºƒbÿÿåÅ„ÿù°…ÿ¹ð„ÿÎÛÿÿþþÿ¢ƒ Ç‚ÿàM†ˆñ„ÿÌÞ€ÿ÷F‚“ÿÿðº…ÿ±ø„ÿÇã„ÿÜÍ‚ÿ¬ †ƒÿàO†Žé„ÿÕÕÿÿþÉ…+Àÿÿú¯þ„ÿ½ì„ÿÔÖÿÿùòìæàͶÍÇÀº±¡ªh¾ƒÿàP†”á„ÿÞÌÿÿúbDê€ÿ²÷ƒÿýÇ×ëäÞØÑËŸ°³¬°·½ÄÉϬÜâéïñâª}ƒÿàP†™Ú„ÿçÃÿÿë„aóïéâµÎÐÊĽ·°¬¯²¿ÅËÑØÞäÞ¹÷ýƒÿ´õÿÿþÿÿ¤ Ë‚ÿàP†ŸÒ„ÿðºó댆313738?DLRX]cWMcbb_XQJE-<5*>»€ÿÂçÿÿþþ÷¡ƒ.ûÿàP† ™¿ÙÓÌÆÀ¹³­¬¶¹4†‚€4ü€ÿÑØÿú¢D²áGzðêãÝ»A† ‹´Ñ×Ýäêðöü¯ü ~ÿßÊÿüš+m`_k„¦ÒݹáÛÕT‚³ÀÆÌºD†±»…ÿ·ó«ƒ™"Øÿí¼ƒÿ™»ÅÀº´®¯µ¹¯ÈÎÕÛF‚¦€ÿõ€‚/Ê´…ÿÀéh†€ƒ„\‚ÿú¯þÿÿþýÿ™ Äàéðöüÿÿôµÿí hÿëy>Q€RPbÌý­þ„ÿÉà/… /ˆ—§µÀ‡ÆÈƒÉ ¯ÈÈÇÆÅÃÁ«‰·õƒÿ¶óÿÿþþÿ™þ„ÿù±‚ÿ\B‚ÿèÂ…ÿ³÷„ÿÒÒ…{ƒÿ·ó„ÿÖÓ„ÿö´…ÿÄäÿÿþÿø™ôþƒÿý­þÿƒ‚4‚ÿî»…ÿºð„ÿÛ«„ŽƒÿÁè„ÿáÈ„ÿþ°ú„ÿÒ×üöîéÓ™ÿÿþƒÿ¯ûÿj=‚ÿõµ…ÿÂè„ÿㆆžƒÿÌÞ„ÿí¼ƒÿüõ¹ÜâÜÕÏÉü²¬®´¹À¼™˜†ÿ´ö€ÿõ^‚ÿü®…ÿÊà„ÿíg†¥ƒÿ×ÓÿÿûõïèâׯÏÈ»µ¯®´±¸ÇÎÔÚáçíæºÿýÔ˜þÿþƒÿ¹ñÿÿý…€ –ƒÿ¯ú„ÿÑÙ„ÿõN†çáÛÕÎȹ±µ®®µ»ÂÈΰÕáçîõûÿÿÖÓ„ÿü®ýÿþ˜ç…ÿ½íÿù©‚áƒÿ¶ô„ÿÙÑÿúôíå=† {ÂÉÏÕÛâܹõûƒÿ¾ë„ÿãÆ…ÿ¸ñÿÿþÿÿ˜†ÿ Âèå‘c„ÿ½íúóíæàÚÔÀ¶Àº´­¯¶¼Ã6†œƒÿø²…ÿÊß„ÿñ¹…ÿÆâ‚ÿ˜Ú…ÿ²¤PÈàÙÓÌÆÀ¹®¬°¶½ÃÉÐÖкéðöüÿ8† ‡„ÿ°ú„ÿÖÓ„ÿý®ý„ÿÕÔÿÿýþÿ˜ ÿÿþÿøòÞµA„ kÄÊÐÖÝäêðÇà„ÿðº…ÿ;†b„ÿºï„ÿâÇ…ÿ¸ñ„ÿãÆÿüÿ—¦³²¬±¨\† {±…ÿÑÙ„ÿ÷³…ÿF‡=ëƒÿÅä„ÿî¼…ÿÅå„ÿð¸ƒÿ—¶ê÷þÿ|ƒþ­þ„ÿØÒ„ÿþ­þ„ÿ\‡¦ƒÿÐÚ„ÿù°…ÿÒØ„ÿý®ü‚ÿ—ÿÿþÿÿ7€ 4œÿÿ²ø„ÿßË…ÿ´ö„ÿ}ˆ]ý‚ÿÛÎ…ÿ³÷„ÿßÊ…ÿºï€ÿþõ˜ü€ÿ;hÈ€ÿ·ò„ÿåÅ…ÿ»ï„ÿª†²‚ÿåÄ…ÿ¾ë„ÿ쾂ÿ þöûÄÖçáÚÔ¾˜ÿþÿÿ$e­ùÿ½í„ÿì¾…ÿÃç„ÿÞˆSìÿð¹…ÿÊ߀ÿûôîçܰÔÎÇÁ´i[¢±²ÃÉÎÕΙ— ÿÿýÿñ@2Lg»ôƒÿÃç„ÿó·…ÿËà„ÿû!ˆ ˆÿû¯úôîçáÛÔι¶º´®¯µ¼ÃɰÐÜâÊf©äŃÿ—ûÿüÕÉо…ÿÈâ„ÿù±…ÿÒØ…ÿ[‡ŽÈÁº´¬¯µ»ÃÉÏÕÜпïõü‚ÿ Àêÿ°@µò¶€ÿþÿÿ—…ÿðº…ÿÎÜ„ÿþ­ý„ÿ ÚÑÿÿûõîçáÛ˜‰$§èïõ½ì„ÿî»…ÿÍÅs5³õþ¯ûÿÿþÿð—þ„ÿõµ…ÿÔÖ…ÿ´íîçáÛÕÎȹ±´®¯µ»ÂÈϵ:‡,¹ÿÿÉà„ÿú¯þƒÿü„/XÓ€ÿ¼íÿö—þþƒÿù°‚ÿûõîÌÃÛÕÎÈÁ»µ®¬´»ÂÈÏÕÛâÙ½õüƒÿË©†!þÔÕ…ÿ³ö‚ÿ­K †éÿÊÝ‚ÿ—ùÿûõïèáÛÔ¬ÈÁ»µ®®µ»¹·ÏÕÛâèïõûÁé„ÿñº…ÿÕÎV†eÃÊ…ÿ¿êÿÿú£J€,µö€ÿ þÿØÐÿÿþÿûÿ–®­®µ»ÂÈÏÕ®Þèïõû€ÿåÅ…ÿÈâ„ÿø²…ÿÝÍÖ†%_ä„ÿÊßÄx2DÔÿþ€ÿûùÒ±ëÿÚÔÿ—âú„ÿ´õ„ÿê¿…ÿÎÜ„ÿþ®ý„ÿæÄü¤‡"V”½Ïǯ€A w²ÿÿÿ ÷ýþƒÿ¹ñ„ÿð¹…ÿÕÕ…ÿµö„ÿî»ÿô†‡ˆ¨þ…ÿ½ì„ÿö´…ÿÜÎ…ÿ¼îÿþÿÿþÿÿ÷²ÿÿêg™ ªÿþþƒÿÂç„ÿü®„ÿþãÇ€ÿþÿþÿÿÀâ€ÿ úùöðâ£ÿ –¬†ÿ Çáÿÿþÿþÿþÿ®ü€ÿþþÿýá¸ÿúÿÿéÿÿª‹’ ­ðýÿÿþÿÿþÿËÞÿýýÿýÿüþ¶çðÿÿŒ ¯ ÿüÿüüûúÿóĹ­‡ ÿžÿÐ fªÿÿÔëòÿôñÿÿþÿ×’-xÈõüÿûóÿþ€ÿÆ¿ƒ ÿé¿ÿþþÿÿë׌4/àøÿÿýñ‚ÿ¶Ì€ ÿÿäªÿÿþëò÷ðõƒÿóù‚ÿó¸E€“nÙöÿñý€ÿûª€ÿßâ‚ÿ óøïÿÿþÿÿýÿðûÿþÿõùþ‚ÿõø€ÿöÊK€Ž‚zàðûÿ¦¿ÿûþ€ÿùòÿþþýðþÿÿþ€ÿóúÿþÿ÷÷ƒÿ÷÷ÿÿæw€‘ ¤èÿ¦óÿÿ€þÿûóÿýÿþðþƒÿôúƒÿøöƒÿùõúÁ/Œ 8€E€aÞþüûÔ¥ÿþ‚ÿüò„ÿñýƒÿõùƒÿùõƒÿû蕊 ?zÅüûÔ4†)¹ðñí¥„ÿýñ„ÿòüƒÿöøƒÿûóƒÿëm $Bx¾ððñòóôŸ†­úú¥ìƒÿþð„ÿóûƒÿøöƒÿüòÿÿþýüæ^)KƒÇüùóþ‚ÿþp„÷¥ÿýþ‚ÿðþƒÿôúÿÿþýüûöóø÷öõôóòðñððñß[Œ/PŒÎÿýñ„ÿçH„¥€ÿþþýüûðøø÷öõôóññ€ðñòóóñö÷øùúûüðýþÿóm…6[’Ëó„ÿðþƒÿóÊ.ƒ ¥ì€ðññòóðôö÷øùúûõ÷þ‚ÿûó„ÿñýÿýˆ ;c˜Òÿÿýñ„ÿòüƒÿöøc„§éûþ‚ÿ òüÕ‘¬×ÿ÷÷ƒÿüñ„ÿóûÿ«„@i—Ô‚ÿþðþƒÿôùƒÿ¿t/¯ÿýƒÿ óÊLD|µôƒÿþð„ÿôúÔ8Es¤×üñ„ÿòüƒÿ÷÷ÿÞ†)ƒ«…ÿô[ƒ&gÀ‚ÿþðþƒÿ öðoG|«Ú€ÿþðþƒÿôúƒÿùõ€ÿ¸K‚ ­ÿüþ‚ÿó2€-…óÿñýƒÿ ÷¦h°Ò„ÿñýÿþýõ÷úùø÷ööóñóìŽ ƒz‡­…ÿöEƒZÝ€ÿòüƒÿÞQ‚Áûòüûúùø÷öñóóòñðð€ñ ôõö÷øùùðî€Üý]¬üƒÿ÷®€DÙÿÿóùüûúùø÷𠂝ððòóôõö÷øóöûüýþÿÿúô„ÿä{ i÷ÿå*«…ÿ÷ô»q0† ?ßððñòóôõöÜRƒºþðþƒÿöøƒÿûóƒÿú ‚Äþÿÿ¾ªÚóöõôóòñððñãÊ¡I…^þöø‚ÿ¯ ºÿñýƒÿøöƒÿýñƒÿœ‚%èÿ‹ª ¿ôøùúûüýøõÿ㥀­÷÷ÿór„ºÿóûƒÿúô„ÿðþÿÙCƒeòÿõOªÿþ‚ÿúô‚ÿ þÓ39øöÿÍ2„ºÿõùƒÿüò„ÿòüÿö…€›ú‚ÿß§úƒÿûó„ÿ Ô'½ôÿ§…ºÿöøƒÿþð„ÿôú‚ÿö¥"Åü€ÿþýü¯©ùƒÿüò„ÿ óÀ yó€ÿów…ºÿøö„ÿðþƒÿöø‚ÿþùÉB‚ Ñòòñððñòíx¨ÿÿþÿüò„ÿôùBLò€ÿÚFƒºÿùõƒÿþòúüûúùø÷óòôóòñððñçP‚%Ùöüýþ€ÿüá@¥÷ÿþÿýñ„ÿõù}‚6ñ€ÿÄ…µøõñõôóòñ€ðñòóôõö÷öòúûüþþÿÿÀ/y(5àõƒÿþðÕ¦ÿþ‚ÿþð„ÿöø{‚6ð÷öõ©† ²ööðùúûüýþÿöøƒÿüò„ÿ š EÛäK?äó„ÿòùª¦õÿþþýüûúðø÷ööõôóñð4Kðöøù“†ºÿþðþƒÿ÷öƒÿþðþƒÿ {qñÿö¤Òúð„ÿõùól¥ï€ð ñòóôðõ÷øùùúû÷²‚ òüÿô}„ºÿÿñýƒÿùõ„ÿñýƒÿd”€ÿþÿÿñýƒÿ÷÷ÿâ.¤ öûýÿÿûúÿòüƒÿ ÜÇóûÿëh†ºÿÿòüƒÿûó„ÿóû‚ÿïR©ƒÿóûƒÿúôÿÿÆ£ˆ¢\'>o¬îþÿÓ<ÿôúÿå[†ºÿÿôúƒÿýñ„ÿõù‚ÿâF´ƒÿõøƒÿüñÿÿ÷£‚Iv € ¸ÿõøÿáR†ºÿÿöøƒÿþðþƒÿ÷÷‚ÿÚ? ¹ƒÿ÷õûúùø÷öõðóòñÜA£…ƒ bÿÿ÷÷ÿßM†ºÿÿ÷÷„ÿñýƒÿùõþýüûúÒ; ³õôóòñ€ð òôõö÷øùòøüýý¨¶ >ýÿÿøöÿàN†&ºÿÿùõÿÿþýüûúòö÷öõôóòñððñóóôÒ> ±ùúûüýþüñ„ÿõùÿýÜ,µ.ò€ÿùõÿàO†´öõòðñððñòóôòó÷øùúûüûñ‚ÿåJ«ƒÿþðþƒÿøöÿðp¶ Zðùø÷ôñôÕK†´øùùñüþ‚ÿ÷÷ƒÿþðþÿõZ„ÿòüƒÿúôü§¥Uðö÷öñúÜO†ºÿÿþð„ÿùõ„ÿòü‚ÿm„þƒÿõùƒÿýñϵ ÿÿýñÿàP†º€ÿðþƒÿúô„ÿôú‚ÿˆ_ëƒÿ÷÷ƒÿþÚE¤† 3M  ÊÿþðÿàP†º€ÿòüƒÿüò„ÿöø‚ÿ¬1Óƒÿùõƒÿùz¤AA/&!!$*2Jyµúÿ¢%€ JÿÿðþàP†º€ÿóûƒÿþðþƒÿøö‚ÿØ:´ƒÿüòƒÿ´¤ ÿÿâÇ»¹ÂÑèƒÿ ¿ÓÿñýàP†º€ÿõù„ÿñýƒÿúôƒÿdø‚ÿýðüûúùøÓ§ÿþþ‚ÿüò„ÿ š …ÿóûàP†º€ÿ÷÷„ÿóûƒÿüòþýüûúù– 1Ïôóòñ€ðòóôõêP©„ÿüò„ÿø-SÿôúàP†º€ÿøöÿÿþýüûúòõ÷öõôóò€ðòòóôõÙ;¡úûüýþÿôú€ÿŒ‚¢ÿþ‚ÿýñ„ÿùr‚9ÿõùàP†´öõôòðñððñòóôòó÷øùúûüýñýƒÿ{Dã‚ÿöøÿÿ½ ¨„ÿþð„ÿùz‚4öòòÕK†´øùúùòýþ‚ÿøö„ÿòüƒÿÕ0žüÿøöÿä-„ ÿþûüûúùøðöõôóòñðð@GøõõÜO†º€ÿýñ„ÿúô„ÿôú„ÿ|(Õÿûóþ]…5 îðñòóôõöð÷ùúûüýþÄ vÿùõàP†º€ÿþðþƒÿûó„ÿöø„ÿßCcó€ÿýñ’ƒÿ  øþÿêààç÷òü‚ÿ â7½ÿúôàP†»ÿñýƒÿýñ„ÿøö„ÿõµý€ÿº…8èÿ 7xYKDDITa‚¬ÝÿÿÎJ€ 5þÿûóàP†»ÿóûƒÿþðþƒÿúô„ÿ ÷÷Ž¥ÿÿï5‡”ÿý …ׂÿñÞP2`¡â€ñ ôõö÷øùúóùþƒÿðþÿÿà… Oîÿÿþÿÿ± DÿÿþýüûñØM0_¤å„ÿõù„ÿóûÿÿu „ /àòÿÿþÿÿ² aððñòóñÖM€(X¦íÿ÷÷„ÿõùÿ© Óþðþÿÿþý³ ŒÿõÚPˆ…$R¢ìÿùõ„ÿ÷÷Ý/ ËÿÿñüÿÿþýÿªC„×€ÿöÙP…N‹Mß„ÿùõS„Í€ÿôú€ÿýÿžƒ:v½éó¥€W€ÿ÷ØP†¼©ˆ Hœëÿû{ †,Ûÿ÷÷€ÿýÿžˆåéÔÃÂÎåëçøþÿÿý¼‚ÛÿÿøØP†½ÿÅ&  E™êÿ¸!€Vìÿþýüûöóø÷õóðžÿþþÿÿüòƒÿ’€ ÿÿù×P†¼ÿÿêV‹ H"…ìñððñòóôðö÷øú÷ž¿ÿþ‚ÿýñƒÿý"YÿÿûÕP†¼ÿ©€‘…CÕïûýþÿþðþÿþþÿž…ÿýñ„ÿo‚;ÿÿüÔP†¼ÿÿþýüëu —&®ûÿóû„ÿòüÿÿþÿÿ…ÿþð„ÿ€‚5ÿÿýÓO† ²ñððñòòñás‚‡„.¢ú€ÿöø„ÿôú‚ÿÿÿþƒÿðþÿÿþüûúTAòñðÒK†¹ýþ€ÿ üòÿÿøž?‹WÃþ‚ÿ øôüûúúùùúòóüþ€ÿ÷úùø÷öõôðññððòóÚküýþÒO†¼‚ÿþñ‚ÿêžZ  1o·ôóÿüøõ͘rN3 'Co§àøóÌîîííîïòöñúýþÿÿùI€­€ÿÔO†¼ƒÿðþ„ÿ ðíâˆvlins«Ðù€ÿýñÿýöè¢UŠ:rmŠi\[f} Ååòûÿòa'û€ÿÕN†¼ƒÿòü„ÿòü„ÿñý„ÿíïºYŒ€¤U¨ÐAƒ ‹ÿÖN†¼ƒÿóû„ÿôú„ÿóû‚ÿüîž1„…3 „;þÿ×N†¼ƒÿõù„ÿöø„ÿõùÿò±4€‹'£ #Ñ‚ÿØM†¼ƒÿ÷÷„ÿøö„ÿ÷÷ÿÿúÏXƒ #0K]`\K6% ˆ "©¶ƒÿÙM†¼ƒÿøö„ÿùõþýüûúùøôòõå‚*e©àùúøôþÿÿõÁ~8„!§_„ÿÚL†¼ÿýüøóùø÷öõôóñððñòóôõ÷õòÖa‚ 4ð‚ÿüòƒÿú“)„f§ ›ƒÿÛL†³óòñððòòðõö÷øùúûûñ„ÿ ü¹@!}á„ÿþðþƒÿþÈBƒ "© ­öõôóòÓK†¸ûüýþÿÿýñ„ÿþðþ‚ÿ ü®(<Àÿñý„ÿòü„ÿóÔ>„¢ 3„$àùúûüÜK†¼ƒÿþðþ„ÿñüÿ û¡RÝÿÿóû„ÿôú„ÿõùÃ%€U— 3Lu¯Ïm €nÿßK†»„ÿñý„ÿóû€ÿûVä€ÿõù„ÿöø„ÿøöÿ•€:˜ .Š€ˆ˜®Èèÿ‰‚é€ÿàK†¹„ÿóû„ÿõùÿÿü¢€GÜÿ÷÷„ÿùõ„ÿ úôÿçW $™…ÿüò‚ÿr€›€ÿàK†¹„ÿôú„ÿ÷÷ÿÿ²€-Ç‚ÿùõ„ÿûó„ÿýñÿÿ³1šì„ÿýñ‚ÿïa€ÿàK†·„ÿöø„ÿ ùõÿÉ,ƒÿûó„ÿýñþýüûúùø÷ðõô漤•ÿšÿþþ‚ÿýñƒÿd?€ÿàL†¶„ÿøö„ÿ úóãDañ€ÿþýüúðùø÷öõôóòððñòóôõö÷ò÷úûüüô›â„ÿþðþ‚ÿ„‚4€ÿàL†¶„ÿùõ„ÿüèmƒ$²ôóòñðñòóðôö÷øùúûüóû„ÿõø€ÿýù›Úý„ÿðþ‚ÿ^A€ÿàM†´ÿþýûøòø÷öõôóòîž‚pîùûüýþ€ÿóû„ÿõù„ÿøö€ÿþÿ›Ìýþƒÿñýÿìe€ÿàM†±óòñððñòóðö÷øùúûüÛ"'¾òü„ÿõù„ÿøö„ÿûó€ÿþÿ›¿…ÿòü€ÿþ\‚›ôóòÓK†²ûüýþ€ÿþðƒÿök‚düôú„ÿ÷÷„ÿúô„ÿýñÿýÌšXn`_i{˜¾êòòñði‚íúûüÞN†±…ÿñýÿþÞÿöø„ÿùõ„ÿüò…ÿñý€ÿýÿš !,X¢ËR €{ÿàN†°þ„ÿòüÿôD‚=Ùÿøö„ÿûó„ÿþðþ„ÿóûÿö¤€*òÿàO†±ý„ÿôú€ÿý¶„hÿÿúô„ÿýð…ÿòü„ÿöøÿÿþþÿ¢ƒ Ç‚ÿàO†²ü„ÿõù€ÿ÷>‚™ÿÿüò…ÿñý„ÿôú„ÿøö‚ÿ¬ §ƒÿàO†³û„ÿ÷÷ÿÿþÃ…/Æÿÿþðþ„ÿóû„ÿ÷÷ÿÿþüûúùöñöôòòðäªoóƒÿàP†´ù„ÿùõÿÿú[Gð€ÿñýƒÿþô÷ûúùøöõôòðñððòóôõöðøùûüû⪤ƒÿàP†µø„ÿúôÿÿç„ fýüûùñööõôóò€ð ñóôõöøùúùòýþƒÿñýÿÿþÿÿ¤ Ë‚ÿàP†¶÷„ÿüòýù‘…D@ACDEGLSW[_c`_cbb_XQJF><5*A€ÿôúÿÿþþ÷¡ƒ.ûÿàP† µóø÷õôóòñððñï:†‚€8ÿöøÿú¢V²áG~üûúøØM† ³ñö÷ùúûüýþðþê…˜ …ÿùõÿüš+m`_k„¨Úøòùø÷d‚ëóôõÙN†ºò…ÿòü¤ƒ™#Þÿûòƒÿ™ðóóòñððñòðõö÷øN‚¦€ÿõ€‚/Ðñ…ÿóúb†€ƒ„ e‚ÿþðþÿÿþýÿ™ ñøûüýþÿÿýñÿí hÿë†KQ€RPbÌþðþ„ÿõø(… 1‰—¨¶ÀúÇÈƒÉ ÀÃÈÈÇÆÅÃÁ¹­¸ùƒÿñüÿÿþþÿ™þ„ÿþð‚ÿ\B‚ÿúô…ÿñý„ÿ÷ì† ‚ƒÿòü„ÿ÷÷„ÿýñ…ÿôúÿÿþÿø™ôþƒÿþðþÿƒ‚4‚ÿüò…ÿòü„ÿøÀ„•ƒÿóû„ÿùõ„ÿþðþ„ÿö÷þýûûõ™ÿÿþƒÿðþÿj=‚ÿýñ…ÿôû„ÿú›†§ƒÿõù„ÿûòƒÿþýòøùø÷öõôóñððññóñ嘆ÿñý€ÿõ^‚ÿþð…ÿõù„ÿûz†¬ƒÿ÷÷ÿÿþýüúù÷ðöõôòñððññòõö÷øùúûúòÿýÔ˜þÿþƒÿòüÿÿý…€ –ƒÿðþ„ÿöø„ÿý_†«úùø÷öõòðñððñòôõöð÷ùúüýþÿÿ÷÷„ÿþðþÿþ˜ç…ÿóûÿù©‚áƒÿñý„ÿøöÿþýûúK† ¤ôõö÷øùøòýþƒÿóû„ÿúô…ÿòüÿÿþÿÿ˜†ÿ ôúå‘c„ÿóûþüûúùø÷óñóòñððñóô<†£ƒÿýñ…ÿõù„ÿüò…ÿôù‚ÿ˜Ú…ÿÛµP #Ùùø÷õôóò€ð ñóôõö÷öòûüýþÿ9†„ÿðþ„ÿ÷÷„ÿþðþ„ÿ÷÷ÿÿýþÿ˜ ÿÿþÿýüìÆžT„ “ôõö÷øúûüôù„ÿüò…ÿ<†h„ÿòü„ÿùõ…ÿòü„ÿùôÿüÿ—èïñðñÞv"† }ð…ÿöø„ÿýñ…ÿK‡Añƒÿôú„ÿûò…ÿôú„ÿüòƒÿ—Úúýþÿ|ƒþðþ„ÿø÷„ÿþðþ„ÿa‡­ƒÿöø„ÿþð…ÿöø„ÿþðþ‚ÿ—ÿÿþÿÿ7€ 4œÿÿñý„ÿùõ…ÿñý„ÿ‚‡cƒÿøö…ÿñý„ÿùõ…ÿòü€ÿþõ˜ü€ÿ;hÈ€ÿòü„ÿúô…ÿòü„ÿ¯†"¸‚ÿúô…ÿóû„ÿûó‚ÿ þöþô÷úù÷÷ò˜ÿþÿÿ$e­ùÿóû„ÿûó…ÿôú„ÿâˆXïÿüò…ÿõù€ÿþýûúøð÷öõóé‰àðñôõõ÷õÌ— ÿÿýÿñ@2R»ôƒÿôú„ÿüò…ÿõù„ÿþ%ˆ Žÿþðþýûúùø÷öòñòñððñòôõðöøù×h®úôƒÿ—ûÿüÕÉÞó…ÿõù„ÿþð…ÿöø…ÿs‡ ­õóòñððñòôõö÷øöóüýþ‚ÿ óûÿ­>"ºüñ€ÿþÿÿ—…ÿüò…ÿöø„ÿþðþ„ÿ øöÿÿþýüúùøÈŠ-½ûüýóû„ÿûò…ÿöÚp8¶÷þðþÿÿþÿð—þ„ÿýñ…ÿ÷÷…ÿñûüúùø÷öõòðñððñòôõöí=‡/½ÿÿõù„ÿþðþƒÿü“6\Õ€ÿóûÿö—þþƒÿþð‚ÿþýüõôø÷öõóòñððñòôõö÷øùøóýþƒÿõ¶†$¡ÿ÷÷…ÿñý‚ÿ«I‹ëÿõ÷‚ÿ—ùÿþýüúùø÷ðõóòñððñ€ò ö÷øùúüýþóû„ÿüò…ÿ÷íP†hÜõ…ÿóûÿÿù¡H€0¹÷€ÿ þÿ÷öÿÿþÿûÿ–ïïðñòôõö÷ðùúüýþ€ÿúô…ÿõù„ÿýñ…ÿùöÓ †*|ç„ÿõùÂv2€bÙÿþ€ÿûùõíëÿÚÔÿ—ùý„ÿñý„ÿûó…ÿöø„ÿþðþ„ÿúôü ‡ #X–½ÏÇ­K #¤åÿÿÿ ÷ýþƒÿòü„ÿüò…ÿ÷÷…ÿñý„ÿûòÿ󂇇 ¨þ…ÿóû„ÿýñ…ÿøö…ÿóüÿþÿÿþÿÿüñÿÿéb™ªÿþþƒÿôú„ÿþð„ÿþúô€ÿþÿþÿÿò÷€ÿúùöðâìÿ™«†ÿ ôøÿÿþÿþÿþÿðþ€ÿþþÿýùðÿúÿÿéÿÿÔ¿¢ ­ðýÿÿþÿÿþÿõøÿýýÿýÿüþð÷ðÿÿ° ¯ ÿüÿüüûúÿóëç¹÷ ¥t8mk@AlލºÅǶ¡„_0  !G^I\q‹ E‘Ôÿÿÿÿÿÿÿÿÿÿÿÿÿÿüîïúÿÿÿÿÿÿÿÿÿÿÿÿ   O[k¹õÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿ#  ZMJXl‚›·ßîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿN 'b9L[o‚•¯ßëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒ:J[oƒ—¶ÙÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕÿÿÿÿÿÿÿÿÿÿÿýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýûéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿü:Úÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿû4Îÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýg ¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿË ¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþW*Èÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæ? œÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿˈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿü ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñatÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÌhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿø‹]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔ+UÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿøŒlÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÉaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿîn:ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¬3ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÐ3,ÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìj$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿš ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿË1ýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÝNBõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿþÿÿÿëeâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿövßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÿÿþÿýƒKÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýèÿÿÿÿŠSòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÑÿÿÿÿŒ$¸ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿôÿþÿÿ‰@ìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿü€@íÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿór'¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿè`]ôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙGhÜúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÆ)*¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ°]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿRÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿå\LÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÉ"DÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŸ;ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿø\3ÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò kÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿí/*ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòX jÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‰@¯åÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÏ BØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿº ©ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÏ=çÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæ<Bñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûg-Êÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿmÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿ¦ v÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¾0‹ïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕ'•ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôzƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€yÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‘oÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¨hÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÃ]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞ1cÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýW}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ®tÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿë{€ëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚU -Àÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿ˜ÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ©%:áÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿ¯&Còÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿi2ÓÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÌ- ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿäBœòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿõej°àýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ‹ MÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ°·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿì²5­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×K £ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÅ ˜ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿë/ŒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿK‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿhxÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿˆ Jµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ«ÎåùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓ%°øÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ5‹ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿO5Ùÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ¡Cóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ— 8Ýÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿºÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿé#%¶ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ8wæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿU6†üÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿxHòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ  9åÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÏÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ&ÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿS¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ† ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ…¨ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ² žÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿè •ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ*ŒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿDƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿh©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ•{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÈiÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿSYÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿiQÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿxLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿª Dÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ8ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿ92ûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíÞ@b÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿé¾£…mVB13; -åÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûæêððùÿÿÿÿêf- !Ùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñéåæêñúÿÿÿÿÿÿ©'ÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙ¾ÈÿÿþÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿàS ÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÞ³ŒlW>.  Uæÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ÷|ºÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÀ›‹ŽK6% Šöÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿ÷Š´ÿÿÿÿÿÿÿÿÿÿï׫‘oX?[!uÐÿÿÿÿÿÿþþÿÿþÿÿÿÿÿÑp y¦~cL7% [”Áãüÿÿÿÿÿÿã´u( %%ic09ÚÐ jP ‡ ftypjp2 jp2 Ojp2hihdrcolr"cdefjp2cÿOÿQ2ÿR ÿ\ PXX`XX`XX`XXXPPXÿdKakadu-v5.2.1ÿ Ùãÿ“ÏÃEÀr¤Ð|—{+;´‚ ¥"fQ1_w, ¬÷vT?}Áñc.Wvª÷åCµ$ED>ÌÎðÁLùÊR¤Ú2¹@€e§íÜHÆRÝÕfæy’]ñ:ú6þrÍIàT ùI ¶c½+¾o"N©cWé}kûËvw¬¾ª›Bø£#½¼~.L—ªB´Î—b-ËÀˆ©¡ø;¶Ù5uˆV {2B ¯k¾Íñß`„CÀAq-Üœ¸©¦°ô浊%„±–Æô¬ù¿OùpïLFæpb¶©…NŽ„[ÞIêw¦¿²qº˜Œ\_üß¼o_þêùŽ4ŽÛùŸpû‹Îô‚Þ½¯ÁdûŹе"ãÛJØz ëŸ|Òã­–Y<Àù.@.FpϺÍØ ™ÎnŽÅ¼6|©2Îs–]·j¯pÞü§¡q‰£ÎUzó6¨€wßš…„=š‹ÆQè›Fõø%‡¿•/~ÎZ+'–΀|1|aãœÕÆvŸð~ƒ@ê”Â5ÇQé€b mM¸ŒjÀù, uˆÂLË~"Å wÔº€m=%F¥7¤»žüïT±X%€°¿{(üÞ®Lj+;?î T`e‘x e³\Pì¹ýÎ’µ.Õ!Ë)«Ï€~WLÅûC’â^€~™Ýš»ú-?ŸO¥Û—ÏÂÓ óæiÆ ŠÉÔ|—£ú¶"´Éñ“uRZÉýªÒ¢2>ýBV´¦ÿ/b*Ø+Açìc‘·v¢cKˆ@FlÀG÷½mSbÞ7J[¶1BbrSÅ8‡©t!ù¸ÿ;Àßsz +#u¸âÇHNñ£®K©¥.Ý}Š;#Ói Rxáâ7Wx¢¸R("—ª^¼5ÃÐþ,°°7e$€ziëùòNùn5ÍöÄÃM"^íèÊøìô“,‚.3ˈÏÎúŸíäz#¯CeïZƤGðÈj¥µì"+ç@¡?Ži¨—MÂJZícùc\QÆÎåJ‡™Ñ÷ 4T²&\T ÜÓÀúÜ&ã“}Eå„[Qþ£fø|Aï§Io\fPÂ/mGïÇ^±~›ä䢂@}`õ6â"‘ƒO5ÖxžÉ­ÀÃJÍ tì˜WopûPaøí†.jbd‹×*Ðç@ëjÀfµÆçL°‹žD`ӻș_çÍ«þ)|е—™^Ö©´= :\tCrÚùN¾×ØòG¨é·Ç%Õüü¥|¤N¡ÕáNš>lªOáï›j¦6¡Kë±Ù_/¼¼™˜;ª='u6º‚töú¢ÿo Ñ„j=y_L˜‡f7•²e%žŠY&Æž;$§:ViÀCm=K ç_À$*Hæûjƒ WHÓ%‡ê°W.§½ÅjôÓ#W ã;‘Ì—©TÛ£²Õ±ò†vŒRKó6dø˜ÝwÍȵ?6u^k Ó¾ÝÞ?:ù@ŒLÄ}»z¶Kv¥Õœ0ÑjÄbf†èÏày‡0EòuUau•/å»Y·AS*]J­²°+gã–öËêë^ Œã;¢Øž™K6ÜÏþL·Ûî¶Ä¾æØHPszÎRxRÄu‚¡•œõÄèä±QMLŸBqF·錜‹xŒÊÂ+»$û M”‹,"[ÌiŒ*'ŸÁXÉH¢²‹oÙ,½Aç9핇„¸Ø$™fÿ~ÄÆêµØ<+G‘ö,Û˜2%ç=#µO2Í‘ÑáÓâƒjº ¦P[þÝm„ÏÊh¼7Ñ{pè÷ZÛÓû9eäßà—«*ÆþàuœÐL5ážæ5 â‡'˜Îƒš§Wó¡À[Ñü´ÚK5 ¨ž‹ÄíÍÈ• _ý~¢TŸ1á"R˜3à>BÜjy™ü’“yöSDð®ø6áP¤þÀÌT…ì )›?aÃA‡€ÄÀ»V¹vÀùï°>} óè€9EìBÙV .@æ~„ëœXƒÍ¥ÇOBƒ-Âe~˜d:ò‡Ð|ÓÍq~Õ°L÷¯+q-O¹Õ‘9ÃnÕ“¼óìò,zzûm]kF‘®*¼8ø¹±ÿ%•ÛΈS™jfðÊ,ÿA9C)¤7#&xÌ9¹Õöm¤ã£/EÐ+'º¥ á8Ëß}=ŠÈÕg°f›°Dq‰ÙâòžªÃ> LŽ¥”´ÚqAyôµþØZ`²m¨š~ΠѥÕße¹=9ƒ2Έ1÷¨Ÿ#÷1½¼bËu@Ì_ä3\­Û.(IXüóx2ý’ƈÝH¥9ú›¯±ïäñ`Ì ¬;B/¦ Î[,éL…–ÀÅ!€]¼ âj”é&©ÊfJ{ôûjIˆãzí=Á‡Í‚¥4SÙXãÐŽuC\ÍÞ/#×AÊÖïçs!'1 Kê›ÀˆJÁé|¤á“‰sÉR„ø»°´*Þ$´Iwpra߃@°ðzšK“?0‚Š0rÊ,?UÅî$!¥^ã“ù WIÀùîð>{äÏ €8‰ŽÅ‘¦ˆ&ˈ’ˆ¢^&ßT# åØFi’Û0À W¨Æ{¶˜”·m·Æ&Í1R[Ú¿Å>ÛìÆ ÔQíÚŒ¹"ú¯÷>~™O˜ÿ'%¯×¥êa ‹ yVA§MñŠ%µbDBß芪ã›u “o9€È~=9b –àÖ"qj<Üš ÇÇïÀ­ÜäŒ+WÛFT©Ï<·û|­GúùÈr„IC1–.ÔÕé ›k~µÖ¹e8lž%QÏ ³<¦à8äLpøeŽïð"ëf&i¶ƒžaÃŒaÚ¢Qó®ˆÿ ûÊŠf‘*%(V…Á@Å!Ë+i:ºI¯5˜;aO^ỽ$°>`‘ttçÎ þmþÎhiZ³`-ÕéçÌ(ÂýéW´Œ´BÖ·8A¨Ó<× kQ”@ë4«m±ñÂÑf…~{¬U—…r t¾žú&Ll(Zfv©<¦¹@´J¸®UFÛè,1Æì¨Çàù?:ƒ¸qý܂ͩ8}7}`á]ãuâÐòê㨹þCêoQª÷ÐÝ>'Àbñ>Ù/±“Õ&1¯›¨DÜòÅÃÝègX†TÅ\›lÚçÞÎÒÞ.Õ]'–YC™÷¾o!ëPàvkÃA}knÖê”é éôŸŸ ÜÞ&¦îE>pMe}ƒH ®?¤•L~Àí« *R´ »hq_P^<Êœ í,sübÞ–¬+…Ö*T5Öå î'1ÝéêJ’|VtƒhsÉ)²È «ÌÔc6ª‚ön tGè“í^ÜÒ  ˆ‚jºMç_ÔlWiï¾-îR5 2‘TѼ©±Ã 1¶…ÖádóÖ-×£Ò÷ësÓ&“µ®kœ''>yŒ-ÇÂ?Á»:o>F>¤ £ ´U9l³À—Kçû›ÐÜP¿«p“ô\ Ý·pe®^"®ŠÑ†Å…¯¶Rüùa`ÏϰyùöŸ]@ÀêÑ|:߃ •«Ù±#òxŽ&'éîýÀ’*QbõmcgO²–ŒËŸb¤ÈÙœ¸áb7ÈP9‹û–먩·”?T¢À°—»É”[ Ttæ™Òÿ-ÈÞUçÈ/÷”¯Z¾CEÎìÅkzW¿,Œ$ãzHG {¹1ËFÒÎUêõ˜È“ª›øltÃ@‚oOÊ„³šz:Р\†qÆH :‡tu8øwœÇñìçO`u5 ª¾)i5Gp-f¾ÚØÌÖcôjsF,¤ê½ýºÉ^ÒµñH#Gz#@K¼${&Ë“¹x˜ # V—~ø©œ}¾—CJuVz’zË€Î!ÂŒ–Œ“Èwœ œ6£.ñ$( Eq,Ãp9Ç«•2qfpŒ/fÀj”•-õ8KAJO¼Õìte„ o¦íi±ƒmª¿¯ÜÀ$2xF @Cu¨×ÌhÓÁ˽ÉïûKÉ?ÜÛƒN{ç¶_…»ÈöZ;ŸâîÕúk“=&kB¦Ñ̵¨{¤(gÝ&~Õž,ÏY]¨ìY› JÐB"h²‰…Ú§ô•¿^dìaû}ðƽwúëK’Ì­0ùhæö)ÙóÃz1œê•ÉÑ¿m=.*%€ÀÂZ°*¢±‰„49#˜Ú l…¼ôLIj‹;#/´M?²åSg[Í'óÓÏà4í7ÏfÌÇÒ[:à½0w:h=6Ô¥ÝÁ&°¯ÄåTÆ­$Dº¸p€°‹0úL*Þ0-#ùÈvæ…jÍXË0ø F¤†Ï\ÀØd eF4sO( ¿º^x œGFaÊ£š5È¥ŸNÞ袂²€¹4ãþ~ý°X¥Òí·¸ØšNèâšP NÀäüÓ~AÜQ듺àš&¡ 5ë«7qdMÚD†-3 í¬=?ñ¦qDÌŸËœØxÌ^º$¤V{Ê5X2Eb„7c”xIõÂA™R|…óÇ2²ö2¨†eYòòî,­.TÓT¨¬IÎØhvW¼àŒíT;¡´Ôµ³tÕ~ÞÚDdÝÛˆÂYU{œÆ>S`&Ô–Œ]ðéGÚÈŽêb°fúØbñlö-AmkßÛîëûyi$”Ù;5›¶¬°áw•{N­Dó LÕŽÇE`.eœ6ŠÁabÇq[*,;Í>ë Tá#,t¨¥¢/íN>ìrl«Yç‚°§ëœ0=\ò$lŠ•è´2þ“½×Ž^âušl Þýõ%BRZÚȰºBuW9Š“;¯Jˆ.ÙótS×Âá‹}7µÞ¬VœÞkXàÕ) ‹óXcÆÁ½%%ÇÓyÏ?;Z®èùã#ì~"/ÁN>`‘)CÎÙÿœoåàðÓc=;K’»+u=øHdÂî@5ù‰X¥Ncm9búeϬòUÔ ðñu盟Qÿ.fEXŒåExk~Ô Õ‘É“]M88gWNu$± Ì{ÃŽlHø×ƒ|îN›çOÙE€€+-ìT§Û…rléùûñ¨Eq."’v¾K¦èº—ZÔµHB&÷).Ðcêù:¦lHÊúWÿr`¤b`pÀ1ÛÙÊÔöF»Œ# Ve¾9ݤ#ÇÈ>tè’wÜå_MâäÐ'¥ý Î!ºŸÀeõœž£rÅH*¦Ì«xb|m ‹mºêÍþWþ†Qä`°aHÏsE ­û¤ Bžh'߯Ë>\íNÌFŽ"‘*niÎÖeò]^^#+bòÄ3F Š2vÂ\¡½K6žÌÜú÷ŒÁõmäVÙ@ú¶Œ½ #(]ÿ6—ºX­°AÁ’°EZîçG£ofÈc×ÞǾi çN– "r]foÑ"9ö{ä´Ä­wUpûÿO%Ü~y “üG¨ä¥aQã?˜ò$¸OÅKÎ`CêØ`•+½ ?‡=Oè¨ä:9(Áßù˜ÿT¾ßv´ºF;S•ÙæÚ™²aMjbæMƒ÷³QWî³Õc,ò¼¸ÖMKôtc:úœé‘TŠã´ùËÛÉ÷;MeÄ” ußZÒÑ ñëfñø\g©®™wºd3§8c¨Åô.™átDgnÚæZ)À˳#ÍöÀ¸mkÐý!=hž'ŸÕŽ÷Ë«kI˜QCÈÍ ÑÜs»ƒC‚Л Vƒ^¨Ì2 ©Y §\‡§ï¼^Bx)Ϊdës¼håî-Œ}øQÜù |Æ–Ù/hÐânšg›ç†›S±{x²èÙE[Ð$UûÜÅ“(šúõnÊöìÉÁdJ§›V+Ìܺè“"\œ\f&Ûíås œ~‰@3ë?ùì1¨ å„Œ`<ךeNQ<+º‰kè¬_™å·2å#S¯-Ì*ÊÆ”áÒ…WÕèèÊì¹»ë%Àªo½ç'±ŸávhVµXñü¥~i…ñœ]ùÛƒÎËëu^tÉu~±žÞù­Ozw,’Õ4þâ òÕÅÛ§¢‚ŸÅáÃáWŽ ÐiåçrµSÛ¸çÎ c$”j—ãÆÝ“®1#®õ>lôÃMèFškºÀÈÜ}ŸÁ2ëW+ s݉;–&&íW×uñ­ón"F.?Ü12yêŒfÛ÷H -íÞ™l ³ˆ=;Ár£»XãiÉÂþ4e¤× u•­/­ã¹(q¯f¸ =ܙݶ2Â`‡PèN«¨4-îP*ãµ<ág܈gÍ×b"g# M4`ø°$u†›]qñ]눽½ºœ@^ö/Ôrâo¹L¶9G[jã¦éñ9îµcÙ¹„ׯ¹IÊ)â±SÖ?愤޶Ï_¤£ ¯dNñü[²ògÁ‡é-[ı]S#_ôxý€[¥d4â'a‚F±­¹yPŸº>,HiL3Ê$&{gQøö#ÿ=Ö½  ›¢{µÆèÉì¡ÈÔ…¤Qû ´·çm,‰XûÏ7´*FÛåóîPp@ ýâ–;‘+5~wbþLi²q³ ‡¨TmXFÊÆçq¿ÅàÊZD”=Š û=¨ÎœóVÝ+±»V¦Vï IWJŽMúËŒ·=Æ31q…û-ðÊàN£  A#CÉç´Ê 1õ„43ï„(pˆ2 §Š|‘=Vε×êõ8:åÌoR…•¿Uv©2Y@»ž6Q|Ù}7@í½k²Ú»u h3îæÆv­©ùN€Ã{žßv­®³¸iL5„ÍÛuÉÏÅ/)\χ}@/};¶ (¥¡wPS-ÔE?­z¿iO•ûÇïJ>ú@±ºóôØN¡©Wô¬æ‹| ?ÈÎ|Ê,Þ…ePú)—²¿¹l¸¯Ý$äÈèšÇ¾Ü¢­§K[ÿ]¯üaå³!«uãÑxü>`!h˜ÌŸ.üÏ’é›ÆOgAxáȪыxÂb—u2³å†m*²8ÇãÀ~eí;/w~½fè¡Yû»F‰â’Ñ#¦5é˜Ùc~ÿ=\b ŸRc™%ÆÅY‚äÎF~ÒÐ\“ä]qì|d"ä¨<úk¿ `T‰ÕéIÁrìŠåÊ|¯DÞ€€‘<¾ÏÙâìs[Þ[ã"‹Þ¨vJ©´…Ã…¡Š'¬×›"ŽKaA([³ñ¯N•§F¯‘HKéñ ³æÂ]™»_ö'Vt7¥N‚¤|Éô/„TI„•ð±„+4)¹‚z“lªßŽ“ûÀ"°Ç{EFÈÈ~YžiàÑS½.ãªÐa"ŽxpÁ©SÛè¤Pm"†ÓWjíí¯ßŸ,÷€PeK´èÌ3ÃɾÚJfèÝV ç?-âšày…lví+<ÂäXî»oßÚX BgD&ßý·ÄáœaÇ` ®‚´‰¾>šÒ2õ>Hí³*ålQÿFþ~9ÌUœPÂÓ¯@üÜN 堝ׯ)HÔ»ü 2ªb¯íì€çRšF³UãöC!8q´JÜ7¾Ýîæÿ'y5™p´¬ÿ|é+‹1 æx?»˜ëË8Uòíí *¬»èü€@Tg§/U[Ú›elsi¦3ޢ蚠Jï×ÚoÔÉÜ0nÁMW†*?(V*Pö–;»ß.´Ì»¤&5öè!ãx*‰§ø°ñ„Ê~=.ñ.@0wl<øMú¼NM¤fĽÄ;©(ÌqŽøí l°ÆK¯-}ß¼ÌΗðïÅä*7irw~´¯†¿4Ь³]ƒ¸Á4q ÎÀàÇ“ÉæÀÍ,KA@Bœ–nFªˆnàÞr–2¬#F€ž‰“/F(%+p3_üôÔjˆBœRÏæÞáÍŽ­‡¯–™¶Ýt x£º-ã•Çþ Ñk’™Šz–·ÄYòƒÈÍeÐÙ«»¶˜RßM™=,Ú§a‘zXy6’ 2dàå*9s)¬9èÿD¶›«÷¹KÕ€YÈ;‚7MÛ,ž<¼qaI²¨Öúašýúlævɵf·¯î‚ï†-õ¸¨+’Ш€Ýš…bç¼±;“4ÕG9‰?“NjP®|üÕ<‹/xtÌ}'ÂÑ!j7¾=!û?pñr¬à.¾N¤F.¹=‚¡X @¤äÞΈqZJíÈ÷•)Mâ£|i¨!ÂÎë&.ÉöÇ3-1Ú½œõ‚؈Ó7³ð™_Ã{%n7ÈË$¥/ýNí'ˆX9kœˆ´*3‰Äü²Qž|R­¡Hmž½Ï*1AÅaF¿IQ[jŵ̹&ñÚ ŸÏÄÿ ñïíOF$­»ÄkmÛß¶ÁA)?ÿC¼´¾:2þ˜§ ^íÿ`¤³†Qð~+Fqó?CiaŒ³ØŠÐø%ª7óÌ3¦„®A;Ô‡8„³µÙ2Ò’ƒq’Hë…³ª”»—EK Ó:92du§DÉÿ=Ñ {òkæØkÇáÏÏC¡ø]€#ŸêGŒ¢Ò´ø‡–Ó??¬Ž½:¿<ªuõ¾À5+16nOgif°×)~0ô/«œY`DÆ<˜SõÜÊ5ÊÕÂM>ƒ+bÄ•ÖÒÀbS¿þ&©õƒžmÕˆÈRkÛ}cfc®ØÀ‹”[²¤Ö¯³p ­WlÇöì°!ðJ.U³õº]þþtàÊä!¡êF{‹f+›ÄqÆx®­eWG‡4RäZu#í–¥)p¡][ÃÃÔ¶œâÕQÙ¸Q§ãÃÆóƒî™ý¦£aåwEbdxžHÀ¸=¡)TU‰>wïºüì‰ë;W†q›b 0Õ(³á$â=` Õ %Ê×Í"›HߌvéNÎqŽÄš`å•0´™sÔŸçK˽¹u=ó¢µ~³©ü;Uv;UË­Sà +£è[žˆÏ_÷äjìú›ãzäCa»hPÐ+O¡t×Rµ©huŸß n°‰×NivNkhp²<,%C†û½ÆH‘xÚñI£/ÍþQû÷¸åíIºB&ÛÌV8ɱg€„%¬ÉXHìDpÑ”æÓ­#ÙjgÕmÑ:Q[&ðò^…Š.ëy{·æHše¬€ÐꕊZ’‘œ [¶ßæ‚jº×AØIq5‹H·£ )£-g£U²;e ¥o£Üm¨x,«é…aþÏ4]Õù<;XËž=“[¬ÝpÊòÀ#ØñÄÜ÷XÂ&̰ªe•Xi'2&Dv!‘òÌÖ4™(Ç@ø«PO×Q§ !M_è[÷?ž#éçÛž¢yÑãF&9dó£Ü·¾ÞZCÂËӳĸVÍÔêO× j‰¥t¬²–Pæè®+.wñorùÆ¿¨OÐuÅNN‰5þ‹3‡PµjTÊOµˆ›¢xC+Wú»Öv¬R-ª‡?¶"uweoñjòEPÍÛˆ¥ ®$=þÒ.˜FþSr#*† âNdQGøÏµïjê;ÇáôQÏÏèÏß,Ÿ~ª•)ú¶ 6Ù8ŠÚî­ —õM`Ç 1÷¿ÏN mKs`Fõ:yôÁ¸x‰0Ó}¬¹ËÍÀëˆÛÄÉ”·‹T!$ þ!ŒØýßxà;¯ þ)¯L•õx2á¹oRº½Æ®}(Š¢aÊûÏ¿ö€€ {e-´ü¢ÅÃòÁû`i|¾'Ui¸/pó¥¥ð%2˜ïœ:¥=T¬X9ÂÅ;wÙ }ÈäâC’f/Ð_ì³òBÓ}æ‚ùYVâ§a—œÀ`/|xó­þ«Ü¦‰'Â(íaÚƒcs3­­3ÿKƒ(\hñúgLç ËïçîBZ|!¦N‘ÿI)xŠC ‚¥Ü€!×~¦AéûÊ|9¥ýψµE£š¸‰À×üÑ{}:U&Œýâ­áëÞã ±{ª$A¬MÍ‚tÅIølu¶Ì«ØÎtA³ û8ŸNóéœÒCÑ•ÉóD—lLâ"«w=ðD+§IÃWä¶à—³5Š["A»š5—é§ ™6©¾ù¹5R8©3pFÕ°î番`»…t†•ÿOÆ‘Tp°ì`@- øïÓxc"¿´˜dÓ¼›É¾Gžû'åÜLhÍ#ÊkŒwꊎ™yPCõYØk‚2ºÆ&kÖf$ó”~ÓN…S_ V»¤¾F`džaô:'n™½èžo“y÷¶@0<7à1e0©Ð»Hc¨7Ô[0P¬#¤Î´‘ÿ ‚="øá–(°re©;Iòjøjó>Áµ:öC“Ô7–¸LÕºû­É HëTmJT“"2M7Ÿ¦ÿ>6öÊDÜûq÷Q´¼í1NÞ«ÊN´ôï9˸ZFŽ‹.n™)£÷@rå5»%ÒêrI¹ÿ!¾•COÔ³}÷ØîØùþ‡1¬³×üÿÑ{PðFTM/öÀ%ØX= ‹áRAR ×§'bUr3XÅ\À3®¥p1ý’°4ÖÐV9\8Ïà_¢‚‰º5"h*€8(ÝÀñžîÕÔò$»ÿ^Ù2¨-@y~eqX3³k~xÀ–¸Òžá'fÍÿ%ä¬[«ePRC'–虚mÜJzX_9ZT³=«q¢¼cº0‰ ð¦P¢hþ•ý¡CÒðyê= 1¦„S1b`¤7étM®1`CiDÿ,Æznñ7Ä Œg½d.­ÁLžt’±¶j˜äE†ðÈŵÒ÷ A©°Ú1\#ð1âè9ÚpŽf'*®Â7Bg/8 ðvŸôàÃXÒh%qÔl{¶D ?Zšƒ3Šë²‘RQíÏñKq€Žܶb3eÉfæÎ“ÝĶ8°Tª²…jŽ˜˜ãÚÞé|6P|°fˆyŸVtîÁÑøÊu·ˆ4£FäV¬wòÚ×I°›´ë«=ùaOz>`BÚZû®V”ªíÐû¦’j‚(àÿw˜ÛM­›Y‰ÚG=¶“_à^Ý2fŽ_uµ™ÔcÌ‚œc0˜ûoÜ‘#çÿ ʧÂd8–‹œ"]AŒWÊÆæ!ùÒåY]âÛvÍ:ÜOÏÜFöy²›¦ 96ð-I2^ü"ÒÐl‹Ôå\;᪂–‚V’§W@••g =nzq:Ä]ÄäšÀºƒ:"˜¶bH3Èâ1]BঊÅî)ò óåû?ôô‡’@6äY¯Û°}åD¨ÐðîJäØ.OòV ûnu§>tp‹?‰Ô†Iöâ¢çÈh‡gD¨Sª ç/'Æ¿Ž™Ž7–oÃ^¾Qߢ%’ ${3Û]Œ¸ß´ï1‡ F£Q¼Š~Á¹2‘°ù/a8´e )çž½„t@‚ô§FÍå%“Ô–4ƒµ,YJ|«]ôÆÍ;ú©ØÿJai Ew¼FOÝZ‚±¹KU=ÃÁg†¯ƒ~±YgSêqZ/`«ßÅøïCëÀŒ{ÓVM®êµ›}CÞØ/³i[™Ò X'Jù*îu^’/Zê+J*‡®`AB|Ö±ÐòuÇÁh@­MÅ?ËfÂqø^¼=ÿ"è3¤!<¿“ÖyÑRa“ee«™ß¨6yȾyt@Q­ôqëy=*ÈœëÂ!ÈRÉ– >âlý4q«8ÈP44Ñ‹Ký+è(`šŠ‹_Œ”: ƒ}éWçIæhR9Ò¶ãSZíqlÀYé±ev8˜£öaŠy:‡2ÿ<óQ<ºÒdôÁÁ5oA¾{ÔÚ[þ`3Ûr†Ry# Â$L¼÷ñFæÓ±[AË»åÂÚ·ÅGï½,üH¸m(äCrO®`ÂBD±Ö;±Ê]_ˆ”ø&#i½zìlÕI©·¾ÜÁT=TüûlKhÁ±^R|Kåí]Ï}8; wqW§ª’r‘œ•;‹@Wö1œn޳»j}Ïæ­±4·XÅý2‹‰BÐaêŠh«Ü¾ÊÜ«?7™Z{ ÆOö7Í»LHeäÏâËŽcóL“Q¡šžLOŸõ Š©§EH%X’¸ ¼øúÍ¢‹µÏòG¶Óã†òIªðkšíx.`ÄdŒ'ßÑÀ‘Z3¥Ì‚·ÀE6+:Ý» 1ø‡…í½ú€êv:ÊYµt³ãÊÎß#sÛψë9%ó9õûNŽÈe æõ‹×.êÝ‘ôz‘~ˆ û¼tŸ@k ³Á‡™™ ¹O =œjàH˜­B÷ÿOñw+2y*+"=€FP¡ ‡Áü¡.¡Öª{Äôôl´Ð¾¦‘]Ô:ãàFôÎI´Õ¤ßYùO-J&‘‹$Å]¯Ì{D Ã‘äÂh$a ~ãq|0?¾¯·™óÔ©×·´nÖuÎTÜÂ!xüœ”š¢ºg/çÝYÂÑ#ØÙoLwýÀèU8\ãQ¾ONœÂ›§lË¢*ÓÖ°TR¦cnyÙ¶†Ã¼ÆÔÊÙeV¨ùêdi:7Fœ.èÐr ^ÆÆ…b¯8Ç—'Т[„±c?ÅB½V®MTµrZ F½•Pj¨zM¢èøOÜHÉ;buq¼ÐùEþˆ!ß™ƒPF%„s~ÕEò¦Úx!Éçf(~r‡~G Ô=ølz l4z-~õzŸ.ŸÈÞùNVÅu‡I7-KT¼»t,]ðŽcSêÎÓ¸}ïÙC¢ÉClë¶ ýàž‡"b‡‡„äçLGIPí;I ðñûeœè±‡É^ %ÇÚþGQŒåÚ‹½‚\œçÕ­íK<$ÂÐÉ< Bc±­:enÃs)U:¹vYúFp­ŸIÑ4i@Sd¥C¬çdºôÌÔåÝúÂ!ŒDB*¨n¤„?$N‰gųœpÅx ”°8w æx¹ û}êaY8v}JÝÒ®yl–ÊK9X84ù¨9Ø·} ·÷ÂþxBé4œ$xì×ô4=6õ”êλÄ5É×BºÚOØÝg`Oô¿­¹Ql…QÝ) ¢fp‘mØÑÙv#:7¾E3Ó³#à{OÚΑ¤^gú™{×<ª~Ýp2úÞBög”Ê™y8$ù‹¸‹ýKŒúJžS«ÿ,vø[ÀPÁ:Ág¾¸Žnoï*ìmÙ| Ë|\³ºHjhð5vöª—·ŸB])û±äD<Ú¯‚†%ºÔù“@à&@S}{‰Ò²Ã‰Ø¿½òÒ»©26Zµˆ0þ0bŠ?ëÝåÅD"̼ }8<ÖÔÂ.h7¿åk±›Æâ7#«»o{wm©øHÈ{EØÐ?¯- ¼ â²)š éfÖZ…¥Y/¹Õlpêφéæö1—[ž`¹éɋЉ‡éWƒÞz´Xʨ´Â'=8’i¢™UýÃÑa<ãÙF¦m½ëˆÓ{®ÙÁ­ìg=™ÛNÚÎÙ›óïk¥ sFy†ï;“– ²·òZTŠEѵuLx%íàó Ê4¨CÖbª"îDÖFMÒ¿¢5{WÊTÝÖn/qéú¥TGÓrÊæo~ú MqA&T‹"d.Æ ñ‘wi§}üªŸŠæŽË¡e€òÆðø“.wë«ïQœ0¨ÓÖ¬m±­Iz]=€êÅ-à£çyí>pÑT(ÂxQ5â—†mP ðwùȰ†¶mvOd<†ùÎâJS!(iw3|ž oQ@º¦aœz¶L›vAËŠãõ»,µŽæä]KÃ>„[^SìMìR¦n+óÒ=¦Ûô@¤K–Rï4]úˆ¯$ÄM§QÕÑ & K}L?·Vô‰Æ!‚ ºctV$gÈV` …ý÷BgÚcƒ„e^­Dà­‹ÆîÚ$Y‘þ=” _j= ? ÇéÚèr±v3E%MðÀ vžŠÏiÜlb¼¥%ÏÄûå;†y(Œže4zS›Ï5EÒÈl¬~J=»owœfwqÛ¹M¹·ç¹máEdu>°Ïó§È)­3¡=ÞCX†h«]ÇŒ•Õ/©‘+ÉŸª RÔI…ƒê¹É"³ ÜÁÏ„Z§ì)kXÇ“¯åIEÐï9 Íè¦-ÖæÖEÁVh«¾*qªÇŽDØ{ ²22á‘}À ·m3(dØÉÙÞQa³Š’¤ë¤Zªa7›˜>D-rG¹¶÷¿fü:û”tã1x…Ø„ˆ§Î—HÐA­e~†}aKq†³/×¼Ñ÷h€/Ö44gå0º‘îé­÷dÆ·t™µµjÁ'5fîbO=LJ·üèP?¯cuÎ]¢ÔÓöµ+Þ^CNXM­\ç9e¡SÀ ¹uåÄ‚ÉÀ¨ÕàóÎB{«½P5ì»^URA±M o8¤´ñFrú®º±M™¶«2-¾öýsy€·ô+…Ô[Í®zÊZMcE¦w’#Rúù@ÿmß^‡¦º3kSTsðŸ,šá†\ïŒB ×I/…0]Ã3j––ŠY€2Õ¢AFÚ!¨XpÈ„6`{^¸9ÈÏÍe= ì1Oê8Á?ÓÖ«ks< cW‰N^J•<ª=IÓ–yØ Òæ\=h0Ce¸i+jmNötân ³*ßÎìæ-j…NLt]82 9ÍAÛ2ç5ëw·_L³r “?çy#KñùelVu„Z8¼”'Lÿzaõ"ô³§dSV¨‘˜ó\“ ®‚½læ%·šp§)ÖÀ÷‡ÜX‡}uƾ•¿s’z¶Í‰|dW„Lü ö„ð„/S_‰û)|ì¿ÓÏû÷º£¼Âåp§ Å q>¥iT#5ÖBFhÆä¢îÏÒÇ?{.6q}²ƒzOáêx×!ÕÄÒ½ì|PÆô»jÝÕÞɈï})½²Å«ÂÔTÁ䬙>h¼{›· åüñu;•ié±Bæ½9w m·CöSsd|¨ f÷z%ϱã,ŸeFrƒ‡ÙlKRž•Ó§Œ0ÜS׸qéˆÇ)ݨpf6¼Âм%N~× •{˜:HZ Þʘ[󿲡p‚9s^cñ{Óé "€ZRQwò€Ü•&Ášz(«=’0zÒ!pB,¬†óŒ§Õž•õ°à!4ûZ'߉(cÝ#Ú6µ_Ñ6‚‘2¸¤ÝÅ“CÏŠ“IÌ”f‚¿Æ®¦‚ŠŒÁu:”8]&V·Q'n ­L‰h þõ¨ß–A Aí@]³Õ1?˜ØŽUñˆâpæÌáqܸöá¯]*äÖÌih@˜4ñ={Å3­¯ÿ%).œù0ã²áhìã ñ>,œº‡ŒÑÇ­1¼°¶Sx¯:eW8]dãsž7†±è;ž{?ìfŠp«ÍS65¶¸t0>«„Ï©tif–>rí³› LðPÉ*èà_’‘˜úó¼98±7Ä-®ÙÞÁð[ô á­²ñÌÔE èþE½4½ªÞ@M,j·Pá3̱Y¾ ‚μÅe©S ’GýžTãsTAòâÆÓÊ]æb7+&°ÿ ‚:/åå 5æ½ß³ãR8m”+Š-ÝÎUíz «(z¿±Zÿ(yAßÐßõ©|óDÏ"|Å+ô\¿©î‚=q«µ9\ë”M¡ëçjÜB{8Å‘ì$+H$Ë­ UI‰Ÿ¿òNM–_qLÂï'NÚÃERl™ÈªÛ6ndŠ©.Ås‚ÆZ“Wšð¢\jø™›Ú31‹¯B‰»`†ÞM2Ðò«Gà y¬áSŽÄÿH >ÌxbžàÅýý¨…LLí[‚žÝ0(dÓ0òjÖî:ièÕDu‰ŠØYÚ9‰¡¾F²ð"4OCÍwf~F¥øšC'€-ÃèG§¨bsĨ{OÏvDX%:"X¹S)†›ª 5'öâ¹é¹Àgd´Œ•Âs”zcwÖ¬>DðœŒÖ ïÝN5Õ¨IBš„Í;ùÕtt?y•ºó±…ZÍ”’©…˜«>~ý×*H(úWªÔ-gôšDT¼ßþ¬ïnKž-œ`^¯|z+ð%45J«–z˜5G,0TP¶e0_.rýßýÍP¢èˆ+1G_¿{·/­dË#÷z‰¬Çcî{c,˜·sÎgÓÚàÍ9˜^Dñ£m6(è;%Áf†rzÍøh(ÎÞ2b?]å@ù]|;õ\PÖ”0.&ÙÆÚâ±+޵Þ%Wt… Gäå#Ôäcy„vÈóš±_µéÎÈ‘´ÔM¹AtîbÒÑ~ÝòБùÒ­³pYXaå¿ø´Åô˃‘r„§fý·u ^#>äPÖRÞúI›>å.¯ô¼¹¨ù6üí´<ÌS— :šÝ Í–¾¡xÊ©ª¬r}buÁ^ŠÁ»ò;é»f5­†#”ÑøBsi#¤Ü sàåéŽLCûk…]±Ô…ˆÎC|k„+kUùsN¬7 u¤^‡I¶v´ÊÇó:Ö'§MEçü¢¬–N–\æà6WØü4ö°Ûf>þ”¤Š*•kˆWê ÙU.©íâëšÕ¶^@ŒöA­¯#)ÿ,X7²ŸAæÑaRVÀv–a‹dì$M Ôëq×í^ŠÕáñÚììÛg@îâfrGªðâ¶FÀ÷É–¬ ¬Âê7fÔ0Öt|ÎøRü¼ÅlÆò`ÌŸ ¨•ýXÛØzJ¨²¡!ðÕd\`jJÌ- †U©Ê9Ìbôcد[z™úÑ-h§Þ»þ)m†FsÒ:HЦ¦eÿ)çÌxC¸"ùé‘€ª9ÑöC ïÑ:WÈÄ1ÁOAÑHIòýÙF…ŸðËÛ~)ÃÎíý¼?T/#Ëž1h°i¸Íq0\¯ØBÕZ“bR¿q¶÷I¹$B»Êpz>ÐÙ!<úÞ}1.{ã³:CN£QeDl R¼Óì›Mfº)Tïp«ÛÕ¼×kd¿“½\ç<-ýÿ=ýfÆ5ùÔÔ±›‹q¯È3@\‘ªY²\Fƒ Ú¿§*EIŠÏm›š_^¸G[â+úÚabb+Ï®”¼@Ö]ïÖ|aúíqpTÓFÁõzPAõz:@ú½ÀH#W¬h;sÏ¿æTè1Èx`´î¶| Oò¾¡øË¼EV¹få<,æÐèk­ À hUì®U²$·Îu.<õð%%0ûÎ5.¬yÛ•kÝ„/›œ] ˜²& ̈Pvq$W•ù©ndÁ}ceAõ?šU§%ŸýöUX–&¨Œ&Zácš|Éi¤W¿®Ýz“÷ªJžZ5ì³ûÕÌB©ÝyH¹Ï_©ºë™ovœtøŸö•un˜!ëïˆÊè4Ò.ÿ)†’ÐÝŽá„®ç~¥GÄæZ÷× 6-£9êŠÇ¿XôîÅõiÎÀà5¼„ s­Ýà+Ú“äó[öFaÍÙòÊvdÒüldz’¶ùw !ÈЇBŒò*Qº¡d·§îf²¡ÙÀõ‘O߀çX¶Ú–ëó‰WÐ^úÎçÏ ¨ ]ÙqþÔ~ôW>ë&µAÏ/§á ®ÚÒZv]×ñà:N¼VK«“ЬØMN£5¡íõÍp€fö(Ã}ô :ë›Ô]ësP³Ë¶G±93ó«ìãó!êBôG´QÀªCÓžYr9¨@½Œ[Kz†€4ð0L¼ýO10ÃŽdÈgÕïÄÄ<èŒæÃ\QèkkßVÇ1ƒ¿íi‡¢!ùiä_д@ÓúŽÌ¼ÏêVÛÐä´b¹ÀWÉOÞŸ™rç1‡/Yé6Òò[ì\(ø€Á_uV$²{Y¢2]“ÑÛevèÔ…¨\ys¶?"õuv اÈj0ó$<±L !Í Êî!º@â{ˆé*…¿,¤Ü´‚ê„f¸³ëKû4žÏY(n_2ü±êÀ‡¼-ä‘«gô^¿ø¾Q›Œ¶Š†ÉO1©sç# G« â-râQW4|_p†t¾VE>ôØëY“@øP“x„rþ©ó› ±]†Ê§+¨q¦¿î{^` ò FÞvÇÖW ºšƒ¦ŒÇ¶Z|¨Î#çplZ Žä7óÂ5s‘qsñØuhÏœÚþžl‘ó‚Ò?<Û[Ú1Xrg ­4@¦¿‰äµId[È»…2=ÖÈP:_Ñ$»Ÿìù ŒÎTÖ,åú—ˆ>Í5†‘£ðü¾ïrîY®@ñH‡-ýˆ®óvÎO”Уfw/«˜êÛ( cŒ¾ï]øF¦¯–x€2ŠxBY·O1¡#zXsr¡Nôx°q5¿M‰ý$·Ñ]ý¬žËû`$Äø¢¸1h•ëãJÖCŽ9T4I¦þ=3œ¤½0¥ÕqXùÃ=¤¨_±^Ù¨Üëöx(à»%ÑZ4•ZÇ]5Ûš#&ü¹Ÿhw© bÏ ¨sRÿVß]$í{Ñd¤ãZóU”U©¶•¼Ü4`³•ìë/Ulä¹<5æ>˜Ûä ½—ü&ÑëvÄ’y<™ 'Æ‚µn^]Ìÿ@þF‹Ê;SŠ3’ÙUvx…;Ÿ°i#ž™‡Ow}VÐËfÄèµûAŒLYë¹;ÈÄÍW˜ÀÒu—u7S óX ®ïýÏØ`˜qfÕF2)¼³ðœØ•ÎÙ-#æ3„‚'w3 `F Ne)fƒé³·^½õÃÝ{8ƒ»ÑËñÂÿ!ý_S¿x&jõ³{BI® ÃÆ°nGuOM)–r/Žˆj§º2x¦ö³;j¼YnP?á•×aþÇmj3ü}©tßøÞ_/â¨úù†öó¶Š7¶3qZ9Gij$“ùuk=Ÿ.䇚5H’‡>ÙSßihn”Áxº—$$+ÏÓwïfmê° ¸¨?TeÝ ðƅْŵ6€ uu5HLÊFò¤( 6•e3G#8¹ÌÕÕD¥µÅ 6†žHÇ!¿%Ñ•»:#,Øí¼1vŠK”]Vüëßëó<t‹XÒZ7FT ëù²t¾”P@M Í A;ø žÚh›(Ö¨ïV°9œL*k,¨ €¶r§¨‚Só#âtIÿ}ŽiñÕdf£¼ùƒcÂM# M;ã¿íx }“þI‘ð~/GÈ“¼üúÂÛU:¢£õ“2G¹1œ’ž‡•K‹œ]sµ^,÷„½,¨ K"ÕÙ¿5USéÞsõ]?C!å©¢Hç†8 ÈöJÀj£(…·Ðû¼A)mö6(UŽÄÂ÷¾½-~)JœSq憓Ü[÷ éßiÜñäsIû½„¿Ò¼BS¸ÑšŠÖg„H±øoãààÐìÆ6~RPîÑÑ ~•bK“þ;ƒF6±>”"62±à˜‹VÙ Kv\EÆò9w4Iú)'‰^l‘쨫·0 –`‹+}âzÇé ·c­¸{伩\iãërî{F¡r䔚zú@öœ.¢ Ð*4$=n Ëb,±‰ \“uµ*±°€K3ñ[¼ÁA‹_l¯rEøÎT§PÎfXòÍÈlqÎuE÷tÏVórw„ }a3ÛÔd¶t;D˜z $€ýFÚ|ÛY¨¶¯Í0D’rO2î³Ê"8k¢”Ô1ÉÁez‹ÙBV¾pEù™ˆZ]WÅ&:ç„íSÈ–·–ê!ßäFMÀÒ­V/Gø–†’5“ùU'þ×)©,ëºB^ÍËO—EW¬ÓòerÆå‹¨~|-tÔ„™)y°ïîJ1R\&ɯ]¢1ýÇï ƒ5_+îÄwlÝ xd¥ü§N(Ài½ΪMaàsÆÍ7 ’h|è˜Ñ pîœUIjï–U(ŸGÙ âôB`} ¢¾qÝî[ï¯éÍYï®b1ÔC…hih)ÒR‰ãÆP§HÖö'…a‚Lƒ Œ2ð{‹kúaÒõ:À¿l®Üò˜PÌ&Oóãr"–Jpx¿}‚hd/"þ†¿p©ƒ9Rl£tL²îZÂTóì}&»¶I>,Ìe¸<›*T½þKØJbþÕÖn{ý3f±¥Ô“ëÓý‰:ǧ¹“½wƒUtÕ¤«§rNÈ>AÒŸ÷4—ùéV‹çÅ–¶Òm5âqm#mw™k;Ì 7Öz êt—¨ŽÏ%Ñe÷Q{ø ®B¸~¸ÃÞ¬êÞdéÛsù*ü†QýµqìæZQ³‘*…­X746ÕCþF®<7g&C4sô×X v$ìnòS[Ò‰û´rÐܬÊÆó`9ß&E‡eœ«ªÁšy Þù¥ÚH!ÎúÊç¬æÏÏïw.Õ—ÜBáœc†K gÞ˜Nžk€Ü9›Á¸'Áƒ© ~c(!Ñlør¬Ò‡8u’Ï9°Ý¢þçxYPY „Lçk±¢¨¶1/¤N&Å L´ aÂa "™Â€ù×d]Û$i©A•*šÇUl”ˆ.IÁ3D‡ÙÇׂÔõ›=CKo9÷c¢SW#½.5Átê³n•F’.bÍÇ„¢Èï1&èÜ©·Bœà# ðMâ´ux¤Ê‰=«K%ÃŒ1$µ(4we¯Ï§ÓÊ7v\v¾“ÏçêY=?Œ"¼â%j ÈKtù1ƒÄÅi©]ªåÞ!È'~H—s9¹2|÷Ÿ|Ij;Ò[ÌaÂ;$5Û5 ®Mh|õb¦À™×†JÀ#'â"rË ì}ËÁõzQÁõz3Aöú€HÆîlWûxýþ© $l9š²¯[Öµ1¿Ý0e8 ­}ç%2…º¶Hxî ïk1›Ä]ºÿ,ÿ|ŠJ<,°†?ãQ+5<3~MÓ»‰~Õ2šªHò¹O2ÐÓ©@j7ãhñÎç¤_%ƒ1! Ås¸bîÅ&€KK§ïmý_âí ?5'eC+¸P¦U(§Ôöô»‹ä\÷¢ˆ‰|íY)çYÞ= p]\!¯]Nòd‚¼ªÆP¦í33ƒ$Àeh…*üÅL àÂ-¦{—#¬âñ6¯Á¹t9©P–Á#À°!X]Ôò+É1QÕ‚f©àp®%¤3¼·KI1Öú¬å]AðQ;#‹ðY×kxhmÙÖlÿx+X:L•÷á ‡q‹M­¾­Ÿ›“v6€F3Þ~&ÇÈÂ<Õ ÂŽšdJp„A i­FîŠQf ®F*š€•K‚€ ʻڗ~ePOM4Å¢úŸÝ~œP%\ãJ-„ÉÏÈûN¦$”þBŸòªa‰îP†ÐtàåØH:+rßÏæ±ÙÞÄN÷¥1$”RÓñDú Ø6@ÓH›áÃÖ¡Ú}ýq˜h$“pyîøÑø;Z3Eî'îóC˜"÷äÎ9©ëÌ[ôðÌó£ŒújKñG½sHø$üyõõø¹£ÓutÓúæ«:Ð cíyè²´}Â¥vèH„§Cz‚l*ÅŠýX2ö@«Ñrvˆ45ó¢0.ÊÁÜtq§jÉÿSér¸orQ\é]K( ´²t±ÞŠJª×vù£WŠLâ·øŠzpKuP‰ÏwIº¬5 C÷~<|õH×ÔÒ˜ÓÌ«Í.“ëô*äF×Þöýå›4¼+ ñë0Wåûźޢ¯©¶²ó›ÓÒKëé"m†¢ñP±ÞyÔªC위ÁÏ ˜&1ÝðrÒ^É:ZÁ½ŽÖ»keÓ¢‰MIïøX•}‘¸àN0ÊÈÚæ/2‡— £Þ.½P0‡t™t]Q` Õ8…¡Ÿze7Ä0×=‡f£ jI¿ ÀÞ3+«i¾£‚å9€!;Fõf²Q/êã÷A¸xþ1Àפ,’Úìm;.ÛåSÅ:– 0EÓOë0F÷%55rR®QÐD•Z:7+8Ë<®‘f XWJ•=ØUï"é§Æ4€DM_݈‰3r:à‚Hã ™èh¥¢û[V© z™Ó}¶ˆ[7Æž»û7Í^Tɤ[[›8Úùfüq%'ï—íáEýYÚA±\žZJýb6í7P04#ÝÉIÃUK‘²Š›º6ÒÐí1\ºí^R\3sVŠVðÇXÜ"µˆ,2O(˜ßí]m˜ Ñ}ƒštç? âV9Ž8É?£VNÞ+¾Ã<Žª¯1‹î´ç!dï~\ s7ê¬`ÖWÕ§ê@í®¯ìPñBõœý}s,ױÀ§‘£èè=7ï4Aê€Þ±MÈj-UÈ€2t3ÆÏ$ú ¿ü5L„9Qúfq&"¯¤33R†ÓI˜d½.jÆ9·(¶÷©Åøñ!*Àý±Ò¹ƒ—€ÔÉbÇqiðÅV~A rÿÖß íåjà;`k!˜!k ,-wÎnëÞÞor¡HaÚcÀIáOí¾žZÿÜÇ5à\ù'íTÃÿh¥":f5Þiòáòâ¢re#‘³ë³Sá¦=Ö6!¥ë¥ª2ª­zjczˆé"Í(QbÕˆ96µh˜qOªç.`’ÖhÉN²->Ÿ€Ü”¥c9YEÈîôµòk¡1— 'îrçN‡Åw¤O…ãÃx²@v•=ýéKæ¿ æÕFvÑä¿%–ò-ýkÆí²ò ®¼ö5n•+KÑŽäö²f„ÈÊ€SU<Þݘ]ÔÃì²]>;­ô†ˆd½Tê™LÄ…üø B¿~az( ºÉr_ó^bý~µéš%nåi ªµàÔTP»p[JU7õÒ䜆»ê&×}ç$ԜȉŽƒsÆ L¶‡ºm-`=ù2¹*eMö±œí7™RFImÛàã‘¥Áz5sÅ>+ +{W¥CÁ¥Ekê}›µá$€¼d»aô‰C;Ã?7Br´)Ü܇êý 8Ï2ùr¶Ïg™ % õ =È “M”.O~NšÀáëºÜ÷Æ|Üxª¼µœEOÛ™ó’™ç,Ò1ÁJŠ ŸÆlÔ8ó Ëm ßKÝ€ }Óºq§fŽÄÁÔ©DW¶ÏÏCN*‹pS!`Ši³ÜÐß°'ö(8¼¨ðâz_ØPÍõT—Ë>š‚¶ °õ*)Œ<ößWƒeyùC©dËã§ÌL¨:óŒ!7GÀÊhowv ˜'îãoÏë^Djf^¿ÿF U#÷r¹Pj1D…Z®¸×ˆÆbAþi:X*Kú6½ãÏʽ9æËo²¸4vúëŠi×µ]®hêi:D†V¨.öÀo[—Ý.žy,ίŒ–¡ # }17þó¯4OÚ¨^œZcÏvøj–Qb}¥#u—K4¹+±û˜t³8rGr3ÁÐ<ÒQé×åyµ«<©¹§}©DÖôCje)dNR½ÀfòWçnŽ[QëèZ‘º* \;!øøFšÿD¾ LcdÈÚk9Ô”4p0P(µ>C CœÍ ©F9ÍQÊÊ »L]ñˆõ)@ó×+DrßÕ€¾¤´bmÇ@ciÔÅÏéO±&àe&º1hdÿ,ejFL¹KŸ®ªÌhÌ*šåCZY[ò-¦wÅK.aÚ°N¢¿¤YƒH󲇂×è›L¹H”í6×…\½Óâ Îöº Ú¹) D²³µ»§„ƒš-¤ÜAø™šuÖÌᲯmÛ“åœôylºeìd‰xFyû¸DŒ:-¸ §ï„‰çxÐôdlmJ^ÿ3uŠˆu*\GŒ[TïÝ¢ÿ í§ÀqpƒàÒu ì`n”sÇË3±Ç1¸ä®œ ÂæY:J6œO;öƒ¥uH2]«ïGû§ëw¹õ˜™ÏÀ|v8¼2Aoæe°!æÇáÐ<üú‡á¼ž (püo¢GO¡›4‚?óî"S4$cÇ:)‚AZKqJ¨ÿv æâÊ X*n”=´Nrîáma«5Ú:®]Ñ{Qç'î­Ñî@«¶ò7i6Axõ3¿gùÉË/_’ÁÄôž¡ ooq•,/p±µê“ˆ>ò$& 4"¤oø g{iÇ8mîm†ØðÑ=…º‘µX…]B8î.å&œ¢{§áºÐ†o»5œ›ß$WVK—Œ­G^«K¯ÿkæ—„œƒ‚Î_Ê9p†ÞT0ÂeB;‹#”ÜÒG7¬-A‰ûÙ–²çéhó¯á˜&±ŽµlæaZúi¨U± ¹ˆà ²üµ[,;£L~8'Â¥wÔúôŒ’ïÆÂ¯±„¦¿M()L†Žo­>Ü+dGMhô=(#ò\/éš³w+ÈRXjñÔSŠñ‡¦á'œë¾¸ ÊÉV(Ê-ÂälØÞòÔæ¶ V"ù¨~ZsÏÁO«7T¤ßª¥Ò JS¨E @  K ͯÅûšw`•ôÝ´±{ër»¬Né%à°•!f»œÑÝ mº6&à6RÃê5•þVÓ,6(˪o„žÚJ7˜i*; u:Ž¡®Bf#VÍÉÐÿetžúÚêMEs4™Í­Fgeô[ºÀR´oðZe}×ö¦dùªáiÖÁ„˜ˆM±Üé-RÀg—©è™7N„úègCÃßSC8 á!‚íIëÖµ­“ô/¿W"QŸ0¾o ªÿIM¥/çÑ©XãfD´0 ÓÊ4$·ö‡ ºÅ*àŠ¬MÍ©81š]9#ccQÑW ¡5½Æô):TÕ-<P9:Wvì1¶ñè–ÝZÈFb»à‘Æ}ªÙÑÜ]ìÑ©p z°G“ŠÑÿJOvèÇ4"!ÞÄÍÈ1Ì^´®ržço¯`Xûå–î÷çmÈ,®¥õŽålõFJ¯¾ZÐËXHâNØ@Ý +ÏMÒ<˜YÁCÈ^Ž`cP;Å­=`Ø /•œâ¥ê„ÅùÖÌ„Ô%±rêhжõ Ò†Gãøzšÿ¥Wðô¨þ±xþ›_ÃÒ«øz#ÿ®n?‡¡Çðô)þÏÿ¨¼V ÚŸQóÕùâ'ˆQc”(ývM ÅÎíÜâ×k7:í’•Ë‘Ñw"àÁ5ŸuNq%¶[-²\½ÖN9H·l-–¿ Oèþ?Öö8õò„˼8× §âfÇ•™QœåA³Våw{•4cÃÀt_ï¶Îlø¬ ˜njáF“­V€J -‚Õ9ÃÛÉÅ+໽|ŸØñé¹<„ȽMXaªñÓkÕËyCy†™S\Ú5Š^‡&‹­'R¥ #ž%u©ËÃ0&¨1û›õ¨T&~Ã^,Áí|ý©ÌÜgRÓøîzßñ!i™ Ô=ÇppßïÍ|§c+)eÜaÒÂnp ýT‚– ÐC… M]mÑñî@6s<6¯È¥–ÜŒÍáØÉTëäQ}<l?%‘}4ï è¿h3ŒÍ:Óú¯q“Mº#úziø!Ý]Ýb ÕÙVòɪ€ótñþ=IÞ-?K:êKðÓ×jEcÂ-s·*ÁÑCMœ¡ìq($€}€ô¡“\øªŒ0=/RZ: ×-·N*£Hp‰z½ŸZªˆ>’“2¨$㮜I‘QöIÕÃ3¬; .3Wú¼Õþ‡ë™à5W¢Œ|‡O Ú46®ØSµHß¾‘üúI»I?í‡c#Й §¥Ÿo5F6ÌÉùœi¼6±Ây¨Y`™¡Šï?²Ê%tÚÊzq@  Ëú=¨7Ìø‚È0–´^óº/àÅnÇX=¥2E—«&η2Rˆ%è Þ+‘Ø,Õ¯°#²ë ±xÐWØ5ˆ:©Óx4Š&¥ÀzSwÒ ±9–ŠdãÖ/z0:¤ÛŒáð†T,‡-à„]‰ÚfÖ¯E±›Áêxí4ªÐ¼›•êôzo_eÉfÄ®pÍЂÇþœ™Q, Ál <;çÕ¯µ70!xý‹ÏÌH-v춸’q¸ù®_h2.¸@’XèáXí”–¹¢Ð&9WÝòìÔîÅ{Êó¦LÑ•‰VD‡nüŒÕ©ÁËifH¸@ÞßAÏ—DØüôiœ¾ÕÓÐìœ dH]~òé¨0Ò7ßjáU NjØ $¸‰þå²uró‘OùÇ©=«±Ãg^/÷ǼÇ}R$v»T•¬6vð 9x6ù*ïOÖ—èÍÂó¼ó Mm×f÷ÿ…Õ‚¤“Þ+cÿ9Éóx^Ó¥qì’Hª‰éƒ^Ñl(…øO2Œ#Æ0¨3hl`d ‡Æ9?P÷[nÃ;ìãÍææv&ýÊ€mŠXž³à±({1@ŒÁ‰4\Xcj²Xþí¶âDŰIÀ úÚÊ[Jý'û«{ûd`¯Z¤ë±b9ù¢Ò83§0áv-…¨góvu.÷[ú…ÃHÖ&/ËÀbñ Ñ€¦eý—½D[<ŠZŽïâvð·ŽÁSs`šZR¯ ZLÆ>V?m¿xaÇT’ÏæÂ§ÈÑQ®ˆ§GêØ¿ejŒõžõ½ˆXµužøºàÏ÷úø®æ­Ì}‹uÿ%09¹ÊL"Œé}×€¯púje†ÊT®›â+KšM,ºq)äö™w‰ ¿7’“M¾æ€œzñ‘ÕHFר³jŒ¸9˜JAÙ&œò‰&®6+ÿkmÌÙ Ï˜Š«rO#8—¹ì*¤ uŽ^ŠÜy_±‰S®8;+Äßo÷6AªÒŒíò†çÊáPŸnÊ:Te£]É®9iÍ–±WXü©ó~‚Ul÷á§ÙÊl7±<–¤…Ÿ‘pICŽH ß–:\ 'ZØDÑÉ~”v#!@Ö§èy˽›à¶€ŠžVç8òY%:'sCabhNøöìŠ S‹X}ôœR"Ùì,„Œ²_cùÊú*k ½‚BQÙ1“‡î»¡ƒV1‡ÉiÞ:42XCå-ù¢ºv-¨iŽjÛí€.ÈzED\Ûžt?SÆ© r×¼]£õV§ž£#àŒ1 `<º¤Ñ/ðáDëëH‡« VÿýüVºr‡`°,ß?»6åòq˜åÏ¡©Nìã^ô O2%aJھǂˆ *’W)E’êÇ$)`Ä’¯;N‘­LTçí¿½G-øKz\<1‚ót«ç[ÅEV8¾ŸJ5CSfIcö¼EÐÎlj»½7p:ðTÂÜ–K°¿ïãÆÚzI+7ØÎ »~ •¯0QŸíX U)¯c3ר²C#áÏÿŠaê‘ʸhÏ&©+'¸ºu÷‘±`ǦGùÑíòóåÞzZèZ*׎cºñár|…$Q¢ÛÉù¡'v`b[àc‚8DÞ'8^}µr]Ãó‡—KEÞŠ25W„¥1¾ÓÔPßTàQL,6Í%YA‹¨–éR’&X}/, <}ø/-D÷Mc®+¥Êí¶ÉÏë9ê%}ÒØhiMèuë:ºŸA ž( ëß/šƒEÇ|¬Ðtàº{"Pæöª22WAl”—+ôèn–.åššB5rò¡_`\Mü7Ñ/³^-etáØþ­éÅ÷ñÞ¼yL³ÒJ1nZ/uæ ŽòWóˆ"íªÿi€¨ùz¶Äè§0gåP¸6ý¶òÿt´L=MiË5¸;Â:{BÅ!&;,*s’*'Ä›ÅÄÑÝhÚ$4¨X³žª÷þ>­JúJõtQHýà¢4 _|£=ïoÙ£æ1wÅëñÔýÔÈï4»¥ÆƒÝßxÜM˜®p¼¡6tùÍž× «‰8úe?Ðà V¼p]¶ÑÍ}e¶ 9¡cK&Dí3Åd@z`}ê×IS}íèSÝ)ãh_P`¾}áÄr×^ܾOÅ—!w/+,}Ùâ÷‰RHÕû•¯Õš”áø[ßEXØHÅ팀j¤îQ¤Í]».ĺÁú^®ÆÖ.ôÞ¯/dé¾?]j§Oá7"å–(_ (pY,¥Ð4Çöæ™\ß¡ÂÛŠ,NTæ ‡Ô`?A2Â/IöYèÛ-,-¶|Ú²mð§$lêѦž9_ý‚å¥z3¢· ›…ôtž+B"/|w’Owy5È=­¢Ñb`<Ñ)M—ÇÒ€+¤ÌJ1._ÐM“ïÍ“c2C®ÁrvFþ^CwÜfÅœá”é÷þý£â»„òÁúbýÛhµHnOQ z¹¬ü+Ññ\‹›éáÜwÊûã#@2-Q–1ëûÃÅ>A©[Q(ïU¯(PžÃLáiõIšùzm&ÉxÛ[Ó}£˜×­8"¹kÌžzÆ¿ÆÏ¤*6¯ÿªb“ŠÓ\Ðäu-çúX[6]8Ì‹’" ‡¥·×S)•|$©¨û8¶rÕꫜS-ø ¦[vànÆÜ,¢›®EIá{±ÛàB”AvYë3Åäájr…ÔÔ†tÇÚ;áÕÿÕ8˜wž{ûµçzE±«}Ó—wH(uh=6Y KÕR=R6~Xß;~C'¨eøñ €âÙ 3eXÍ?Í„·}kŒ‚%Š£ïè¾°ø¶@Û{û,mõ÷„5>’‰J–³¥Û·_éômÅôž£…§ñ‰¥ ]+»ž<ò¾Ï5—3˜¿³2ãkŒû¼«ôýŸ{ Ô¸½JÖWt¹cèe­UÔÎX_Ü ‘09@Í—†¹úŠ^ø™i­Úì7Áã${o^ è‚ñö‡K›¤ð.³µ¼ÓpZÔ&z^Ý9Ü´\W0,ü‚Jú$‡Ö\êDàaT‘ÚJØT9^ª*}›–F ûls»ëK7—é¥;|ÓACÍ Êñ´…Ý(C¨øÍæ¿8Èw$‹ÓÞõ[/¥BmÅ\²ÈUçq›Óm=_ÜÄÎ_¶~×Jêñ¥{o‹Éó˜Ö¤—æz‡«îK›dñ–ãµxyR>×OÂå•@ŠEçÜŒbýà*pzj¡¨sæ£X2£Äå5yOâ=Zò¡ˆt„:APñˆïòsÇL¶ ÌcåXˆîðå=OYkiê-œí<ðŒÞ~ûÎ͉^G’7*aBè$2f\¦ÝmBÃRÐڲр´Rh Ä÷!Íd¥ñ›æÁkà‚ Œe*Š,Šæû>Á 0&Ÿádõ}‚ÿ+cçݰ³m C%ê'ùév£†J”Ï$±vœŒŸ)¶#J˜ÜŽ ÝÑÓ_\áÈñ~Ϫ»-2ƒ´)²®•ÁÖ­âR‹úrÉkèx#gFWƒn ÚMS‡…Þb3î5C`¦Ï·ÔX(µë«È˜\ù°:ù@bÅ•szãœnŒ÷]Ç ö¬§ü«š×‚ ˆ-åh¥"˜B/ûmWü'»ÒL©8›iD”Ž%2[éB Q®A긹ÊÃaÀòWñí_Ê‘U>Ã$eŠüa>·wR{—¥|Œa×±¯È]ãöý‘⃠ƒ:Æ.Âøé|ÞúÕTXœã-âAòX‰ôØZpúÉÍ”Ð0U †S™ùKÒ§£§æÉ(Û`­Ê¹úSÛB›²Á»ÏØþ&;,pÂÌGï¶·¾ƒ-À—3/Ïé8±"2OèþÓ ýV¿Q§¬îJc´ÜDwðߊ?Óç[4ÌøèQ#\¶ª´Àál®KÎZ)k|iÓ/ë."†éŽ£\ЩO<ékuÒSE<ÞûëÝ!€´Á-¦¨ïKü…–mÜÜC–ÍúÌÍlõ8/¸\¹º^¥‹Ø0ñÇ/eºQÞù;wÒ§Ò‘·g Xq\;Q¢1—ÑfOºËÂB)}I±Ma§ÒšÂX&±]^¡Ï—üsÜØÊ1+ùÄK¤õ–¡ÌJîºÓ˜Þ7Þý=t¤£ )(áÝ}øYÖZé o®AìŠÕRtï|µ Ý%Î’»6Cܳª1>Ì’z´Ð·.ËÍ÷lŽ à4–RïZ0„iTkM4$Ú´‘–‹8*Ž=£Î‹-Êþv·¼·Ô–Îr€ÕØ£6ƒ™5<§F fçLÃ$! Ó7=£&šµÌ-l.õч€ÌTä¶ð;î8—ë€j“Ó`Món ¹Ð™;øpRÅétÌ næA©"£IÙõΚ+Ä[×È»-‘:0¢î¶Á²@\ã§ Äùm%г¯v'ÝG}‹†Ÿˆ†y¹üÅtoxi¾é1¯ÝÑäíJä$‡Í›º)º€×&ú ß²`I+@7Ãβõ”ʳ®ïøuŸ[hÐÉüUwúuTY)wÉîŠüaä”^í.yø•ow¹¹rnz±Ù…1KxÑ?Õx1iœï3,t¹èƒœ'@%TÁ'‰½èãÉyÁF7ìç±£¸ Äçò‹€USêÖ7ïÊ^NÛ–9ªµoŒ·D6TÚBXΓ—ƒºF P¾²Ý/,–Ôr\ CêôM)ü“иê‡DÍ&Šx =J°iÓ’è¶\l€ˆ‹0*]+ñmí0#‹ìêA¦`ž›váÞð`Mš‹’¾1‘V>lš[ˆÖ êb·'û ´{·‚›ýŔӮnÀT·Æ¿P=ìù~ øJxP w+a$DŽù ®ž#÷Þ‰Œ6È9ÐKnÆKg]6ôÈ ®†úØÆ6ÅE©Õñcj4¨ÊeÈ€[0Þ¥m®gÏ}‘½ô݃ˆ3%¤ðê“• ìÛÓqfO‚lëI`±÷ë;ÚXYÇ.˜%‹p<¿­½ [¼æaù-0iδ†ØÖÆÛfS]‚zl…ßÑAôÕ'ßÜ„º…·ó¡ÙîË6ÃèÒ‰UÕ½˜ˆ r¨wq4½xfKQÌ:ÌË¥ ˆlr÷LˆÄµDà·“C©ÖfZ"⺜ˆ ZÙÖ¬bA±µîΗ°'1ß<æÅí!0sÌ L¼«³wBË&\·°G÷# íx êLJ /•ˆ‹M8ÏëæmlœûœøóôñÐpŠVx¿~]y¡ˆz #åoð¸ÑšdÄ$(¶¥ÅšzW¡ô$œÖÜBÄ,Æ„tÆõ÷BÓ»xÉêÆ&{ÄIï9´LO+B5+ÿ,#ñ=÷ØóCõc‹à¨Íúb’¿‡m! Ã]Y-ˆ{¬HãÏǶAµ÷Ú_×`=wAã¨Îgq\ßk¼Ký ×uB>òvÙê ŠŒÇ7”ž¬ñX°Ó?ñu€Áu ¶ÐT-fp&@ö0 ArÓòXpAßb;KD•Mó¼•Ém8ttM,5<[Ò¢wß–ä(á'zha>!9<ŽJ"mëØ/XÖÜ /ú(”äêI~8{EM…ïy›½õÝýôÆ1¾°2ë˜d•Y'Ñx—îD¤hž(s±µ¹¡;Üé EÊ]²kôàv£;Åi)dsSÁmK¢/Óêz Œ1èÌ4:Š:õ¾~ Šèi«§†ÒN"õ Æö\®_hÌ¡D[ÛI¿w]§a?:ª@põv ÿ~¿Ld±žÄY_®òË鎺2™b!Õòñö¨¾ å7[³~æwñ»·Ôó²h¨㽞§az-ÈÏZRº£úæ÷¿ä&&¬[s'9&î/WéµÕ˜ñ+¯ñ€™•pž5­“ ´#:Ï-lO¼ÙF£ÔDKƒÃ‘JÁvN©„X›¬V˜[ôÈÍ“„ž-;kžÞT>xªÕaóCÖa,^™1Ñ`pwÐÿyzq|à¬C¢â¬)À¼YÓ^¥Ž—Ej£¶ÍŸ2JûhÐÚû, „‘'˜°`ÿ'mébhç¿øÔî®Ëi ë6ƒNûìŸ:pjráÖ ¤òÂÞ1cEødO¹©ÁðæÀÝd¯[ è%üßÏ—•ž—ß½dˆÔ»WÞš_·Á 4îÕ ºxÜ̹qfák iüCÛü AþìèS™ŠõM%)þ`KèÃiÏѽQÔ>FKlìœðw7 ݺõ¦è»€dw—–»Ïfµ˜¦J*FhqëDx`)ƒ´˜“;,y|¼vÀoÖ—Îã›]¹©ŠßÝåÜ¿ôyô ¹ÅÃ6¼Šÿ¶¼ù¨ÄM¿û;*y‡º÷C>²›Õ·Šº–Ýj«Ñ––Èt^פ?×t /^¶"Ñ»€UË–V–q,éàVL;©Fþ,ix_ÂB·jH&ÁQƒü#Ü>3h£+ñÔª%Ül %S*^çùdCJ¶£Å^q×¾DzSåÚùسâìN¸‡ ¸¯V펩eü7™õÊŽõ vûµBŸ¶kŠeåˆþa4þk`a.s‰?$ֹȅ‘z9ý±S‘âå4SÔ¿¬”½:âMaº«iÔ!Íz²"U9 …béÍgNW$éìâÏæÿƒ½Û¨¶æ†AþÈqn¦gˆÛ‡u Š”Âð¦r³È°ªÓ¹c€6÷¼4ë§>¿Ñm7tžæ“ÍÃÑ·8vŒìwÀq@§5­=Û7|t ÜØ:fíú_Õ^Íõß–å£Ô5w‚/‘9kœånÑße¯†6Z¡VjoÉ›Ìüu UúpFÓVÃ~hxbê¹ü£™rÔ[[Ñ®€æä ¬|Œ\»;ÿ9銊WБVæ .ŸÍ´Ée«Ô2´>¼¡¤àp¾CÃ^«„ç2Æg Îß„ÉF†gˆìˆAÒÜ~›Ñö‹œYÛ¸§>ò­²¯i.éà]ÅÕn¨ ùãü¿Kg”pw%ÚFOÜÊd‘2 ߤò)%q1 œ½Ñç¯F=k—?{Fò%zQøUéß=·Íé6áñ×/ÿ(E„^‚à‡v)ѽÎ`–Èuéò°!¬#úéרq¥)¤®åYì>Õ„‰ÌRª(&íÄÐHóQ¯%å>+Ø,¶W)w¤­Îù=¼-(X-!9zÝ1µðÏå2Ñh·æ‡7ô|ùQó#Žc Ny`f)ú¿r´;ŒQfG0}èÅf™q¯*âJ`űÀÔª\t§Ö±Ø?Wr-`,öœAL¶‚ϵúa𬱠•‡’I²–Hié ²ù« ûzõÓ'•6@[+Üiš`CjÉù ï´#Z}‚ÎtFâ^Õ*¿Û- ^1zîìl-_?L7¹Žú/=¹¿Ö€YLszÕýj~ë—@A§€-®4·rà:&l\}ã÷šYÑÐÓÇ9=ÝuwË¥³BžÔÎÄÒY¤ä·³Yÿ d˜"²Wí¤~çªsÚªãà·²ïéBsÐí,í×JEÖ5t`zÜbØæ/ HÐÎNÆfPþ€Â3ülb±ºð ûº*É]…Ò¥‘ñ–X‘жINE hTgcM§¶­6@ñ%øe®-TêÉÜ·þo‡+·9ç£,y.°Z`øv³¢ øScWý¤ùô)³ˆq‘^8]˜‹5›ø|jpœwmé$¿þ0Ø;µ°Ñ— ÁõÂÓÏ™:wÆî7µþ ïæúèæû½Eȟψi‡à-|'ñ寋Ϻ´hE£wVr‚Z#°Ûç€0•ò½^7‚"Šiºð9ï ̾$ ¦Ìn ¿XmÏ9tÊM-XÝ–(@KåYY0Ì4è–[ôpÎuþrÅ5ÈÓ¤Èi ìÛñÝ.´Ù¡õœÒ$2Ü.§ÏOÈ-•Û§õ"Ë™u‰»HÊl~MÔÌ!‹q·°µ*-žW-œ8t]½"³Ù¢ûÃ~ _vSëÊpƒx¶á^ÑzSlì(ŒLo©Â‡>̽û F'¹f' ëzEpŸvóxër)kU ©ûú1 é̦¢ê㚀w…¿b‘“Y#BЖù©Î§V ô1DtDŒõ޽Q&„ià ‘ëHçyô?CKç쾆Aª!±øýÝ‘ˆåÄkF¾(™.p〨ò-ðK¢(Ç÷þ“eu——C}ྭä>ƒµ…È^ÓW-Ô ù¾;77%zæ'œŸ³)E¾H‰ø€M­ñduŸ®özà¸ÁEfsžÌàXȇI-¤Þ¯)qqéUÚCåzsî(·¦©‚%x-Þ»æÝ`èš¹|€ÂZHšgÁ ¬šU£þŒC"Š(Òß.·=’ƒÔöM›ãJíéiP<ÿZ3ÙeLï¾tº £¢xã§ö¿†Ñ„|!¿ŒœâHƒ—l…žUb2*=çòOÇŽ"÷D¸h_½K–uµ0\ï„0Áx,Ã%ßiÊšŒa^© *$Ìž±2À4åÆ!ws~vE¤ÑD×ødñ¸g°½và? ¦v.!ÖÊ 3yñp ÍKÜN̦¢çµ¦Ef(›çØj\à Æ õ‘l~>ëhŒ=¾¨ÐX5ƤE&^W¦ö†<·VØÑ²Ëbò=ÉÈ}îÔÔÔ¤v$8 çjÑlÈ?:§ª—6†ÐwÏuz¹—¸]7•ò=¢j1…Ç[@‘Íÿl­EÝKÚKÅ·Æ]·njSüÙ”2»U›üà»ILµŠöÿAÆÂËÙÌÛ+ J×ZFã¥ÛEyWé¶tû2ð­¨GŽï:DÆul4Js{$œàw3’¡˜n*†Î¶&HiûaR+v“qá'¡ÇNŽ`ƒÆ¨ó+áÜRäÏ׌깓‚w«öˆ“× •LP bPÁ¸Ö·.Ç]ëz0.WáµàUJ½Ñ%饑Sï"?¶H×6ÏŽläL¢`Vž®wJ×À°¼´²#ey·*7zCàRÚ”µF’Œ‚(‰‰ÏÁb¹ú{nŬÌxÓda™EÓoú ¾=¼TqûæÓ\0ö˜©Eƒð?´ŽT¸“`Öâ|áÝôa'ډɆ¡v+4êK-è.„âõ-´ÒHçÛîÀþÏzË{¾—|@[**cëv©_~‹è¡™êùÀº=5ÿGðMZ~– ÉöÙ®õ@ibÄ…QãÝÔM£…Ø•àèLîAäIÊ"üÌÙKì¯\Ì5…˜ôŸº+Q&+çƒ! êo­¦Gí#¹:ÄÞ ç½õCÞ¹ ]%>‹Þ¿ã‹UÍêX÷ªc#"ê?MÂÙÀGfGw‹ø‡Œ…ºHŽN”Þù–ý¾÷øšižo–Ò˜–¦ü£¥ð.ƶ;/}Ü%¶ûpÓíª A"þß¿ø<ûxkE$îA0ž5D˜ïYñü1ä­\úuP]© äŒ= Q_ ¯ú¿ÅOË4\™ÑVž‚ xÌ©À‘uév¾š=N@HŽáòÝ^EŒÁá@ÆVVþºkrkš5“ˆ[‘² ÿnksê|0g¬8±«ɾ·¾»z²|#¾hÊè)¡U/³Yôë1¤#d–F@iÈ,¤´¼XUb9÷_Gï¢ç&¢¬ [³ßÆ¿PlsAu;©rŠßns[&îbRÀI` DiuíWÿLsÿlû–œŠBê4éô„B+HsAB]qnÌŸ”ø¶®çZŠÃh%ÓvZ' ñ‹ïøàůwÝY쇪I'¥=aÌÆ6tº*;V'ySÄùI¶ÍŸµ'wD„¤:ô¬sIQ'& dåÁà_„´èi ¤žÜGB¶'Àmƒ˜ŠuûÿßF˜S1Â]Ýqh˜˜©ÍÆ$·ñ`Ë·¦Q(õÀ·x¯(/ø^k§V§ÒE‰ œ´âSâ†øv„Z)µ4¡ÿ€ê½M<}3¦ª_öpJŸånÊHV#Õ*Ë%gCµ o S¸AGšËág]üùQP3®ƒ^G#‹#êpNÅØ‚¾þé†ÛÕÈ¡™]´´bmY~©QÓûˆÿM¬7§]à`‘ÏúðÎ ¯Š\ÙŠ‹¹q“º»™_œÊ¬ì›—(šC(U§ 4¬’ª,Ù;9cì6»Rb£”¯e* k›ÜK©—ŒU^Óža5d‚hÀsà!C­íé6P~3¼Z;”__šóZJ%öECq§Zê,JèÙ©‡{NøPœôÿ‚Ü”â?‰ãÔêŠ=eÞA~6‰Š«øÂøÌvŽŒOpÒ© Ø‹þ0[xÂKb%§yÆœÈTXMGL¥\,Þ(’Á×ÕÛ2(I˜"ÍnÛKb"­0YÔ±RA2&b¡|v1Ž úÑzÿ2èŠ ¯'Gü¼³U ¢i"ÃDù²äô‡“ÿ '/o±ðÊ£) öE!Í ¶TzbƒâÑq2Üpñÿ0UÚ»1›o›˜ š[˜‚@4d½ÞÖ| ûÚ¼ñ¸ž°¾qþÿA6ÏdQС;Áù´¸gy!ФŽoš«”½fI[·À¢}`C’½Wo¼£ËA'œdä¨ÿ ‡: þK8 ÁÓ²-Ñ:Ýêc÷`ƒ2k²°ïÓίfê¢àçÕ VÙA|œx:ïÑ.›‡÷²ÑN¯k@sD%f>†Œc¢PCöX&'cˆˆ0úÊZÎýÓl«Ðï-ѾØÁ¡ýw® æ¸=„ª”ÉÑw$l½¥5bÅ,·9ÇJ\§g CåæŸ¨ÎÌxhÂÚ ˜*ÅuÆ39ÁeîÆ?óÁµ7Ÿ–ÚQ•öv‰š³Þy? ¨Lç3~j¡â+– .*åVõR §áŸœY„?$P²“|7 &ýÿv¥—@¡³¶ëp‰3åm,Íp™l÷ª“Kéý éçiVtåÞ‚:{廽¥NRêÑ]¾òêA»ßû<ãò-Øú[F¶iš°Ó°;æè.jÚg¨jX†·¬¼©›ðSng¾ 쎃&Þ=ø-:‰QJòf}÷ÝõÑŠG^Ž£ ò±¯ä8qPÜZ¾gí7ˆ[3®§•·ÇÑ1bÓf;ÀÒª]lñ[Kmͽ€a u› £pA¸×aWš€öM<ê»ÊŸDM~é15Ü“½‘Ï@l.ÆýkKF“•®ÔýüÖÞ¨L¹LXañ%ïÃ4DK0S+uõ¸!ºæIÔ&M8eûÀd¾t¡m&*Soå®K„4ŸûÎÒLÆc¾)žVF¿ìŒk4D:׳۱HÁOÍtÈw¨ûþi¥˜a‰#±2À’þ<-‚“Ä¥÷'’d¨L•¤ô°§œ_%ηä„ÄõÏ÷7¥MŽTV}vìÊ뤉”¤ 83¨Óü¸°¤ô8LÃ5µïQºÉÿ‚õñ¥Ð‡kù5†œçu­ùOa,N¦ü´ÙHêÄôùéó«É½ÇÁÑ…'jú8æZå)ø†ªå˜Bä‡GzlRï@͆¿hDÜ}ˆ=EòRXr§B73 ‹Kj¸z¥Ñj)x#”u‘^ø:aEó èó'íÞ…0¨žìæ!ïj-ìwò"˜š+ãXÈîÄ=Ë`ŠR–ï*N,VE««íÆò“šèƒÂïeà`;¸±Œ ePn¬Fu';"Â4}ÜÙC’î½1–û”'BvÜI)¡¦ÖGÕ6$º^Öi{ÇYv¹˜r¥q½ëè‰5ÿ€Þ•çCDSB#$lp$á®…Äõ´ý~÷kßR¯¸uA3¬9ë`’6¦iª2¹c¯ÆýUÞA_/ºk'Z³wàþ0wÑÀ§mI££w’MWÖUnYš_WyašËi£Â&ŠiIà§æd3_6QÖ”í¾¯h’':|Cë cßÊ:zWÓZ‚ö—»“·˜ÝbC¦Ï§µw¶û^LvOí àîìf´½]tT%¢ÿgL5ž˜Þ0«3þÙºŽ°c3£ª?ÜQ7í¶3BÎB ö(©âG«÷ýî—Èê’Ù[k÷ öK”Eò–ÐlÅ’øÿ$!‘I±êÍD,,L9èl[îQv?ý¤ÌfÃs§ænŠCÖKA˜¤1›·´9»Û°.(ÀãY§3 "jðÓˆQð}i½Ñ=t B{ß’Mç¬s±ïÕUè ƒÝ6î¾aTCyçÌíZíøÒ»úÊõQÄ ;°Ø<þˆ«×€i€·ÙU/YEÄ`µ F›þÝ"t¹,]Û÷üìGÒE /ã0‘9o „ˆNH1jj­6d8'ÆSñM»ø ¬Œ¿ 9J:Zxš|hêe |¢Ê‚ùËEkåATùŒª‚øÙшvgä‘ÎPo1Å¥>Ãb·ü³ðD` ±{ÖI08+ýÁBKï·ùÁLˆò¬ã¬‡U¹Çkm­¹TŸ{’‘3‘èè;pØÉ&…"u`…º‹ƒOï;qû òoåÁH³î“2ë‚! ˜Iç^7|QØõ¹®9÷>_Þ1hvÈBwcðÄr#g -O¹¦x¢¹“nðå?0*»5ZׂLö‰(o±f¶c±a¥´ˆåã¤6¢ß(·æÌ ù£mý÷nó lI«\÷ÛK›hꉣ¨ÁÿB›mßæ“ ^V®99Î:চ;ïÊ[e¹0WdahF¿7KÙGq޳é©jq7«¥g¾ùóqQ?¹ºƒ#lÄ“d_Ù„Y?fžôÁEõTtR€U`ݰz®yÀ?L•€ùª½ÊË«þ¡UTÀœ(æïÍs…÷kxa}"ç {ïÕ Ò•Éåí/gœ vsé‡v;7ÜQØa~j„²f¦ÛŦZäˆ5©‚o‹•$?.ž½ íÞ39CØ ÛŸ&UÚÕ?ÄGØ?Ѿ}ÙÆÛóärRš­N)ª3ïTˆŠ¼•úÆv{‹°ó¾çš5H¼~•ƒí%ô†ž   ]"©Ùÿgt’î ?Ê{{ Xö#ŽþHT§×÷¦Ô|¼]èÿjI^3†c["R÷‡^+]ãîPo…¥‡–WÚò2‘Ž“‰W™ùL¤‘BXïhúú¬k|”ºó{?¾(ly,·Pp Ë£- è:Κɂ˸5X_Q@s¾í‰[¬Ö×<-yÑcG†úËr þ;c¼™X)`[­ ?=¬“—cÌD}:/ª‘ÂÂÚ@ŒZüÖ‡ŸÇØÁÀ!ÙUjؘ|$¨vG©õ;¾ò}©Æâ—iæÇÏ;±e‚µ®¾ÁDð »Ã…Ü ùWMËãF×Ü=cB ªåÖÙÿzÿsi´=$ñæ—(¹=´C'/ë@ %içòQ„ž@ìVHlhÈV±uäôq0?¢$ RÓEOK8ác|ßT­OûPvIb(ÄA È©Ž¥+›õÝCÔÄ,bý‘®“À—¯ºb„á²­jT8ŒÕ<§™òlr$(YÌ~Ÿƒè;2ƒ”Û m3i¿Ê,Ùü‹,Ýܹީÿ„¯bfþË'Q’Á†3°Ñ6ŒÓÿ.wød`±Ÿ>z5ŠÃÈ!¾0ñ‚ÌVåâfƒž‰öŒìxÏÙÙþ¡WšçRDã]îÀH&?î¤Ð„5G,Õø_¥òèê¼dFæ+¦¼*ÓÝýIÙY.Õ“B°ÏoüˆîY‘²äk‹o‚Fûu‡Í1¬ií)oD?ÓòòŠn);»É– hµ–ÓÊ¢·–Bu />6¬c®Áy8kÃ92{ ëô‹om`œo’²A¼»\frHò É×ôLš,93O>#†ÐHžïЇq‹¨GÌîIß¡8ŸßÑ”–ÿ^ñX3‡SƒtšÀþ¦iÝÏ„¹µövXÍ‘üùtFe~/ÖÌv®¤ÇNda8È¥ôôŸ8xI@HM¾,øKdþ@T £u´eFm‘û[qŠñ陋×,Ä_×yx`)–MD#L•þ®s®§(aÒÓÈÍß µW¶Ó ¾qØs823k!µ5s¥~–mŽh ¦^–ñZ[%á&2Þ‡Å$dÖÅa‘æ¥ÈÀ¹+ð&Âv[)¼jˆ„ÖºV]ÉS˜(G¯+àÅǰ¥&— Ñph«*VÖt£Ô‡ÒõŽ‚ÿ‡º7O\>o}’jô1ßhRñ7}kjÄ œôHøì›Lñ–¯†âH~ÜŸØ@ã}°Uüv „«Êk½V`·Y,pÓæBƒÕ†ÊOš…bJô9CcO´Sûu‰–¤=ÒUî†mYê…PtlqOË\Zå•|ʧ“i‡WÑàóK§«ú‚Ê€VâQO3‡H:îXë0®*ïËyo‰Ž S¹¤ÕÈìb7þ˜Ã±=LØ×wŸÓ‚å3 bE}äñQWY>„þÍM‰1Z¿J(LÍ÷ÿJ…M¾~Ljö¢AG R<¶àÔù6súâ¶ô'S¢rË9AÕ‹¦xõpu¦ä,é|ÞÖRÊçÄ2(úS%šCA ÿURšªlÍ0]e&¦Œ5 ª{fKÏh nz«¬ÓʱQzÁ÷÷V`£ ž;Î=Z%í$[¨idƒ pÕ3~ÚÅA‹Ic)Ÿaå-Þ TÏ“bA?¡.´• /–3G›\á#"\²8ö¥V;ç¯Bäi²gî0ÝÒº–k2×¼Y¢ CW×(Î@]j¥þLjê×^!ÕìWÚ° QûN N¤¥ÒO7aãN¢õ 'ЉfUtÈw ,±¦úÉÙ퉬~Y{Ò%Ä“¹G”¤{±µ+«„+ˆÄ\ÝŸG g§%»Õ6†œðÓ„…&½#¤˜ôÞÍZ$çÝ œ){lò"cö/­.ú¼zù†þM*AS€7ó|ŒÙÂÕ«`Ƨ\^ìÂÍ)méÁ&Ÿà c×ø>yÖ.›Zt M¸;Qv±ÖV¶¼‡ÏO.dÚj+vªNkŠïz‚â´ïµ kÝlÎýÃm[¤Êú t®gmH*ÈàFæ´×°îcm.¦Ê »•bv=B›‚<‰ÛÑ"Í.ÓñÁÄ6Ö9í.ö½D§ƒûC©½˜ëˆ´çQTãí6¡Ç¥OŒæœ‚–C#Pî“iãÏAø1œålÏÅá}]'ßWI—ÕÒ—íïŸ êè>úº0ý½~Þõq>­ÆŸVìÏ«p‡p@Ãi¤ç_Ú;‹Û «Wîœ?iž—d)GCtánYÅÜ=È|jg#„üÖó&0‚CÞ©P`ºu{ŸÊÙ%+Ze?ŽæK0DòY$ºÚSv ~ñÅÆòs`vg”ZÉÖ¯¥U’Ô!™ùÍSPì0LéfÊ[¿·¶ ±´>{½¿‹ZûûÃRS‘òÛOYS§2ÝpÉ×~q¬Œø+ŠêѼ&LvíñzŽÑ,¦”MCYµÉÚ¡Y½3%×t»#4Ísb‘8u+b/×¥§¤ª¤)VTa§ÜfH(cPšõ³À´…Íwìà1‰ªi­- Ý¡¹GدF¤¼i$·t ¡ÃãùÂäyêÕv°œàà|ùjª}/¯dÒ¸NòËÅNŒÜ2³O÷ò^v_ñ†­¶Ú¢y˜»mº[¦:|*`ä¨34´IýÂæM)èNä9לr'»=”œ¿GŒN,ÊP.”€š°¢lb>_&»W^Î’1U*O HÙïúZwúHyinœç9†w/€Ï!ŒŸ¯àŠÓ–'îRÃaã¾ùœ9yªïÞa ü³‰œ™Ì v+Ãl8‚Å(Úv Úö?–ð0,pÊòÛW§TÁ<®† â„Ø×Kf™ôlÅŸHç·WÉ~7ŸMwu+b|­i¨þöD$‰Q5Õ Y~àjåÈð¥a°×+ K¬_·òú(Ï^.¥ó~^5hHwD}¸ ç,CŽãè(áx".t:³Ef/Òƒ]hš 4)1K¾(E¿á%‡&™×k”ì¸äþѸï:¡˜ˆR5Q™W íQÄ’š>wõdž™^?:Ôg½G Ó¨Üb>HK­ù«î´ˆ yUÒöÊîN áÉôÖ5„!LÇ/§WÞ¼äaŽU˜˜hÓNŸŠÈϱSWõSJJ‡µMZ¼&eOØœõ¥ÐÍ0öÀ“kK}߹ɞÍcÁ'€zlô‹£=‘OŒA…IøÑ79Y¨÷Ð!þ­®ø Ub”iU¦õ-XÁÒMPük¥Ç”rØ-Š‘¼½{…Ùìp]ߺ/žÄËÌ2¶tòe­ñÚlìÉη=ñÁã)Lœ7Š^übRæ…2‚ämöäHQè« EïÅA¸ K3‹aDcó^³?‰ûƒYþ‰HPr¡JcMT _"ŒÈq2 ±^|Ô£j‹ºvLWÄΠY‘ÙmcƒÁL¸@Äÿ}¢½=Ð×Ã7ÚÀý¨C”‰·©V/8kZÇÈö?ÎûÖ<=º‡±Yåe¿åÁæ()ˆ¦@9rM«¦üæ3ü3§š¨£JJæï÷Ç 3¾`Ï#„þC“‰å„ÓÕQù¥RMu©›³s^÷ð{¾-iÁ`So¥ªÈÁ^ZÓß+æ‘8´Ü\æDFìàÝ¥*)¦æ·%ÐS‹ù’wf©Ê À[ñÛ\Ã)ô笾²§‘˜ÁÍÌwõop½¶i9¼89ú,ú×Å¥BðÁQE+Áa± ti•iFÓtÍŵ‡Ë&…iÿ'…ùÑî®q—އº¹$âk¥ƒí,â=9;nC8¦{0s,IÞA?z#dþjWh÷`"ÿ ””r\B;ÃÔ9ú?. h´”4V=/³ºˆˆûŠòåøŒ«ƒ Á|3¥Lg¼õ®—иrwaû&“ð øüÏK­pÊø*6Æh,áåT.D61ƒQµÞÐë}Õ0¥ /¼·>Bí)“p¹ê ×cW´‡#žâ¡+ã¤~‘ÞH(ÙÓ<Ú‘(ws!\Ø(t€B.Ìì&¡^yyÆ1ñX)Þ!µªÑvˆƒ@ÿ/‰ÉP>™~'$2™¤w½•HD„£—‰ÁÝOý’““ïUÐ85w³ x›÷±¤Ò¤Š2®“º:ýéÙ‰•{f§•µ?»µ,“Gwy!ðûUéo.ãl#º׳Y‘û—ñX0†âñF)'Ø}:µlKŸÓÅÏ;mž†; u–êȾrô¸TR¾ÙG½ŸÝ0”â ºsëP”|Ö÷Ãy¬$Qd»¯ãŠCÑý óõ¥"fà §HU¡Ä ý&£< ¾V‘–}K æ}ýòÒ‰˜Žzô ]sŠÄ®WÜì2T ï„‚çÚDŽnŸò~§ê½áðTîíeÖ±r¥ÏÜKøeQX¤süz_AÀ”AOP‘¢ßóí¹`N“… €CàÃJ÷ºtePLêœt›j VÕâÉ—'<©¹r¾v€ºi_†<à‚z³¾|a¶ÂÜ[òµ¾£Š°j:aÖzºcß]e–9¬³PšSŸ¤l2”óækgwÛªáqƒV7\VñEõ+ZóZÎd0à„1w‰-yÂHacó})œ1B!X-ö M¯±NUÙÐû¬Ê\ë¬Â$«¦æ)4'ê§§÷.Ï•¹ä ›\¦¶¥ˆ”³MT”i¥L,å >tª$&x>”!†&‹a¬/I<»ÕÁÁ6þždï_–äË«Ò)çJÌ/%æø·6zî{Æg >¬Ïz«w¤Ÿf'øÌ&ú&ìØ .-ß@zk4¦ñÀ$¦Bê†KÝÇ+á„ÚJïÚr÷,0'nö1€Ú4~Z¬aù¶ð =ö‘¾ø …€¤þÞ«%ä]€S‚÷ýúQ˜P­(U;Œ»€±s†u«}®Ë†¯‚Ÿ1 ~ã\J’;3íbÎênY©æ¶ä0.EçtäØpÀ#9ùúQÿ[.TõJBÁaô|aüˆTÅ™Q´^¶æ¦Fú†ßp,>A‘ñ%Xñ‹“÷PþA@OOú é(FYÁ/5«)׆t{úeó“ïy–Åãœd w‡Q.28™.*Ê<ÆÃT×HHâɤV0h»ÙäzŸµ7(²· ÇghHAó§1ÁL”³oSvu7!¥T•N–)÷˜I*æeP3£qíäÅó 6ç´`Y°Å¨NAÆÀÉGtÓ(«<£ÊêÔO«’æ_!´{‘X[í„àĈõxŒ[‡fú ¢E8ðOƵ\²z'g/cÐ:‹S÷#T¬¥ûQñå¶iÖqµsº[õ$‘Rå(Ñ(ÖÑfE•M'zØÔdì¥Ì<Õ—>Õ¦Ào1Õ__æFû„”»Æ‡èÊsœâ£:þë¯)LJã—†“ °0š}I½G%¹ÿYí»¥ zááfwØ*¬VX€'h”Ó>úA0>Ä+ÿ›].cÕßaô Þ÷üâ‡EðfiAÕæö ñ¼· »)–í€Û\£êÍŠ"ßM±Õ‹ò%iUtüÖæø) €A»xŠù‹;ß‚ö±cæ ñÐ ¨%}™MÚ5ÎMÅ«ÐêºÇ…Ràd/a'í£y/ë²÷<Ø<\«Õ^85ò­önO÷ÖRãrÑÒ‰>•þuIÈ4‚j¹n©›¬‡W¤ÇœšÃ󪤚UBCÌôå>s«Ån7!•‹QÔõ͵)^˜ªüBØt2¿F$Ý÷Wçh„Ñç@PšHz$ÙE¯W‘z‘:W=§]’߯<-æ­zd²+ÅH±¤C&Û÷ïŠeátñü8äzp“„Ö¾Ù4] ¢bÒË‹Š•Ãèê©ç®a|vP2N[Étñ± Úd±N‚Qú–©Õþ£HHvE$ÎÊ^òp”h6¬ÒvÒxÄ-^+Ú7e–ê!µÆµõ»h/p„ˆä0çv¸N" 5’ a"4ßP&ö|yKæ…Ù‡™*Ñk©g'$x$ŠÊº‘Ó®¤æ²“íu}˜ª¥ÃíÜÚà<šnNÏ<–r­byþzJÕ׎³8­†tÎÓM¯ã£BàÐ9Ô À†U÷@CuØÂŸÉú'ƒqºÛwÖYÇÕÄËÖ¡në÷ˆé‚ÞR²”Q²‚Ýfg^İâ’Q øÎû¬ÕFŸvÏ£¢–Íœ\éÈÿ%¿ 4_Ãï-²)(CÔL5¤IŠáàH^Où@r‡ô¸šìs"éºÃƒÆH1¶{í¹Faœý)%¬ BܲëÍŒ[WÁ"¶È9¤DÙzÍ,~2$ÊG} 9Lú92(œ%Ì“-ÜxÙô¤ÆœHPû©¨î¶šÁW_RvFÃI9Q5 G²)¢¹ôÁ¸5šGèØ§¨×Ø¢¥ˆÇŠ4¯í,5幸 en_ä{~lNÂÐ×UÞϺ?%ô÷Éͯ\Uç}L#ˆ48™»iyPú¼Ò¼6ç©|L]Q¡'³]Ö¥ïªÃh(FÜ@·ÛÁ,*JLöAüTV Ü‚uÝ* òj3eÑj\M Ù‚Óm6D½4UH`ú&ÑQà“ÎÃÔǤWäk¼oÖ—Šñ@šŽL(Valô^Ñb¨ÿ:iº5žÜ Î/ùJ€MîMž[&·‹N2›/Á©ƒûR·gub¾;LÄúËê^þwØíÜ\a#þ{ ‚Q¥ ¨?MÀ ±³®·BªAI<±T"4yFîtÁŽ^…^Š‹€Eç)Ýb™·ª˜‰Ú­Xd~ö$=J¾¬0Ù|jÄ-‘Ž9{do»pVÐf]«”ïX_›žsVÖÎG¨(5R›g˸§ f‚¥µ“ 塸ràZu*:Ì‹¡¶ŸôJHPâû›bäWpÝ &Ë1 •Ž@’H,¦JAtÚ-¥zïÂåõÍÑ”¹/È5£e$BEœnY³…Š¢( M%—³Â´qqU cp(”~.žÖóiîl‘·ìyg²r_æùfõ¡\N\××Ò^Åj>/'›Ô ½+æÍ^eUT,Ò„xÅ«ÕJ¿¬ L¨Iqñý%ßõX+¶ô@]ý¼Jü•&=ªÁ;MÁ !Í’ìˆ÷ƒ¡3ÁÍa€±‘>rªä\1ÏŽø¶¦³ÛÀr€€z:Ãçœ:*Ä´ºaFNàg\‰eB<0UÇÿPÚûm— <¦jY„Üb°f[øÍÃá¯2ƒZN4ÝX‰&^ç*êgÕŸ2>¤šÑ¦qn‚ùù{€ÁŠX¶$© ”A mHñ öƒᇘ<ñµŸBiH‰´nÞzâ$\[î6åm1À¡-|€I”NdÄ¿œÚä”u©[‹œw^Ù¾­©GøAª ó$…î@ßïdjj zi(~P¿©á¨Ä ‚±iàâj{ ¨“·çÌ êaW¿-ÉÆ[”ŸÔ·w+ŽuÚξ‹Ü|tfCW1ü¿5nlzË¢7Ø7à5tuÕl—ôàHðÚf²¶Ì‚¨õ¶»*£+dnU9R «ŠìMußM–Þ^逤ÍY@šÎv² Çp`£ [ygÒX_°ÆjæMÙÐÃAÔƒñ©TÃmev¶ J¨z?J €R9å!Ç1ÂY`+%¹Æîo1½­‹½ëÆÑv±¶²ç6À~ÙÎW‘#Âyö”i±èõLª\¨sý¬»@jmªÁ.ZÓ¤Lì1 (Ôt´³›`ò*´õqRŠo¡ò»Æÿ ¸_+«Iî‰Ð0mU@®Uáøû$_Ä&®½¬ôÏ‘™SÝ·x® ±TŸÉâ\‹õ 9´ý‡É  wl¯b9®†Mk-äϺ¾¶Mñ™v@¤´3½}áÞñ4^•êÚˆîã¤HžÃÌkPøÁ7)Ë  ?žÏ"ÁÅò’q¸+áØKòëŒb›é§° v˜¶IñN`jÌ_Ú v‘pø ìï–d0D=›ÚàBE`w‹"mì8qëÚV]ÁfŒvÇ£mdg@§Èbó­¢,að@ÏìNVD¦{Eäe³Î}Z7VRsç·ž£Ð³}‚‚&̪¾S“ &óE=yû´–z¸> ³Y$¼€øÌx3eÏ5Vel¾§‰Hà>‰œ52¾âBbž}$¹ªß¬èJ(¼âƒ|!AˆÃ•œ—"Oã'`®Û"‘6!]räMÓvðÝÓïFö ƬĘö¯àÕt 3²8¨ŸcÃ=+#–·‡¥œÛú‚LÜ[ ÓŽ'Û#2 wžš;2©>UÞVv–-Bëâ±S…òêgjÎ9´Ðf›Z?åÎÒð¡wnf€ÄK¥Ã¦*-D‘ÝÁ“¯{äŸH÷Cƒ‰:çW‘‰z°[PõF>.嫍ަ[)ëŸ÷¼ yÆ {œãª­Êà~{âm‹ëòU«›ÂEê(P+·4ZöÒýösþsÒ¥)kJŒ­ŠÍAžŽFÅ@#~„6ùåsX^3H{Ú€Ž 9-‚î˜Ï¿ûô™4Õ÷g$®71õdÿFŽ<ÄçT”ßò`÷÷þï7`þqˆƒ²¨îÏèxý¨Årêîk- Õâ |²<¹yCÅ,|y¢œ^©Ô·{±g=5&¶ÅÎ ¿4št˜ZµdYÎ~žƒÇû8оaD–c¸+ã 1œ¨¸ƒ Ä~ðumÌ‚XòD†ï«5;i}ÉÝï0ÖE½He™úÄÖØ”°ïœ5ò²?*®Ö€<ÝSÞàØêž¬Å÷?–%Ö„÷ql!l•xcoàÓ¬^³„j"Ûü|P15œA4GtrŒû‡_u+¯}hn‚]®@Þ@RëÀ‡Ø`<ýè” ³dÄNÁ¶Û³ “=×ý6Ê*9}G™êØþÙ`X;Ê-(Bì&.Kƒ$NøäjwL5… Ê\Q©þÀÕ7Öh¡)w0î93â–÷ô4›”(ò!Ámq$ZTFæÜz° ‚‹zŠš¡‘ýÑýù;áçYRÛ=‹O¿tÜ3ìàOÉïu”XA¦J7Û]µ®c©VÞ?seÃÈ€íY‹u1›t$çÑH.€/úÖ˜Hë^ ñùZ_ŸrÖ?8v²‚±ßM¢¶S¯ïr¿ßÎÐ < »©›wÑsi$µÈôÒ]ôʆàd©Kˆ:½ŽÀšë=5Vnk­Ð´¿¹œÎ….KÁÔ¢?8tûÕÒߟp3R)¡X²˜\ói1øî'JE`ûÉ4ÇöNpAò\ Q{˜ÐêÿECvHidÞÛµ=;‚¥-õ@Ö õ†‰ w"›ë„Û<Ò‹qãÔ`ôSêØs·gQÿ5Œ"šü…F¢_Òýþ±ÆÌ±:aîPÈ€*~íÐ>¤O45²IøoÐ=ØÉûÖƒw "†Xú´á »>ÜÈ|ÜâPÔú®›1D_K¨œ=qaEkîOCç{Ú˘¯"ÞÒ¿eî%U9ŒióDÜýi¯HÄd)¶èù·%ßrªYx©‹Ü-â˜û?k‘ϱ³:ÿmȳS(d‚³ßÄÀxÈÕs=U½e6 xkž™,^ª¸f"‰ã  iñy¸@TÏ£̼;°û?Sf7x0q#â+ø˜">9ú7b¹çeÕ#oî¬Û8†‡ÿb\:ä€^s¼Tí!>ñ¼“qz1&zì*Œ(ÓüÍ-™/LÆò+qð|tòïŽ%gMƒNa´5ü[Ò{œ|üL‰¹Iüé³À ùCapX&m.ø¹{9?€YBP—Â3Ž7¶_ cL/ÊCô©3ïmŸ@u(﬘€?~Ý¿ŸZú`†'#²´ì½´×âÙjþ”Œ†ë£Yâvƒ\“Rdæá4@Ó~k¯Î?*­^7]<–Ðåkذ&Óxt6ž^‡])ŽEÁñã#ô~n ¥ÙŽ ‹x+†A Ú²Îà@äŸp m¸ëààUÅgΪ›qyžòß ŠßFöÛßÓ/R\§M5Š· +ŸñQfcUìM·š.ÛƒÑ4 Mä)ö7Û:Y`˜Óý£2x”-ÒÆío×Vw7i¹¼×øÝ ¨Èx]K ØÌJþÞ@+õKÀÔ_)V^¿ð8@Koú4)&?°¡âÈÆÀIpg¿ãN/.pøÒrOÏ-s]NMxÃÑ^ÔëÄáë‹u ãö2Ý*) >†‰Eîû¯—î´] ¬ŽP°o:¹:q8KZMñuQM·ÚÿpᬜUùW†îìÀšfdº;÷€Úüsì‚ZÐaYPÉ,°üÒŠ"µcü@–1žöteûv¤Ù2Wp+J zU»M¸«6"3~d"o©ë/«µ¢wŸ i’yÓ»v'Aa!ô¡Qé÷6é²4Z§cÁlÅÌÉ!Ç¡J逛ÁÄ“$U—O6#{äDÚ]ž,(ÚG·“'ðXR+š¦G×oÜAþò˼´Ç¼†3%´ ÌX}„Ùí7£¶MäNMSX«}¹àwL%^´åQ¿;HÛúÀR\ÌÎÿ=± fmì¦Â?EbwnM£¡ªŠ¯ÒÇJk‘¸­òK(Óÿ7ú Ž“nàyhlƒˆ»FÑù*Ò ˆQžÖ¥y™dlú°~‡M‡*Êæ²‘’]+lç!G cü ¿X¤ ÙBœùUëY0° |›=™åQ…† HÜ÷§‡í=AþÍÏ’D©í¯¡™¢dC Ó„S°Á{ìW_©ÍþùM•¨  H¥ˆ'/8?o›ä’¿&·¼œ.°× ªjÓˆéHW_'Ë.%ëÎd~ej9sPµv!óñi=¶ŠàŽë”=í’ñŸj¹=ªq¥•0Î M„LþÝ»’7Ô¥ù Üð”Ë\ú¨vìhf¦ÈÌÂè_ú3Ê^ò(x“/ºÉªÖLZów p*¬ƒ¤ûÄׯä"J‰} «¥^ÐÏ瀻Úè»Úíúþw‡ ƳVR‹LdŸwÆTu~‘ÔƒÖŽ%çwsÃÉtåyÄ }Ž»R~¥Ra‚r‹ÄpžO©ÂoÍáΦ‘ ±<¢ñ¶k+‘³ÌQRÍÛЊ\‹²î¦Aôjôþ„¨ìP˜²D·$¦<ïXQ‘Þ9º ŸéÝ ;³Áܪg±[v”K%KU†ÀeuCoßOÐÊÈðÊßøÂó³é_b‘T‰m™#ufšX44b¢<°¨[ ¨[¹]/|™3­öa*m¯•?>+ÌeÀ@ÅU“‡Äxh^ÍÏ6Z;ѹVþÿÅý‚ïAsYR’×êèÚ }©@^š3Ø,ºn:o®«ˆ÷À¿w+à@Ü ö¼(Yj±æt7†5(ÉJl'E†QŸk¹@qöBì§ðre-Êã í`„­üóö¿dºiZš•Z2 ¨kîuG» ¶ºžX‘Á†Yä°£óy×ÎE ÏËâþÃņVÏ¡öŒ¼887Ÿêçù‚ÃÇôÀZÖ¬éi2’Žš’LÿX0bR7òŒM¼3uþ=‹7Òs< éSöþŸa•N›*ªQOVŠ+­GCÜ9Ûäü9ã@·hÛ›… OGêý;mûÝNýü{†ÿoTEíùsÉä:¶‚G{hÿ0=©ÑJæå‰u¬ò¤®›„¤»¬©£§rËH6Û}ׯ…)¿H¦bai_–â[h«f³á}]#_WH÷ÕÒíï“ êè"úº(ý½~Þ÷±>­ÃŸVìO«m‡qÃdD×_ãñd§iaµÏ]™äÞpe¢à’ú¹Ø-ŽåÏ@X{fègœŒâðÖ¹j8{ÿx,s >m]ÂÞGp:ð2mw)€Aç ºûc,|=çÚîBa èdqù¾¡ …ã3Fxjˆ*yÔ*¿UϬ}úcÚŒ„¾žÓ€o™#ü­@…G8C0ùL~*ŒÇVj¨8_]šZ!JŽ‹0Ù,ûášÞÔLx,q#w>_/ÛÆË˯•Æv½cÃ9sšO®æ‘S¢tå×XñÊ> ÿ_kuøCPnéc$)«s2Aê)P¯íˆe”† Rå+V¾t·G.ÒNë]~›|Œ®_ZäÏÇ +g¨D”z뉳n e´GX4wJ#;Æ¥|Ó^¨Hÿ1ù;=ºTã·Õ%$œßz(u{ XLÓ!Ó¾݈+X–ÊûRW¬2‹ñ0jüXnÐ?á€ù–uŸg(¿IÖüÎ13’â;[}]Œ×:ÝÑ5¨›%[E„i½ÈãÍuâaF÷êJ­‡+L‚Sk‘êIO‘“ãNê‚þ8˜Pùß(=“"ÚŒÀžž@Hãõe”zÐ?£ç(yâ~ÅèÊ 7#nߊå 5Ü]uÜ6³_:ªÌݲY¤l´NÚg%:ôþ•y ¨§E²ŸT˜ê©ÙFžo‘zš¯¨BŽð°ô¼ ŠüÐÆµÞ5HæÙ̦؄›*S/õuÕ\5땇jë—XĈ}:ä‡Q/nÿz{¬Ò9öÝM¾(E¿á%‡&™×k•HßÇÙñÓ¥Ÿ“,̸ÑÕž2¢ì%…"™kñU 0mðç¥C½‰¶U(\UÒqÕ”`Äy£’fcÜ^YŽpI(› ióßí¿gÉe)ø¹2ÒœÐ&-à,šb¯p‚V–­ÆÌ2wGLªj¸˜Ílë64¡V”îïwÚËÅi6^ K;£˜Øìê-¤gLNÉ#æŽYC/QÆ@ÐmˆS¡©='Où.E€ç¡æ{AŽgvS‘bË9žunÞZñ;aõ î4â¯Ô¦ 0ŒLIØ /o‰’!oÐ gKÄ!¯ÃäÊ:Gb(èUr±B› a©¡±^F†âÜg)®…1´llN :„e€À¬ÎO…e-‹*ªÚÕ‹6ÌÔÂúgj2§M‡(¼!WÊg ‡¨bÊq­6Éé¬ò¨ò½1÷oÒTLÏeê)3å0ßE¥`[¨¥V çFoý«çŸ4vétþôÿTõBS@öˆÂ»¡çbʺâ´h£Á6þÑòpè¡Áö+ßÂå´dU*½Î2êû„ÃQ7«óÿöùüîAË‹ÕZNXí¦<Zl`¬Å K‚ÜO@þü© gŸgÙ.ŸÕþ–F¾2áxsWRΗ-‚|Ð¥Y¤="y²±ZEàÞø]kðu Q=ĪۜrVðÞÚE‹^þ.ƒÎ»Â+‰îcÏâÍáÙüó%ú]óÄY’TQ×&›)‰hýÚ{!zÂcƒÂ,døk„êäÉb€Vý5À†Ý9ÎA½',|†¿ÛEÜ€0SSpáÑCØBû¬Cn²êÞ¸‰4Øð1 nèî>o£ƒÉc ÆY†J±8J*WØk² ,ˆ»âá‘v4ìôݫѥ¹quΠ}}`Âjç\gcG%”¾% 6ë–ëžs{¿/0/`Zº÷Uq‡vã0Ç[[ÒèÔçéOµ[SEøY†н\q¢¦ÛÿT'Ê[ÙŒ×Ë¥}©¦5š”z™Ç¡·R€#ÝJÖØO5Q–à4Köª»Ö˜³¼J!¬ñrŽV?òf.p4Ø6vö ë6à_×HCnŒµÞÎ$PÖ´úÀPo·÷ùªÙØ@j€k¡öª‚°€RŒ2nËF:>"qÆXÜq ˆUpÂÄHÆV{ò^2óÞÁ†à¶ô2šëCb6™AB!wÆÂy#w›Üð£îDÛTʸI6è œ9á°Â›cWS†–È2ÞöâôG”Ò+ã)ñÇG80I ÚûT…kòT~.]Y}Ì­¢ú û—é®®’ƒöUëlÆF Jaã:ð€h(绎’ð<{ò‡Ì²ùB]JlGˆKrk½²®'¼Ñ©7åElÂ&¤\Bß7,;¼5öÞè·ßjLRžyi¨OD=1 v9’ŠÕs7•-TåtµL³èÖ#Z,j6#®Ð5 «4½ôH~}ÄqðŒÚø–p¼…ö­ÅÝÿwœˆ“Žvâ|cS"|;Y·o"LÈËÀºÅ©×Ãúà- U³\Úù§ ŠÀ)þÈV®ääN^INm™_÷-{#ÛtMþðfuàŽ¢Pž^]KËzÔE»nˆOÄ<ñ6,²ïÚ¿Eï°®{Xf)™\ýç¶Ök´§‰ãÓl PÇö)„üU†&j r´6{—jžwË)êmÖúѰ‰wûý‹I(³'‹‹Á’¡æã‹jÖMœf§-¶zQ™qÀ££=Î{AXD=Ó‘Da¸=¦ô…¤ +9%9‘&±õE`^t ÁI¾uŠfeâU¨Ú(Ë;Ü& &×ÕåU“ù¦"b„Ç«&8l™Ñ~0õCU=ýÊa¤SJÇ1¬n†#›…µX’ݱé¦9ÙœÀ÷w²€ ì…ž¶e¤‡dž<¿/¶^àr~¢}ÿ,)¥hèÖKö}(˜æk¾ç®[mÅ=ûÀPL.hÄnþ×â"ŽÁC³œ/Q—02î!2š/ëæq†ó¯¢º XN;1‘Ê-ãv0Yè¤_«|ØW<~]î\µœUíÍÞ ÆÂ‹Šª38  QNöÓ´Y®¸àñ¾æ°’å»%(OÇYAOǪÁê^¶ÛSÐäß?š}‡ „dßæEO—؈fZÞ3.7ñèä¥Õ?ŒN™5…ûsyS*W2¼œ'|å5«$ò¥ ஆI§ößDO ru¬]}c¡¼Ò¨Æõªõ“¹.ª\!Mhe Ðç:ùî@eD¢&`㟧v7¢w¥>d…Ñ ÃÄ­Âì’¥-¨ *fõ“ž®Z¬oý8òƒµ Õñ3€øQ[6z,ì¾¶­ ŸIBéØG°73ã¥M» §|“Þ*ˆˆýÅç4¾BÌóDô8=!À°ž˜vSa%¥ºÖ nÇ`_.²·@°žP†º«HWéBŸ(³Å!“¿ 8@;-)có>&Õ¾À3üC¤r¶Væs É¯¿Éd:±At 7\ÌEv@15X§y[Õιµrzgª|6‰ìäÑa¾Z÷¤¤æ?UyÌ­)rI½’=\kÅÿ*Šã¼nUu–©S´¬?‘úb‚?bš¼>ÆO•>šæñaŠL ÷Ù0§TXë3~hö‘ñ”0œPT~¾Eà¸ÓŒ]saL¸Úh4×i4ßoÍãÑ‚¸I¡ÖªîÚ ¡N‚Qú”Áfºùᅫ„ŒËÆ5›ú~}çòK¾á*NîEøu'0%W°Â6üF`S]stEµ{%gnΦYHA™DöˆÊ:²òoK§9èÒ8ÝG˜,¬W>|óI±îoô ÿRøé€ôn žØöƒ2<?æM'M±‡8 ¯Ùâ6Mí°¹žŠi×—Þ@—¥îÌÅd† ¬íé£uÐÚÛG³1Åó±=õÉ_l¢Ÿ›¤ú%‘ˆŠÐôI{*…næäY#âáÌ„½ñ)ÑF£µ<ú ƆtáFÓ©SD´ˆã]öÜ„xbÕäJ¶n¡ Ð)ÃêLYû¥kÆÞZç,ßr¯7é&¼‚þMù—ŒîË6Y\x(h»KÉuIùvô±Qg-qžBøPß«+ŠT‰Zn„5‡æª<8ÈÑ:Ü/ÕË®,j¦ Õ~c~ÿf/”mC÷ž Í5ð<0ðOý5­ëÓV5 @Îãú÷Ðô1‰ˆ!j’ÿ,E£ÃÍsÎé67Ñ—Þ,šÈݹGP-ï–\kS7.’.àá¢ØzòÿL°d² .)ýòàýs~7˜{}ÅŸ¼Ëv/ÿiPÌ—Žwi|uE…ó‹Pw•ïÔq`“¤Ç³—ró÷62n\:Ñ‹Àέ£•D‹ÊR¡BÌ£Á‰RYÑ_œ-³E0j‡£ >ŸÇSnç̓NÀ—É«£ŠöÛ³ðþÐý˜Ssùñ >Úv Òt@¸vÀÊ7óñ`Tr‹FTã;!ZÎ;ؽ%Öv;÷=b’a‘öâ4 (wÌi û3Pijtùš vÍ\% sëÇ…‡q¥ie¥¢ubüš üRçBóÁB¾±À/kÁZ˜=s9µóÕ°7‡Ñýºc1:ç`ô_¢‚nâf¤O:³q·—·¢'×~Žn üöfXCcþÈÃØð÷r'©Í>KEúŠ $CwÑ«£7å„:4Ô½>ýf°s™uc ¯®ÏJV°dz­Tiç¾¥zòFÉÝeAþ?Q u]Ú¦Àpï pöa@W`â΀¹À3új¯D+T°b ‚¿"ù¡>—²ý#EFªß½¨¿bh'¦“Xaþ‹Z>¤÷Ðjb¥8ÏÍYÀÔ¾y¦°“4[A-¬k‡MsZØV¥D¨0åýàÒiÏ”cA\t•Ê=Ù4¯ïò>[Ï@ã/ôXc©÷   ¯?”ÝõÖN£jy°°¼ðLã@þ’¯0SXx2w_—´n"8 |È­ÛÁî«›Ÿ-(?$¼D5ÔeZªœ9˜öMÆÐÕ”TžI”fAIochz/yúòÀé­oyÈäÂÒù–uuì3›õG½b©õã$È$€þÁÑæŸñç—8 ´ýÕâlÓ@§&Ýeqš¨ñò\‘›’G’¾I€J›+I* êpñJ‘8uYŽã™aò›sŽqa¹!=í>_h8Ëέd¶{?&30aB«»ªQ‘¥Ñ$¥üÚ¬£ l„,;ÏDGµ_i—HÎ)Dºæ×ðÒ·©º®•’ °è#_~s«ÛˆÔ$‚ vJóaÕéØ9Ì$™‚›>,î_ÿl¾I‘;à:‹XI¡äk›Úh—ÕÛ´“ªL ºá;æ áà:¥²f Œ±Æ7ê¡mé"}€—ÆH ÍUqDúDá,q ‘ñr²EJü¼%÷.ÍÐjÍI V¿Öa[…+YNGœÃpޤ.EK™I[Šý€ú‚'Èã ÃV¶9ÿ_ô¨È˜J¡Ì“ ´.‡Œ Þ‘¾QËMá9!ºÛjCÕmEJËX¬HåÌ0§Eô-ÂÅîG7™">ˆé£VRuã‚Ú`ªB,?–ìòu° Á€Ä=Z‚ÏLÂJŽžŸ0lØ÷H:©ÛŠæz«QëðÕ¯¡©[ÙF«(Êï³UŽ÷>Y9†µ‡•câÑ›cnmˆóÒ¾¶–$ ,·å@“;L€)ÿajàgnª÷#ŸÔ¾}ûS‹Q£ª.‡qRý‡íÎæ¯ÏÞƒ½c²«_Ø5…'}À¶Â‰~ÚVËrÖ­“ZÃØ7ÐÒ7zr?ñë•@@M'ù¨F¦J'ÿ'áò³/?9?ÈQ?í `çERÉ“*fæÈÇ÷xp(˜#·HwÜùËY_*x<˜î rZògozL¡Å „¥»„{Û ù ²žÐVVgô Ó§špœ¤Jô¨Ã¶€x_]b¯ñdV¡Ôoxˆ4¤×äáá´5äÎ*9ø†§k×#8]ûkðò6æð«@êöZ$e5e5÷â§¶Ïk­G~õo¼Bîcn$}^®ä8nª¦øõrv)”ÿEÀÞ O IÙý ‰:c™ýD²œÅSè—^ïäñ3…m6ßå=]þðùà=Žþó_QÆ…“ÝaÁB“L¼Ø‹Iýz?w’¿rñQ(jha%n›Ïeâi{܈H>,zhäÃ&zSÕ¿ñXÙš40i.€_´/BZvb,hŽøF†Ÿ}t×PƒpéÜŒW8k„‚L’%-ÂSAÏJ9Öþm"‘¾òñ³[S%~Ä á¥,Sï6RfP©œq’y÷… ±^‘> F`——Ûœ´Cê[¶rÚõ|¼e¦b‡áF«×¶Ø]–’ Ée6³-?ôœ†uǪÄës#Ù˜ø?RÞÞ%ì^° :ìA 7ÐÇŽk×ýãÖ"Úbÿ)EzÛ@’¯'óèŔO– ’y3Ù›@)¶ã_û5Ü.iL›5é23|ï.uŸÆfw#‡å/- „¬Ã1~ñ<5¼&)oµOkT}ÔKZ¡o9È5QÖî¶!¢{Zo(¶•âDÖsÑ‹I¢ž‹_èÙG­ñmhŸo åN~cM‰uÐÌFÉt(à'Ó{ˆ >Æö:úå­Ðð‚0à†.Œ˜ ÍW'mŠsÀŽŽZt‰K8Œ'ØJ÷ƒ…%ˆßzûS䋱yü7c/iZXvoæm\ƒK|öÔ+EsÞ÷ÀY=Êä7—ó$ÙÊÏ¥¯žzøž3îǧ¤^9O¶Ù¦ÄC„4°}gë'¿o¤ïÙ0A§)é¦ ÆØ^H¾„ÃåU³§ÄwoËÊ Òž ˜#]ío©Å(e_Âöjßã{¢"w.+*'oï»iiȹ¤+A‹pùÈÌüÐLÙQàSÓǘ}¾Ç‚«~ ¨g¼Ý„%ÎÝ~wËâ§r¾|¢N4­ž1ë6ˆˆ½aŠg¤¤"ì?qÛ1ŒÉ½Mc¦ßvr¨f×§ jBÙ²ÖuÃÇn3F.ýs ›üðžÜL¿2«HA›ÿ-ÓZg+Ýw¿«Jž¥9KÀ¯9T¥5Ik9º¨Ö¾ÃrIû¹ŒÔSl¥vÒ mz&È}±É9{ðuË‚XòDs¾ôW—P£ z ¹Š~Æ®a^ËPëI}U#‰W™˜O§E<³Â!4³_–DiÏázÄŒÁg"üöi]Ãׇ&®TÕ„‘ŒÎYŽÜ‹¤ZÖµ¿DøMœ®WýZá¯û*´|BF'GÚï-?îÅœ7¨„?/Faƒ™W²”§ § מËTD 'Vwºíÿc*ö寰ÄéÛIVrO˜o€ý;É3 ¶|Œx%TCËí>™ãÂüÃIè+úvÌD.ª’Š­KÂjÑù>“3!øÕ‚šÒ]/ n*ÕÃç CižU>ŸœãÓyëès«â·;Q³íÜ¥1qç óŠâJæ#ê4"œVkÞ'ó~Ò @hº_i’jP5øù¶7>QU†œjsnò~[ö¡XËÒ¯( °Lç¤óÚlŸP7©ö7I¯:û\vùeG]Fµ¼CY¦ê/œUåµ@7‹FöÒB¨’ æ¬)È)®Ý¾oÙË÷]Ž–ôÄWILëG1vb6Övä"寻TWÕtܺ*0Ìàê¤]=Cøöã ‡bÄ07í•ä߸a/ßÑÖf›(d;ÖP5çäã†&àtè"\w)á! €“‘°¤»]ÄŒò6ñª c~‚AwÚ\}ËL.Y© è,"x…äÄšôÀ0dîÈßQ´ûÅ)Ž^7ñÃÆ$ ÍéêFÐ{ÿ(Wh¤swœqO‹ßdš=~yc†2Blè¹~„<-ôfJ>–{TcìÏ™ß=nÂ;µñ˜ Ã9HCœ–÷JFjuk«xö>ˆ™?¯ “@n,Z^»Ï½–Øï±5mû"@ !ÚtÖ´!µ‹æ–.LF—Îÿo» ŠÌ¹«6¤ÕÔdE4<^’Ç3GèÝÊ/VÑb>"ØÃ$¢—žÙÞÌ9?„98"lŸO©ÍÎ7p7Y}‚ †´í“ƒ.Éaµ¨3R[Û\x׫QŸØùà²`~ÜfŸ÷{¤¢*~¢‹ª}b\ö*a©)”=ˆþdÖ…~[ó@ªÏZg"X½ +E¡y×[’R1—í–Ö¼ÎAÈßèD>'ÂâéÛ²»7$ïßo­lÞfêôK™XýŸTÏû‘ïvÿs¸ê±ŸDåA³gHM¬ººø³a8ɵY†r•¹”V]­Øîã]äÜUgRðº¸ÖiSi›fñ"ôš·j$¡1vbâ®é)šÊý®ÜËðM„£!ö¹ò`»R•A Î$‰[»œÊÝzGÚ`H¶Äûi‡ŒßÝ"Ü´’=6'°z‹ÄØ„ÞtÈÓ†|ÈýÌ{tÂÎÝpQÏöaÜs(¤Ýòzjq+ÝÙî¦ÃùK¬%!&½Ä¢­TBRR#¯£šú?VÞG¥õcCÅ7èªÜQ¹* Iß­~&¹‡†©Q]÷ȵ!ý„S06dž=ûõj$î¸ •¬ÛEžþèX“Ša¨_o†¨T-²@¿ ÷A(ø£š|íÊékyäV G Ñž‹w&s¬¼µ"•?Å®ÝûûeYµŠg‡§Ì©"aÙz¨fsVhW®®‹ž>ÂTŸÇÑÌtÃl¸r8v-W‹;ñ¤£Ë*MC{thX†Ð$¥®§Ž¾ùQÚüÞ›[ 4öµÜ~qÒa¢™tã(Ç2›=×8cüs‹ÉÜþÎŽ7 G²(§è3Ì?Š!Ê›2æåÒvx—Ẵšp"ð7G@ÉV{TN¤M·°y¬ÂÆu²ƒçgùÜ|Ú(Úùâ`T¡¯@ôʾ¬4üLîØ£‰«<úM ZMÀØu=ÛÛýÙWÍêd¬§‡ÿ7Ç¡_z˜ò#§Â˜º$¡ê6Ƙ9NT”í°Y³Ö·"ÆÆos¶¨È-÷ÌÐcgÚgÔžT¹hl¸lâó" Ø+´µÂ|cçôTáy¢…ž L»bEûûtçάUYÛ*çI]¼؊MÐmz2þÂiYsØ gä±ñÎQSŒ`þ /êaL¾/y²Ò˜îå&À«NB–ˆ &<Ãpd±#ÆCš5åt„óùooˆ‡qO,ƒI¤`ÖΤ5ê·‰ÞwGê9¥°º$)þù®SéF xøª»Q¨aY ¯0w*ŠÞ.±íOGõD²C”žåÝ”Ù×;‹Zö$ª e’³ƒnýì|Û7Ÿ©ÐšÕþ-¾}•«Rôj%#d a·‰/zÂdÛ_I’o¹jijäSGÆÁzØÅôÄì¯ÌÒ8H[6Ôä -ç*ä}I´°Ñ–Âa3öôI6ÑêºýlI c@$ÞY‘Æ‘Ð[ë7W%՞ݿ½Ue³ tƒÃ 1¨ÛøP®Mý¶` ßì45óuû°ƒ_ ç8½ƒïöŸÎ+c½_H¾Ê?‰ñSt ¸ÎJižè¡w¸ßF_Å/(ÂNxö¡-×nY½FŸž©QÉ(ä)£?;Çæð=Î}Z6}žG¬³øÝ71·‚Àß¼¯"KÑŽ†–_£[N­^ßù|9ý••Ô¹ªµ_õƒMìK‹_F¥ŸZ”ž^ãlœ93×´ÞÞÁr¢¥Q8ïébdÒáe‹ž×a#käÔyÛ‹´z]]lJØT°ßÉÝÑ#Lo¨´ªÍ|Ææ†ÇŒ‰ÔÑýT%b. wS ŒN*üÿ (!Žn’ÀdûØ™AWŸúØÝÂ_ºÝ‰ý\áBGÌ×bd/f¨µ»/5^p¤]|ZˆüÁË„­° T0Ã^Ârç â'–Ô9&zæµ¹1t'Ð]6ŸNþGh¾Ž†ùó–Hï†XLÍËùëXàí&8â-Ëö%uCâ'Ñ+kwÆûŸTu]ÞºGdÆj”´ŒøÇ> v‡gj´@q-²g[mŸR­ŒSÑ}EŽßÏ8ìɯ]QÃ_1Æ„î$vw«…h EÂ,¥/ ø¸Çá¹ßŸ# ‡ ?D øÎú¬R¼*R*„ÜKG6’‹„2¦ ÉCžœŽ›ôœúÁt…ÔO;÷6%6yÉá)_³®m´÷æÐ@K´¬:äSÊáÈÒ£?ZýØ*ÍÞŽÀáŒ0 ¾ì@Jp°‚™Ó7Q3pð]of¥±„b[ ˜‘¬DBr&«§jBS¼áY™Kù]„¯›ØÆÑÚô't‹Ù%ƒeT ALkÒÛÏFW3Ø¡J:‰ù¨žýœ@—Çâ8§Û5–Øïyä8G‹„$¾’“bÊ’þDÍ@,¿ÙñbÝîI“u¯Ö(7±êò²´+)ëõðÀ'“·uvyzsñ}ùÿBÐ| iñÀÁ!JÑt9+ïžÜ4çÏÏœz‘‰HÓexQOB”Î0ÄáLóld2¢}Dzä;5hàÕjø¤'8¡£¢–‰WD -6z…®$Íë葨:òjY‘gÕ 3 ÑösøA§_ç•0[ ÇÞ̘9í‚Êb¾<¸>]J³Î“y‡b³Ñ-hzÑÿaªphÏ;³=6¥zKF6áîxˆžNvâ ›JÉŒiŒéDšSŸúaÍo´Æ-B?ò´Š•’&œÐ‚&k8sßäÈòŽÓøQóy÷ÉX×ö˜Aê† Ü!nÊ*·`œQÑ9$ÞÔã59åVk¢Œ‚Kë¯E@ö¶^§õº~ÃìÖ%¿KV¼›ÔA!ô¾Ýâ ¢Hutx¿Ûí}ð9¶ó •áèSHhÇ-Êüʌƫ4xuÕ ÛÅŸøêÊÊõh™…¼„b">@-<ÉO^8!q3'`Ì!ø ×±ÓŒ*ÀœÛjk/ÆùZÊÏÕÙ%änêy%ÊßíYªuÙÃ4 ˆÈi¶X7iz¯M/AÈBgØ,¡|С̅g–„‚‡jñêð+°å‚Ñýk¶M ÷:¦m¡óü:¾Þßûíí÷øXÃj¯·³Ûíîßøl¿ü5Êûzæï·µ_áÔGðßÛíënûzÔþDsü:*þ“÷ßácßnâßoM7ÛÜ¥öíoü6ûzKï·¸/áÕ‡ðèøuWü:ÕþPrþKü:‘×Ûַ𭿆¹_nÿ/·­ÿpÕ¾}º…>ÝÊ×ÛÕŸðè¯ùì¥øtü:>þ€á)æg »5×Bx;‘ Ï3î{çÍ®YëL“"_šŸµ´&ØÕ”‡ì6aT=“PôbÝ8 fÆó9S‰f1O°ß6L‚H jíVšö¤À—ì$¹5.ê¾·½;¡'A;°UõŸbñÃ¥L S:súDd·ÙÅÂáb..¸4ñ¬éÎÏ&¹ÝCÙ7Á2-ûp[­•¤©TÌ)Š%Ùu¸Â6•õæí(bx ¤CûòÙ°Êi¥Ï‰¸RVóö¬ÏÚý5QX`œÐÕÄL¡7\™à#ä俨ŸOM€ìB©Žj~¼6¤C,béùµl3 d”}—!~Ýd5Á¤ý§ídU 7^3÷¶Ï&DoƒÝÌadAÂVðÛ½RŽÙƒûŽÊñ»Žì ’HÒë•ó»gñe{ã´Ö‡ÏYÚ³éRº ¸òÁ w\OcÌD ?ö+`‹¹pÏ9cHÃ]8V»1qÜ}V}@ï¶Îm ®M@ ÝMÍtÖ»UŒ®dd HC Ó;©Nó‰tx†x“ÉGæê…™ãðrBr½¿ ½ç®S.TÎè¨þlédÞyŠ[V•6ðpTks!¦K¨=$1LÃ,Lç³ôsËF¾¤ÁßMõFf ‘ÆD6Y^šÆ¨þòÊýÙËœ5]ÞD"^%Ýt—|ëâöÚDH¡\Êè½(©l¤hx îü¬Ln³àbÃdxŒø&¨äÊcÊàôÙ‡NLœ®Ë„À1ѱ0áZNï9Påiàæ«nľfåho½8Úå5ÛwõwðÒ£¹¡`$èX€´´¯4|©Ñû߉‚n úZNïø“@+©Îè­•pûÐf\´W#†Ùg6"ᱩ=p|¼ždB7€¥µ2wçâ«ös%*þvu5N¯Ók†•ÿ+t¼RhÓåÒkr7Î$×™ˆN¶Í|‚æ2á;v­Vz—ÄIéÞ9%b@K7õ˜¨ßTràR—H][n¹Í#´ê¾ÛŸŸ¢â¼“c*-¼Ë\ÕJ6"ø³Ã›ÌØ{œ¦=’mJϱ’Z8”ù:Õ^9¥Äéã(÷wp³„Uh˜u)Œºô«P ¼ž‹ˆjˆ»B ¹†Ç8®òb žóëMÿSÎáOá_J\‰=u‹+©U½J¡ÞÆË‡1\ÔË3?&0rÝ+KÙnGŠT•jÎìÒó²iJo†M%~Øùþ OÆÜÒ‡¼¬.C“=‰ØÇ*2° Ãtv‘ÞPAª}&O=|§^ð U÷Z¥ ñ0X£^ $Œ6T›„]ÒPédN;ݕöñ=ɪ*P8"yð¾à! £vßjØ8íbWË̸Õà+×òÙgÐþ²í³m~Á/UXfbñü•žE?¥ñÁKÇMxÙ"ý¹G ýÿ8‚[΀RiSËc_]¾÷€ÈøucC²¡S‰×èr_.‘ž7€'Ðêù‰_/l–mÚJÜ}Ÿ` L X §É¬¯¨šÅ,]>5¯9I€?Þ«-}/¦Q9׿¾¡pºJÉQkL±”ýÕWòA N9zHbs! \šÃÚKræ›vfŸå(ƒB‘(>%¦æ®yv:a˜Á3 ÝûA){ qs졲”ü0oÓ@0œÚK ðØ¦ªtW?äþx™>á®T@ .:Ÿçwñ‹'¢e9›VƒŠY"XCç @c!±F¿ñBk§qçR…¿Ð¸@+LÐ>ÁÛŸeE´ÙðÍ÷?xÚC]µ DÔ”—ÔÂþé0¼ôµ­ª=oEÿGê0"PÓ¥Vý.fšòöíã‘’•ÊÆÐýl HW&A|dšöÿÚšŽpËÞKpÓAÒ*Æ»õãân·ÕvšM˜ÔÈ0¿m7’Ÿe)--;g×D¼¸M‘üRmÒè_áa£á 7"\zf/ pè.õ‹LkNivè½¾“#³EW¿ô§>Æ >a ÿK/¶­ž’ @C¯¶ Þnà›\mÕLÖ匀ßHÌ`­¶ŽˆC‹Â¦¯gØŒªÕj’§>¶ IzGÀ ;¬œÖ|º_ZAÊ{—VjˆŠ_ P¹hºÓ«/EB›¹!é Y´ †¸¨[¶7§éœˆtÍ­ßúO˜ÂåÑÒ dN½³Nõ&¦81ëQjÉÀÝf:ž—ìN÷‰x:,h|áZ¨ -ã([cå˜Èî$…=6ƒín[ôDqÅaœ*§ö¹п©:—”¯Ðuôö=:ÙøÃ@|Ö¶éÃĵ2¢ÿ=ìŠpîÙþà­z‰Ðsë]oÜ¡D¶—¥§Êý ׎å0y …þœ¶óëÙ"¡8 [žZwÿEA•®GŸ7Mϸh«^{!8ϧŒŠ¸n:™Ó&ˆOPÅxY^¹u¸ìÂt'rR©_| ¬³ô ŨÜMél/¬*s-•gÎ=ÕðƒU°K'M \׿.mÌ/žM¼+õ¼Î®7K5-³©s—&³•ù­CÏÁin_ )»Êë?‚gRÏz€œ#m±+Ç]ó&vmø÷öA¦9Ö²†œš#‰0d#Í`A8¢3Ôˆ‰¯ê¡wÆì8Þ¾Û–€Fè-fÍÌ++ÅUÈQ ¦‘7’h³84t¯:;49!Yìù‡ ¸26:Õ¯õ¹f}Êk²‰QËLÙäÛH¢ ª¦uÌYÕK<ÿ=4pá0Ü´¾6#±›³‰›Ön‡ºÃu<5¨£õ‡Yªd§OÎì^†Ã(ï ì-ÆñÿJÃô®áƒVÂâŽÝB'Í+ËÏ"é ï¬"ÝòiÊH¥²™{¾.Å=èË%£YÄÚxÄ®ñë|è²ø¢³öiù\»&a1ßdvMœ1+3CvÃ]ß/t‹è^$¸vŠûé}}ºâ6µa#0?Lf3£fÇǺ\²‰ Ê×È;©ÖRÜ4wdœ˜E“p–è\b Þ§]8Ò°»øRîó$ÀUÜo”ý1Wµ7¬N6B©L,û“çšYc+™ß;Kú¾õ”¼»ÀšòŽÔµ2t2S¾¦ÎBõö¸¥]™ûÔ.õKí4)XOƒ:w=­ÕHÇñ+Qç¹Õ>ÌÒ­{N*qLªZÞ±¸jÔ LÁ ÔÊ3tÁÊѦ¥¶‹u†+y„O༠öƒ’ØT¶‘ê;Û¯#Š ö3­+FBÄa†bÂ[L:¿•@¯‰[QŠM\ ²I––ðæ©..š0·‚  ©R]Go?©‹Y&䣰‹5¿YÇï 6+lsÅÄ‚ùø}‘«CAš¯±ÙÅ` P —7/%œ£o§èN»2›;ھ߽¨¾ôžÑÐzпõêûèø+ùÙð6]Ùo঳Q“`±ià-ü÷ŸzÊ;âXî‰Ì¶çöáüjkåØÂ/ç|> 俎)&UÏk¤v„œn­'j%¾b›žÖÄ›sÐCëาŌH–dd©•š_ºá™Þ—‚•Ã$~T¢'qmNùÙÇ#53ÆA¯Õíð³n8×Û/ãKæ(Œ2Ã:èËT[ŸøqŠÑ+[—å#1I(j%øŸ“çêœ KtLí.ÒR(=÷âf¿Ö5¦†®Q³Ÿ/]‡&ñE^;VVΡ0 ÿ&ü-mý«*®?A#´&é(ê ß#ÈÕFJ/äÇ(wŸúëÝQKvŸ4ÚIN£q‹Äåç{ö=DÎúM?àʤþä¦CŒga€àæÐäòƒÀJ±ñOÔ˜ßSÍeëJÙþÝŽãþMënwžÑ‚µ“\+ûé™å0›ÇZø¦–9â[¸Üîp=C`¨ê&_¿JNœžµ­»ˆ”ŠeÜ3)S›lƒ÷À¿A ™PÅ èwiÔõ¢æ䕨Q祺Ǹ6ò—éƒéw žŠ‡;þ°ºMÝâ¡Æ\YÈ^OÅ%R eƒ•(j2-ËÀ4X¯Îx äŠLµp˹ÚãhÝ'µV:‘¥m®c7­mlzð´¯ÙõÒ‡LBñuñn£ð׌– >wÖ;`ôq …¦Ø©ù“RˆžÈU+v:žpàAÂÀ¾à²tìµ_†¨°[bâ=w'w¢óáp¡t\çi±µeü"Ë!Þ¾oÀއf©ÝºOQ§0;]UÇM©÷S—ˆ<޹w™&Öì'x‡äþ6(_$ì-EdâWóÏµÇøZ&ÂÓTWqtå×-«ÍÁ¬¼ç›¢’žXdW_„!c˜ùÙŽàäàÅ3*«Å¬˜ÊÎu?OY™ðøº£­ÃëŸUÏÂâ*× àËùÃß{î«ði$bŠüàVlkV æuµn0è}Q†5Z]Šþ×4>Êá=K"ã_¸ãl`zÓO ßnÏ1§x2MÀv¿„ü–ÉsáïÿbV…‚: ãm S'ÿmO¦%3Ëc<n¦:'Ø%lstC˜su…ÑÔ _BÍ &®ÔróçßCˆˆ?ˤ¨]ûÍš²ç"r,|"S‡Èzàz‹üƒ/-”.Ë;D¶6‹ŠÆ0b!s2¦ÉAyBÛ$–PN é Õ¾¡à>zh-·*°"»ª/•P;¤=?A‘Wù³ÔT\­†ž»Éù¸…ÖªŒäñÍå²(â6ý`¡kÿYj‰ë¼FÌiiž¬CŠ|5ÇoI¥'E{(#WFÓä“„b#}WH¥Ì9~öÅ|§ãñÓt…áÁýñí8çÅi%7†ÁI¢WK²Âi#TÕñ#Ì úž:©N_·ºÔDÄ£õcgð~û÷¹žË<0'¹ì>ÏU¡5SfÄU‘ÍU‘wü^ÒÓV‹«¯±[Ž/ìî8öF²ßhæóòVÙ‚`¾zÓÉ–³de¸fW<Ù#PΜ›êªéƒXì0³lh>ågªˆ!F…"tyå¸á,Q„KLP›´niì¯SvÓ¯H' S¯V*õ]ì¶œwªh“0YoÛùª&ºçÿ¶«P¸ó bŒâ‡Îwg«WH­X·Ot8Æ>9×Y$:ÝÎȔݧs¾eò·U¿¿4 ß–ä ì|=/Ý–N6ôÓhSËvÂQP_ø sQ4‡ÅÕ*Ъ"sçtrÃÒn k›¾Åé$ˆêÖÌéf¬~Æ0î={™¼ÂԮΩêVé‚´…¸\ð`GaÿZG"P&ç#-•“¨Õ$’\ü—o޳§Ið³cõù=ÒÿqöA(çµÿp¿[ú\ŒØ<³G1b\ÒÖ6Åê¸ üì}²5MÖš@?βs-Y€Ð™¤tŒ{¬ÅQÔø!ˆ”Ð<Ð]ýó1T 8Ɖ× v¸à‹àªM©QÊdJ?+C.í0ÔŸÏÌJ€†o‚j{ÓVÒ¯q¥T¤)¨Y0u7²ìéj(Âô©)Dtt5äô}—ðviëV–d…oü;JŒùÚÛ£K¸#*Œøi6ƒ|~ÔuÞ_tà62ÆÓ6Ý50Í\_?ÏÌ2´ãæïÑ4•ºSP`1vÿVStȾÿA³ieA”jh]±3Š\cÞ$%QûyÍsÙ%N?]µ+yžR¡/Û(Ñì3BY>Ì4éÊy¿åš1yå»9ƒ/è @i:î o6„}ô‡›ºC¦ Ð§+v©‡ðoám÷›Á8}½‚íIf*W»°Òêp–ê‰\(3~¾œ¼(žcÍx¡ªá ’î#˜èäq(Å©èa ûZû™ŠQ]+ Æ=ïJˆŠ÷‘Píµ±;ÓÊûZ”ÿ ì,ùŠU‘H¢ÄÍ6œ·‰‡$á¼]Sñ ²º>Á@6²SZ?Ç?·ŸŽŽpò;]ZÞÅXĶ·U"öBÉ¥ÆÀÑDÐLoîÂ^Uä}B#p–¸ZoQLŒé¯ËZé¿™†OÈÔÏ6 Æ|†;›²cYP'>öÓ·y^ª*…š‚Îæö€.Ý *—%c0|Ží]ß>ÅPÑÕÓC ØgÜH¡÷=šaêÉ=_ˆÔ%2ćŸ“cœàé‡ÿÖ1*eº¼wš±&†YÚ‡²ÿ¤ñK”«iPKüCÿO8T#É;A£.“fŸ&~9ò8ôz7õ?¦oØÔ¶Ùö þµ ¬òaF‘³îßýP‡„S8k§Mð*'ÔÀÙédÀ–mðÏ[fú7Zƒ${öŽÅÀËOÄ Þ5MäB‹ +º'¬èZ{$“A8ë*ШÏHW%;:t•ƒá«¸„•²ð\8¤È<˜=Vü(XrttE"[‰qŒÔ“-Ò<ªà 9åºyâ#%£¼PŒ§üX‡>Å’梷“éì¢8†‘ý"î'À¸_€!¹« V:BŸøŠ! [á ÃÆ:Ì,‘¿}r¦æ›‚Ìk(É©ÙòiY{χtß‘ÆØkõH@Üm\vŸmfA«3¹t%N$zF7T: —xØ·‰q&³^í)šÝ´ ˜X†¦µ+ÖÛ%él8‹Òû8hœð EýuTÉmÀá™cØîŒ'kõÛ‘­†zMJGà¯ÙO)Ÿéo¡}˜&ÜÝéô‚Òí„•úý ½â‡é͘ §¤2IîŽæ)щªý·ðú×I öI}×ètáÒ­t){&OÖWŒä[¶t„4>U?/3xËnÁ©/2ðùödÙB|œø·—ƃM£” JVÒûŒóeq`ô~b{¢å_AŠ‘S´qGÉêcðuH¤€8Wà%¢Ñžö}Ùâ+ÅkÀZs“ÔR ï˜4áöØéØ-Êæ…2j >K꺄˜ŒeâñsG´ˆL¡†°Ûæ ϘiÀZE%Ë>;# :[–Û=öQ…¾U,ô`/ îfZ»̤?é¢<•º¬â„ñ#Û£ë•þ¢È…eï­Ö,Ç€ð!`éÑꀦ±ûåqb9± FzºçÄàÕÌüš«ê¼ÖpS” ì*ˆ£Âw]ÄB^ ΢NáàmÂrŽ}‰ò0Øy¡‹`s5Ç{Õ—(ƒ-$^+Ç`öfñ‚VÁ€¤&ŸÁ7Ñ3>)£6˜Ží„sNÂ'd€œ‰§%ŒÑ©‘ÚYÿGÀM#gá¼!( Boé.Ãï@šÐÜvÃ…©ÿGç÷ˆ~¡‰‹àŠ;W}gt\””îµ¥‡2‘¯× ¯þÙï¼Uzí»¿+¬5üx›r›£óPR÷oCm B‡Fߪœ7R›œ#|Ÿ^iÏÜÈäÖD”&-è=g ßûÿgà´.‰µ·ƒðæ÷ Å!½¶Óî·K²Šc문gx¹i´€p»4ˆ=™i{¦±A’§h±LAwÑK×fl°…êòDÛÓFÐ#ý‘⬜SÞ€}™hÑÉ f²üÇ‘Àª5÷IRuH¸KÕs²ßìaíÒ{k—j}ÂX:Î<(¸ ~Šô_…kÔ‘J¾$Ù/Øjo¹ejRzIò ¶=_¡b¥»ušâMØ:ó#‘ŠMµ7ÂP„¾#¡?ÿ«þ­yûYØì¢òDœ a—~ùCå éÇgÓœý¨š9$ý:ö(Dõ§·cEiv!EkÙ"®…1<ćÆg°#Þå."$?[â1›i±…±'‘j9Æ'†^£qòòAÌ4¢×ÂA˜à+dä¤ „Õaªí7è—In¾1©õº?Z$·i´ WÎí"Dß¼Ì1ÈÛ—…Ô²Z‹Œâø³c|>Ø7l›"y²m_EÍèÂQiËf˲TïÖäŒÈ€ë šEÅ›í[2¿¡)Uzii9š%2ß±pàÉÎ'„¦€xBn¾‚ãªH¨ð¥âØßÑ)}k¬Še+rq¾:t¦3á€ïn~$Š ü>í\9;í¥óè ¤ßýRä )° €®'o‘F.z‘˜ñ–&KŽv> \ÙhÍs‘oþš¾À ž„ëÀ)kñ[ÑGÚY­OjQŸnÏ‘«¿‹â¬q®5O‰¼˜ñîUOìÊÛ=Ò¬ò¤Œö:OQ ñ·'éÖ†n„âǾÀu—µ¸!I&ÿR¡…ÆÄ|ž;Ì1Q]K`¤ÿ Þw¶™‰§ëÍíE“Á‚ÍÞ’÷-¹¯¨ž ,0"o b'Ž·Ç™xÿSèw¯?ë(ÿ0è²(O{Ü(°‡:ÿ<+ï¼Xã;ÉîÂÙMΈ²ÙA¢¯±êš¾~t˜!.îCœ>Êr?¤i•ÄA®[©u² Mj'o3qto’÷D»4ÿH/5‹²îÍÿ{ºh§‹þ¡”~P­ùEc-0¾§sKy ›ËiÂär(ͦŸ³I/¦tˆDKpû»‰ÜÀ&/?8öÍ9öQ/§.OE°ûâscì†9^šúTðQšU_ÄLj~‚C#I7W•é´ '6¬xÊhÌþ]Üó2Ë)Ñò64ʃÈHŒ³ofï,Õ4šÄ§ô§9" Ê›HVÆŽ¤xÌ·üËqG„]GÊçü`ò0¶Dnú‰ùz屜ž‚ϳZ Bçj[¤fÞˆÔå¯`Q½ë[ ¶ö˜‡§O; âŠã¨‡‰‡¯oÕt?˜$YêxÀã9ûÍÊ¥àÿ hÀpäÄTc¦ñŒo"IÕ±£ÿxïžé˜q-=Æ"U¢2ýL†ÁÔ±Ï0W20ôZ[ââí+æyê˧'gš… ÁV• L-‡pû¥n_ ´QÞf#5b0ÙFÌ“ý<¦Í”¥½©®Y.íëèyLüjo!´ªÙßß)óø‘³¢¦±É[6R1ÿS| xqŸÍ-Œ*ß·›téí‡úXpð={ Tæ6ÿQvW˜±„ EÜÊX4ÐVÉMýd窘Ö/ûC‡—2[¾ÎoãF¶ÎjdN# ¡‘oiÝ•Ûøñ$ΠWs7¥ãÀºÀà¥]³@Hñ¶€~Äaô»…¸”.M Í"0½Eæb«'1ùigÎm^K )RªÊåèb%‡"qY¯š¿Û«j­j¯–rï.·}3ˆ(d)©Í€øðO)0¼–Xjœ)ÉþÑôÎùƒÊÃÜ•Š#…ÿ ¯úq¸jFô_€û…(ÜrÖÅÊ j‘-á÷ <¸zÛ˜QÊ ckˆÞK9ñÙ¯O¶ wS=>[›| D6O_*šüÃ×a”ð>áÚ8‘—6xºÀu¥/Û²ÍÎUþnûp]Â]j%3ÃG}Ö“ä .eî¦éóš{ÈÍô–ÂGœåSq1ñÎ7Mò‡é†c✓YßÎÐ+a2ó_¶´I?†ËYuÄNOØbÒf.ØV!eÛ’Ü ”|ÌD}èà4«’böã‡ÐÉÇÞ³Ÿ$Å?cú'¾Xñ7h1JÈÛr,ã&º?þ¸q8XÿVVç"]R Î8šx?Œ˜Ä¹8ìâó\sÕ„ð [ôÉÙ:ýòsu¿ª´ŠÉôÒ! q“u«Ò2°PôÙÕá$ý¤á6°Àã(ABø‰bÎpŽÉîL8›‡*!3îUIÝý޽rtLSÚû9ã ÆR <¼¯ëav ñ ÆMºÌPåëöÑe{"&x‚ˆ1 R|Ô9úŠKö›“²áÔlrh¼ìê.͇=‘uVÈöÞn—QQ¹­ë‰ 5›f%2¬¼¦‰ª)m¯Ì üòåRÃ&CËÇ‚}Ëðdä/­9”áIöˆ =] kÉÿh0(Åmh`é?æ[Weº4WCä¿r»ð´†O€øQ'K5|œºx÷t%Coq)÷?Õºë0å‡tHz' B ‘¯ &ïúê4Pठbe0 *ËäêŶC›f}Ígå¨)¡oÔ}9GD¤²…Ñ/ÊáÎÓDÝ…/—øD-qh5‰î)x‰6óTCÈ0šR¹xÕÀT«(ßଛ™°ƒ¸»WS;³b(b"À¹,Hn›6n3ôl!ÐåMm àÒ4ضQu¤¾ðd‚â „­ñ¨¿kLó }3üÇŽS•,E Ð€èTæ_TrÔ†*#;õØ«c>äÇZ |ý"?)Ö”FF•F[m£Ü<åw;F£æeÆÉ‡§;‰H }󺛀ÒG¨PãÂK¬~A;Ä×Çøã4ýJ05A… ~šáoq‚ñ…§’¡EÞ ÍŠ BÈ ÙJØê1¦rT5×ZåÉý[­Â)ªïŸÍ¯ø]EK˜þºÊH<ȲI‹.A„Ú†)Yüë×P쎃í[ÇÙµÉ†Í }¶´g§æ«ž- ¸ÖÁœ*‡o=ÀKŸÂx¿çWw 4×o1€)ü!^xîMñ–RÄë¡óX„–”F¤œ=ÿò¤jãÝG‹\íœÖ˜GiÖ’tºÿT3‚CTÚ¹}h[õ§C¡¶0ñEé³!Þ:“î±Pu»Œu²ÒÖŸ¤.=ã©È s¾=-éðòqLªvré'j{ýõþf¸"qúF8ÀÅ»ö‡¦ß ÞóýÃu$„•ªÙ‰Í P•ä°yÒñ+š^Ì(3_êdpbïœ)ãG)Y?t RÚù9k=à²~Õ ÃÅð÷0r…eð ŒíqßÏ™fâï̹LĉVGÇWEZ#ìÖkŠr´î–ìÌ~¿êâËh0z|4žn‹äï'„ê„c¨Ü%s Fí»w©ëz“"-ÉÖk¹<ÐÍâ΋9œÞJ†´Ji`üÿ;ïÚ|GÀ·™õš¹ õ$¼ÒS=¸×.¹ÕÜì.8SdMÇñ9ÍÚ6pb˜µ,Ÿ«’åW€D±%Ðo ;úÓÔù›Ír0Ö­+Ô]â`Á=dû„àl¥\‘ÈßTžðz°FPüw³·~M¨@5@2’ü[&öyy‚É•ÓÖ{—îWÖ&b>°Åbäîw,çÌþÐ[ò3K=L$¸skVh’BÇôqšŠ@ld,眙‰¾É)1çjJ5CÐ7‹*æ-Ø[@)j3Š“³³¨û[WZ\îaiˆ—Gÿ{ð©HëºÃ'q KSÛ+OóÊq|È_Û%;±Úè®ñ~i§LB,¨4?‚ VÐSFi”*eL*TWøCV°û¡f}n%3x9µ± 0£ ˆA¶¨¬dë°ÕÙa<ÛWvz4°$•@‘MôíÞ-™°ôbœ¹eËóÁEêJÝ4¨T‹0©Œ=â×$ŒÒ ~æ0~32ņ©¬æ#%sÀä«hqâ$Ü1pë¥Pp÷NMS,;dœ.15!\Œ´î0ðQ0N»ž ì0}›ëÚs käZfº8ºö|pÕJˆM€Úäžï:ðÿtà$r„bêfÎ’®Oº¤š¡Í€ãaDsìÒ…çÉëNBñÖ_æ7õYö_êN×¹Óœ;1n,‡‚—~á^Æ,ø Îxéãd=ùä¥r¶ÒhÝ$h}ajŽ&ò)lë!‹ÓôWþ¥Þ®_¦áàÂ/ëLƒRðß›FÙø}R­«GlýµŽhµ‰)¦°}lðÃ[â“n/½³`+ýlõ‰ÊÉÇá.í²GúŠùOȆ¸2óœà{â…¢”2˜wœ3ÑGNpTËœ@`¾Ž¿¯óðñ%•êÞ©ÃÆÛÉk¬ð½ÀÚµ…T¨Ìc†!¥Ç¸^ ?õ6~»/4‡jK7#îÁB‹ðàJ„IL8O) l ˜Þ=m?ŸN?Ñë0V ཥÕÄ;Ð^ÉìaJlâbtß‚Kl½?åIbâßà[æÚÀA„¬ïû‡MÅì¾Ñ)ˆ«4äYàC㆜ØF&-MyÁÇ훲„ãûõlª%zgjÔ µœ]üHô$Ë5#ò£8’ã˜ç‡¦ÉjM%MÎ/{ÚB¢Ýd?˜L¯«Í(ªÛaKkýªÉ¼Mmz?ÜÉCäø€hÖîÓüº¦hºÏ¦žn(zn‘Ó"™H诇ïhA>N-b–¨hõ3!°ûbú¡T[¶¥ã¿Ì‘‚QLOƒÒ¢vÅð €Ð¦‘+G§ ÑìžÍ×r¼YŠª¨3'šPËk” eí–Œ”ÔÇkT{çÏI5î ‹H ßh„*ö+’£Ä íÉDb[vÓ³põ@Pù/_lÔuî ­qy¿ɾaY&%Öxío&#mÖ­e,³aëî|ÅjÛiŸfúË(Po6váµøØŠ¢˜4‡å‚žSvM3ˆïW¶e]áÛ¸>O®GÉ´PëÉdõ­F¦p¿(ôÄbÅK-ûl}w5ùY0/iw¤þÿXmM¿Ù¬ewÉãûñ¯Ñ¸} 3ð%…=eÐÅ|6;Ð2\N¼ ÙŸ´õÈÂÆ´ñTÞgd´/§Â9¦åÇ“•é|)m¶¿f”yÏ3«×>jxuý÷;æÆx×ÏÚR›at´ duÙ:/e…cEbA§üÚ]Ô¢F'ªc³JÝÀ >†ÇU åÆwi<è Y-Ý3)Á*ˆa»¶/˜²¥Ë—EÉ–†—…#Ô£­I·&ë®Ù¯ëðŽ^³FýëFÔc¢U˜lûFMTCüï…[ ©=Í‘½¦y'¬í¨ú~ƒ¶Êa  n™&NrW¾PKì{BØNüßìµ2¬hîc*ÇmWifÞ?oÁoÇÇì¶„ëÐ='k°M(þrU†&–ìôÌ”¿8 ¤] cþ)éhÐA‚ýBª}‚°@ÿ$ÈÏn2XgDŸaiw_ž”êH1}ä—¬ Q †Ú]Ñ‚B:æ%zÏA- ÜO Ž„ /ÁûFŽV î™è“ÁûsJY´_þÀš¨ÇZIYŒÃJÊ0à[Zý±‚Ce­D–MXÝá”·éi¤#î7̔˘mÕíPNÓëªól…†žîùö0ù9é‰<†›+­”¥â µ_/`n¢Š’ ŒµC‹]ae–`y LmçÂa«"ý“=+ͯOl]r <Á2R ÜÅ%Î1ɪ=ózïÝ‹ØVPOóÇP`Ëô,éÄŽ³ Y;- ª{æŠ)MöNiaÇsïPìŒoÿé'U«„îC² wÜe’øÝ1ÝJ4 æÒPªcÚ§èhŒ <CO ezŸÔ¥2sôíX§E8e{*ëþ=ÓôÚö—ý°QÉ H$F”ë°­ ÿÔ‰.Ën+>[J£_[“¬ ·üÞùHS £Òĉç‚vHs‡P0[šDFœ—ñË~l߇Uÿ\sǧœùl~í.yJèn]°p}AÎMFDAÛ˜c{c¬àßX’¯ÃL¸&7U°ZZ}¯.õð™Q"2»Â¥g™à¾°Käåº?ºMÝ™ç†{Ä!8ŒÇ‘Rë;™9„`~5¯yKˆé–ýnÛèÐ~%]†5ý¦—e|U²†màƒž/;Ë ‘ðÜYnÉFK °z³ƒ@µ‘w6&¥~¤ñ‡H#¯Y·Ó푎wžÙ±ô`ØeÚ>ÝvGQ¿6ü¶xñrUS~«<2}[L•ž¼ÛRÍÖM¥T€,G’6ÇO÷ãbÙ¼ÓÖ¬9°U°z¹‘•¥ÌžÐ²Ýá r­º–d/ÉG¤Àj‘r¡ö-šoÀÇêN¦ü’sÏ%FtiؽÆ;Ë>³H¸2Ü“C©Áhv]}<¨±E0:ìy>ƒ° sež!ž«C.kpvºB 7©i.,_¯[7=2+¶åÝdá÷cÇINÙú'ZB“ñ¥Æ‘7ÉB¢.Éõ%oÖ—¸;?PÝ){±‰ó­íÆK nÊoÑ#âqõ¼SÉ2_ ¡Mæõ*ö½,(|d§š#îˆh(ý»™ñ‘!ÔDy$®Íœd¿eDg?"ÁWyÄÚ’6›T#óùª&å wOn¦Íí%œ†ÐL˜gý;V² K@Mij•€›T~ ÔØëñ.¡Ñ£Rê1AW-RÉWæHaÒ*‰«àŸ¤®M4f¡¹ >L‰kÁûœÙðX¥N¥4Í ùˆØD~÷ãÏ"Reû¡™N㔓’]T˜>¨î ΟçÁZƒT#z ·#ÇÃHï§2u‘Ÿ“tn«k“ÇOåÚ¼\«ˆŽ¹¨NˆcáI)/Q~šÊ¼cÿÍ l3öÉXûÈ{aÒ´b.ü–Õ$`»FHò¦9Í¥,¿râCyчę‘ù¹N:yn5æƒPÉ„¨$¯®4D“2ôT“xCÂŽ4]wȆ¯hÜ…`¯4ô¬ Aä ¤A€ã*¿ôNÛ1dÍ cœðÔd8Gö±¿&¡#`Õ tåÞ†/ñÀ¥1#3B¦â/æG=:2Wµ?L:`kõÕŽÞ$_sn{bþÇFLg —¶(›3£ôô£Ž2£ÁÀIsV^ÏÚû "Qöߊ¬SÆÉœiK°xÅ"ʼnä´×‘˜ºFs”ôƒ–UcÒY÷1\ð'ñàÁô|}ä ¯ÉÓ„Z"êÔO‚ú=ÀŠåQAXqsÅ2ÈŒ‡–»£‰Že¯Š`¯˜3v±ïVºü·Êy­„M)„/Ù©­`¶bJÅR€ùçZF| >›x=‹ñ;öÏL™¨„¹JÓYkÐ@‚7*Õ?Ä§ŽžâÊûêƒ<¬hûËÚ»ò°W;ðÜõ'«DÛÉNdÆSaÿ7íËN¨+A­ARR‘ÊùëðþZI©ï¢ÈBÑ "ÚÍí.19‹ø¨‚3™Aù ¿‹Ø²¼õÀrIÓ•_Ö˜Ëb¾„¿u”ñÙÕ5Iðdïñ"}ÆéÔ‹².Ï8Ÿ©‚9¯ºï³[N+äÎ' ñ™ßM¡J^WÂN >Çp@fÚÚHÏÙ…¿gËŠíA4¢ ¯D‘fõSŽÂ3> üY³Er0mßàŠâé-"íŠì’DÇäØÇÞNÎ1I5×Ùcò4Zßž}“I]¢ñ'l客ÿ©“Z+¹g{OH;—>=©ì^Œ`â®Ö©ý°+ øÁ0Џ`eâ.­»%nÿbþçî5 ~Tïf(cÞ«Ò¤—Dd‰Zp°Ò$µT•nè š_˜ÄVynÈa¡ØOJÏt?IÕn*Oöâø'È>’xl8ŒŒC¡î{”ÎÖ4:>ž˜„ë‘3·-šÿsïJ¥•/åmlÄ|Ánk³Ö¿Â«©­§ 8 ¼?Œoõi8±êa³‰4Žy6êÃ,Ucg£ÀO _K˜Ð¬ñä"H4·ªOí[F¸Š¬$E8{•HU“æiƒƒ¦Ò¦ÈÈþWQ_â6KAjp¡bSŒ0'D(6ÿqQcÿ_þ¥^£ö`A³Î&ÍŠ¦Ó)šÃ¤kME8Þ.~¡9E!1ѱ_ÿ`‘ŽN–“€qñ±xš “ØJ„«^]ƉÝk§ËÝý4Î}¢Îh©ÑœCcŽ'e޹óK8ÐਗUrg¤I´o‘™ÅŒ1{òë‚Æ+ÌcÀKõb·6»ÿ‡Bp”œÅЖœó•F9qI÷Î4%&ª¸EíY>GA ­‰1ö~Ôjì*;OõQÁ&àéÏJ‰¸ú²!l·Hÿz‡\Ñ©_ýq»"ùbª)y5vCµü=úÅ|À¦·Ð•æ0.saàdŽë’žRß‹umŒË8é¦cÍküá܇=iJ[±-77‚MI!ûê2œæ¼,ìí8üª¨Ò¶Œ„`œý£Ø=¸ÅŠœŠZ© Q§MæËØ@Œœ¼)ªs8‹”•û 5’¯ûrWs±l®(Hí3„ž(ï‘°²,Á*Í4–_¥Gõ,Ó¡öKܪiÏáo ø÷:®.“ÿ"~Y<Ìžær1”!DÁ(~Zêlåî$(38n’Ö FÞ€úôŽðü¿¼ð0 ‡ÖŒ€f‘+²©­3@ó¦[-ûÉxwŸDoÉÝVñÀŽg€¥AªÔuÌüvïYŸ)-­×Lœ­|Ý„–ÍYâg™„t7uÌø‹‰ó6ª¿g”†¾¶ë?IŒ1ÀÆ«€¥4Šåáo5Àè)êàLå49¿#ãf/ÝsùeðÚ_¤ù/5Î0Â+WÿI¾ç΀lü<==Ì.u¿Üîï"®*œÙçýwÄ71”Ëât”5½éøþÈŒX¾]±¶n"÷·’1øéðÇmÉŸ‚±Rç ëáÖ·‰³r™oGOÁÿTcrâ ÀצkËÚÞ¾)1Ì©RÆx5»óë «†ûø]u&>¸&Xk¬,ë÷ƒ˜ý¦¡‹;ÀŠën«ðž5*Ä| hìa/A3‡Qà&úñŽU› zcÊdÂxp>< L•(†™ÖÔ´»,«ks$‚AOešnØ!ë}Ãcp{–M¿ÄèÄî$¢[.Vü‡üÚ?~œýç~ÍŽ*õÊgGS Þo‡MÍœ->8i˜ª*ÝÅÕ*ÏþÈ% ÅSœ¨Uxæ{õßãN0²ƒ*…'üÆÞÌ~-sŒX ¸³¦ÐÛ›ñsåU±[)zÛÌÍÌ®øÜ …‰ëÊȇGoá÷Yh†‹A‘ònÕש#0K(LÔôHÕêð‹vEBñQæÌ[ÔX[3Ÿ1怮™5ÎÍAŽfƒk§–,çÅ/«ƒV†ê pÌÉ«³³ÁÆ%x#¾‚ä?*^øKI:ÜÚ”+. z𥼠7TÊû]mаÆëçù³óÇñZ·ã›çAkE¥oÄ¥ñ¥gµÑÆ2ç˜ø¯Ê=§aƒ\ž>#›¾¸é¶üÁˆ`qŒÉdA篷L´+Ðïï¢k¾U½w¯ßpîÉ6-—æFrƒÑ¸y¶ø¿?Btª(·ˆ¨’ õ/9ébê‘…ÆúHÉN/8Û„ƒ=$D¸Å°÷ ¿èJLŒ“½ðõ]q ¯ÆÊËjýÊvÂõô4—ڈΔ™ŒÆ·9|Ž„À·¡ ÀÉjmï#2í*¶3¼þ]}°Ë„G¬Z÷RvÄoÀýLŸ<ÓÓ; ¿}®ì¤„tÞKÄ߸^¤†â¼Û9•»Ö5 4G¶™ArQ! ×øÌÙl‰¡7V=Åâ·iQÊól…ß ,f{êÇ̉vb)¥¤@‰p¶!ZZF‚†r˜&ý—!.Ô,lÍüè'ƒwñ»fQ‚ÙùÓk±/ßµÆÑî$Ö¡£ý0Ö¬v*gL†Ä"†Ç“ siý@‚1A¯cbUI? yjT©\&YI±£Ò"k Ðu±låE»[>¢µ£HLÁ¶øõ´:ô¶6õÜ{ßÜÁ$ù¤Kv¼Øö¯VtS_«Î”Ë=Uäêæ…Æyyëô´ÙJjd²|Ø`H¦åuA©¢Ä 8Θ*¨X§'5&ÞŒå) xšŽÖ '+¼cªL}#™$!äû9­2Œ[YŒÔl%g3)nñ:=[ £``¡H– $f©@´AMXc+Dz2ÃÐ5÷806ˆðúT h Á#²%yvʤ*d§¿Z£ >]ÇÁú¢LÑ¥¢}5]UeeÁ“÷ hwõƒ(¿Æ­$ùߣ9Äþ@±Îh]k±hаÀúXZ†µ:ëûj” uæ¹lƒÔ0Dr= c˜¼ºl©lHÆÈœÌߦÑ) ”%9ôófبX$ægþìŽê$ ]N$†×l aµ3|ÆyÌ…â´2%u46ÆÄ^޲mîÎÑ?3sœPÔRA²Ð6øå¶ û&Ï=rèÔ®ëq*ŽùC¦Ç”¯@„£/§@W&FyQ9Ó|ÑB™ÍîÆ $O)^Óp^·þgìåï~ .™Gýà°^vÓ&Ôkëqé/h‰)+š„4=4XâÃ\@ÒE~¡Þ¾“aÐp;u4Bë"¯W`³w¥úËÂ6H*\<›Óú Šù›Ç,;z†|¥-ÆÈê Cˆ$a‹÷Ç|“Šgá‡Î©#ƒßS/aÍÈÆì«“·0[_Xôqà×NRŠšô÷½nZæˆÏq÷hƒéÝÕ.sŽâUуÃêy»ŒóCuG°ó'5w…3`©&|ºa  ï çÊ6¬jûϰŸ³êNHvà…l¾¡Ð "·*n£ ÕKFN[²SÞ>[‡2x“àá¨qÍš}©6ìæËê›J ±3ðYRì='P\ •õŒ™™©ÎtN˜õ誕:Ý];Æ•SÛ/H‚Öh[„ÏR_‘cG`-´þƒ0—ߌñËž£@ÇæOgwȼ·3o’!¼»æ¿šdˆXÏqß,¹Â“1‰»Þ2ªåu‹ÛonÔynõ$8ÕKe $n³o~5qØY\€é§X·9.(ÊG›»Ñ „t­e¸]ÃJÒüö/?oîí}A¦jâÅñ+9'÷b5¥àWÔ¤!ß·5äA+Fýw×'Ôé¯v ›¼”Ik¹™:P]ºT´`f©·i}ZCZ­´G{¶'‰ š” ~d@ƒ¡zMÁuçDüSM ñas›2Å04;}W‚¼´€¥5þØÂ’'ßGÝÞ5`üN@¸|I3›3ƒxª¦‚ÿi+@eáˆiדgàLM!0/èjr¹œøÀ˜€ª-z¶bñÓ‹'¾ ±»‘ƒÏ—;  yªÁVÀ>+2CÉýšÈtBœR¸F“&ëÙ½d§œ¹¬Vºê û·8qÀ¡ÏíÅ 'ù÷OPR¹6j*eÝÂT™aÊ5(Ve­h®í;h\U´-8+¡¤íˆÔ¥h ®iÝ8GˆP­ºŒ˜°$8çz—vˆxQ0e—’båCÜñŽ‚æ‰ +qÍÚÓªðYî’Yéûú‰\Èø[“¦6v^ó]VG TW)$ …€¦â®Å bÑ“kÝ›i,·ÍNh‘®Eg«&£h$ýº?ÁqqG¿Î§OΙ©kŸ‹ŸM–Ió pSvú¶xt0£W'scÂ\O €ƒ{püb€Ó3f@Ç$Ål9äÄ(lƒÃÕF‚©¢ Úig‘>ø°…òòhÒòßwÔjüŠ1¼V\l˶Jr0ânn°}µéѨË¥^z±Ãƒ=p¦sØM|á÷ðªZa¨› Z±üÀ^>Zºô8³2Z3r»ÏQøoä…g¬Ô0/D«M·xšwÿAWx÷ê˜ÿfyJ!¡2£b”ÿ~¾"î—§VR¯|»2× 0zÓb°…¡ ‚õAßwˬIõož§êy®mc9˜È뫼W~±„w Öã•ð¯ÆìeÜóbí¬ÄŽƒ«3‡Ð…$ s;r¹Øh‡i9ä³Y·¥¥Q €¥ÃG£ï¼Å?mÀÕ¯ê…ꇣºÀ®P?c|Ì^¢ß3Áõ«,jhV¸:ÁYö6,¡Ò/¶›Û<é K{uÔ¦ÀK nü|1=YÏB9gæ"3¿¿mlò:ºQPp}¼ Z´åd*‰·/êŽNÔ@WÒ¢£' l‘è¸ß)= :·ŽåìïÃó.¿ÒN×âAó¢ûs/BàÅÏ´Ñv'zË(IŒV ÐÎéû¯m˜ÃB Óbëµ½Gð=Ç¢‹¿ÏHÝ\Ybˆ§H‰t tJµM_# NPæ²L@nU¦vfœí}nÓctîàN()Ã/K­E\ÉfK+;Ñ}–²ÖðoKÍô”1vÍs¼`¨ÏŸþOa~u5„P5µ¦kR&Ñ÷mDy)<1߉ª}n©ÉxŽHß­cº_»ž=örw^-o·LŠóÀæ…m˜¤æ;oõËç_WÔÆ„ÌX–ŠV‡Õ„Ú}¤ŽCÜ;OÌè’'Ys¼Êß w§ ïc:÷©u{7fx¿x)¬k.ªðrÑsÌçñ¥EÐ÷ ŸIVܱ*üüà“B|Cðé<"«'†¹ÒŸsð&@~:8<¦Gs0BêTí$e*‰Ÿ‡F À¢Æ½!ÚîËVr6cÖMÕ8ÏÚ î×¾™§ÍK„2yfÏXP8ÕlV˜ã´n—O´s ?Øâ‚–.ë<$ìV²¶Íº»‘ç¡kcÉnJ_î=†M™ •ªêè~ÜÚFõ7,Œ ÅÎOyzÿUuÂݽ6Žoȶpœ2@¹Âaï™ÔÊà`îºc8ÿ`¹é®ÊÒ†ÙóLc‚1_ Ü÷üÕ·AëÒЂܿʩ:×7œW©? Hô“4YÐÉC3§—7‚A/M=ú6Ö?±ªtÔ´TíÞgÉv*¹@jlÊ:«-jPs©ð[-uŽÓƒ}åàq—4Ô2ŸŸ#—+£å´>4[-QW†Véyáè ´LIªƒHXÍ6íp¿‚6\0›K‹KAŽ·6ÀÍ`¢ßz­ZÏ•ÎÁU;Ö²ûhÓÅJÞ;›P*´ëw²†šÙ!é/ &’ªà’î¨ÃÕ% wžnQýç3›©÷°ÁpUÉØ# ˆZÓ¡5ü]—Öi;‰ÇG%iªÜsa£ïfȸ|û¼CÍv=~§Þ€‡¤ƒ²ò ÊB%1§C¨ÈÛžéHDóWÞͨ¸c*¤¨[gNp#ˤ­«D ØØ¿ñáâ{>jÓØüêr ÞÜ ±×|f‡}.oÒNÖä5£vDdu(Y§…ƒýµV©×­œçÁ¾i§±nByB1mз0Kàxí…}U±h)™a-þÍ@<ôÕl¿¶ßaø×(yE“(ã‘>ÖDro–ÞkQJhíòǺ’l:nk¾¿Â:mõ,"–Ñö¬Ó} ª)óöЍûñ›Wì˜G‰á©¼–ëèe¾e¡nüðZù³†%/híŒ]H “‚ßÎfÏ4™k¸üKÞ|rßxM,¬?t~<éU¨™*tøe~b·G3IºëÀÎާ¡Ñ±òL§œ%„¼dè£àjL 0Dt&äF(½Ž6J:/÷`; õ„ÃîÅå­iøh‡‡Ëù&«õ…má=;¯ÊǼž“R—œÛßdzµòVÏq5ù3 è!D»Íw? ¯T“™¼ÈÕy` lÿ+¯£ÿCIªÿuâ= t0 ߨ†“am­‚]´r‚«1i™&×¹´Àä0´nÙðÏa•f@ýîM!/yoc*X$FMaΕ®ì]A‚.3MIljµ03?/Ùø8•Â6#Ä{WèVÇܽs‚kBeäjn&Îòº»ÃE@×¥©È~sƒ‘åÍÈ8L²Ñsª¶ö×2¬P¯…}Ýý»’s9ZÔè“;lûDN„8~s(rÈo)®1÷e‘4›Œ\ý1äÇ6¥X™ºzÐfs’ó}/þ7ÕÉ_”¡3b7ó\”&¡Š²”ZÂß»ã{çš="*ṙ?}ôŠ>—"¾F¬^?{Ñô 7ª~9eо…o³B‡ãë‰wâEnÅAEª!DÉõ Ð9q¿Êü"Z*¾f>Žo µ¶ÀÒxÛ–s`F¥;‚ŠmFFqÀ¦=”ѶW¿Ë@!7%¹|¥Œ¤?]:ë!üN(8=Á]a"ø†¯·6ä›ìKxj•âxÉ%× DÛ¼Ìqëp_ ’ȧf’žs†3ÍÛ8tKî>{“‰Ý‰{òtn{à§J¶«yT‘õË0ë»·Wn_ÝØ•½$H33M¥ÕCúò-?qò. ”ûãL_'¬Å…Ðmë¼É!‹ (Î]Õ£Õ%$@Ó’05Ò{tgèÜîq%²?ójm,IДíû138ú J UÁÑ8àkýR~·¸¸DØÝmשëÑh`Ùß”§¥ƒ <½,^döÈ@y •eÚ8~lÍ&íä.ºK‘©‰ƒÑž9…hXQ]õ{ó]¯ìÍ–P€¨Z\gWƒ(—|îFçÈ4åíë?7–C"ÈGм=µZ˜oû@Î4N’ïâ[%øbâà8a[tǶê…À jÈÌÃų’¨n¢öŽ›Ò‡Âˆ•zL¦ýã%Q‰§AdÖÜÈ(>¹LôéÃEŸ””’“²Ÿ³¾ögÝç#àê¾¥X^Íx)óIáb™²˜ÍÒbGöÛñB4»*`£ÆCË/±$A c`~Iƒ<åhi ¬Öî¥ò ‡ò N®¾ƒMÐ6"Å^,¡àh ©ÔÏ”,µtð;ØJ7Z-Ä<›¨Te®úzQ¼ÉÜŠµ²rJ ͤzìqÏ”9¬b,AîÉøT̆’£ÊB7Fž¸¬aIÔ°H¦fCÈáè.‹`$q¨YHýF@ûM3ª¡ù” X¡¯ä­›‰HèívWûó¾NÝÁª¦&ÆÞ%ò3YáÁÈøEµ»6/-;‘ü½$°5éwÆÁóÏ^Óäí!öÔ?C­ÊÇ &zÎåškð®ÃÅåÒ‹Ô&*½Ê…—hÿ×±Ÿ7^SKH·MŽÀ3‘c‹S¦Êå)†a›+§S\zß«ECÑBZŽæs¥f{fy¹XkJòܱº ±ìx$Û×÷~I£”èɈà"‰´©¯‹AétkCJa_xâWüà`x9î‹·…Ó&P¾+ùHSÔËŸ f®ðÒ˜VQç€à:#÷»gñþ-ªhN™ Y8â„b}ËddÅãAâ qÎ1U€£W±…ÍÀ£–ºtqáÒՋ×¼—æ %`æ²Y p'«@k@fåj²¥!ºµR+š,2 :n š%Zs¸™XÝÄ×—ƒoÛœ2ï"„ ÿ"rŸ‘43[ÃC’otCÅ à}ܼ—°@# ‘ß³âºõaƒ•Œ é%h¿FðêÈWó€®ZŠm!..ܵ˜˜åy»©8va·]L‰ùLmÊŒž!6í$Ri i¿:®¥‰Õׂ‰Ã £±ä›Ë)‡¯¿Yp’\5 ÄŠWÓiPì‡í×J ¬à5}!]ß>bBE„½oÖ»² Sìk³BX³4‚,ÒmÔ“CõÖÔZaSÑ"rc]?Ùwqòåðzç¬`¥ÌKÌ Åp‘ÍpYœÅjOÛIß< h‘ðþµdGF-úé8`ú&)éŠ4£ŒœÑ—ÄŸ÷)k,˜î ›´+#éw‹¯áÊ3ÛÙ¾P¡3tAµŽ˜Ö팭gàL “ à„3¼€$s€Òvº‘aK£^üš+61ÕÉÊü… ÃŽŽQ<+Z«4yvÄ6®/øÈBDlÊ]âp/Øe'þT[ôAKÿPˆj’K¼Ì¹uöÄê ÕJ7×|Ø"Ô_¦íŸHS•YftmewD³i£+QîƒØ§6z("ØE{Ì%×Ï-ó† Î`Š$h&òÍ<“ƒ‘P¯rì;o¨déKÁ¾n}x7#qŽ*ûPúÕ˜%x¢ Wr+!àªÇ¸á-%>\ö[ßë{ýnœÐDõÑ™0:^~Ra>B¬õl*yƒU…ÄPÿ‡%ž‚üç©oä½³¾øë1Òmýw{_­4î¯R±×ýmó¢Y –E ÂŒñH/Ö^*ÙÄþ¶ð|ˆ’ß'Êõ A(J8Äg Ÿd¾™(VsˆDb¦±®9Jíñ”å,¤ÉmCߨc¥ž7<2ÉG¿8ç}AJþTŽ,Ov^J±­Ñ…$ÏúÖ9" §yΣÒ©%X‚ó<‡cóá- ›Ï3c(À`7C6'ÞÍ7å”'«¯XF)w|6"€Íõñ•¥ ´ök¹ÂúcµŒo}ôB_PÔ`ÅœvÖÍ ÚiñÆ6òuí¤þߌö¦€ Ú u=<δ½½’¤lZTSÞzÔÑ_]Ù* KymW˜6ñÂ"ô\“4<4ÙÇu‹K.^‡Æ²Tô9&–¼½ÉÝaë¤G0QДòw$®)8[†ÿ;+cQ~sñ&&/¿d^˶áè'x° ‚ö|OúIÂP}äÓÍ;Z$¬Ü§ï?si°á£il1cÒ!°¯ÓÁ^&¾ù;ï¬ "ƒÏIÉ]G0Í%齕#ÞfŠp üOlïÿyþšoGºÊÐg¥¢B¼eýR×åÌ™ýyÆ ³r^0å¿Üÿ’Öôe™ ©;‰µ¨Ò†©Î;cÌø¥¤»ŽàÀ?·¼ÝGÌ,øÙ.ölÜK®ˆžïNÌc\{·Ôíg@å}JÀS …±,¹ë9ù} eŒ’+=Îg¯µ lzÕhóNãçZò]‹G;6 ª²Zt™_•è酆ѿQñ(l2|KÕÏC{M@@ ‚Œ(=?ïâð_=œG¹âYúsždWˆ`жE©úˆu4ƒ»­ÍÍý‡¼¹‰oöZŠgA8°áîf›xÎm´ÍDNtÍz¢…RäcÃ!ÓUöÐdÃ5f‹®¯0ÿMZš'$û€Ç<7OVq;ÄÖˆ#iNjÒ_åFX'¦¢ž€Ôb¡Ÿ¥=t `mÛ F:Þ¬4%§„é÷t±ôOðùˆ©‘qzÑ84Yb!:ƒˆˆš+Ø 90@¯Âh¡Cªàþ†¶¥ì ¤à#K„=Q 0 8·ßZ&@s-ÉœŽ6OfaMþ…2’ÚüQø†zI.5šŠéB%ùRÓC;roDA>fùß>£F«_s¬¶„¼ƒFw²ºˆÊ˜Êà?¾aŸG®[¤ínŒSÈé¶2ÆçŸü/&ö¨`?¢ ‚^Ñ\tH3&ê–}ùcÇ{×®Ztp½•†ˆK²žVÏÏÌùÀÿY<™rPû ÃÉgaäÔ¿8`vnð—Ï».²Š@Ò=À]^w!™ßÀñ‘ÆÒ‚{7qì8‰¥ª9ÌØe¬‘8©ÝÐ`O(6 ªêªã·ÑÇäÕû-å…=—a $¯=º°bus0¢wÉNG¥•ˆ§Æ½Ò;Gž¡væ·BËë©5~Çï=Õ/ ¢³´ç~zYp3è’P»â)«òîò{.âw×…8Ë)KÛOqwí—˜ &Ô] /-‘ã›cX –ÜŸäôæ÷’íäœNCëÞ$=0GVp% CS§p°Ÿ/øc²dÖYýbqb‚uI-°Ús겄¿ ØJá€røäU"C é¯'S=^ÍæÛÚPlÍž´Õf™üÿbV¥þœœõ@ñçIÇV7 ² ±GÖ’?ðŠZ¬ÇŤ_Ž •ÄÊ_¿¹þöó'Õ'-"+ó_¤²d€NoÂÿ ÃhRLÿü>õˇ’^íz@¶­ÓÃØÞ¿VÝÏ9çí©°N9¹×­s²-Ö.bˆìyý"GY¿hþ3‚úZ6ó)8¥å$\bh=J¡Üõµ…=ÀˆŒÛžíÙeD©TÉŸþ8×(C5vHx1ÅI@ñe­·J 0‘üÉia¡íùÇ´]Δh³>CEÄÓ FèÏœˆöqÁ’ õ*'åLv fÖË¥æÆŸÉ£ÎW“…)‘XMqï£=F˜ˆ¶©í|%«urfõË6ž{^×JÓgK †–kK53°ÙÍ;¢Ä(‘ñ ‹ÿŠIûë§tòMHY@ZmM'v‘¼Í z˜Ó$ümÁñHd%&MÜŠ†>Å'¶ï&9B&KÊEÕùÒ;@ˆY}xÿ5­ò˜áؘ§˜®•àOUé'8ùŸ’{ ‡°…³¡Ü,ï]Rþxúþ?Ô$%²7&¶hË®ÈH(¦0Ñ}±töã*Äháðö̶Z ÒÉ{>y–zq}ßo=šós«ûšŸð¤8„ÅÒ{Ó›¿~¼0{}ÑÝ¿í7 çcüfŒæ†ÐŽÕY~¬EPxÇ5÷ðwBµ˜ž4ôÜÈ 1Á kKÜá #¢žÙöÙðŒ8î³TÛ†}áš{J¨kNDL£õÓ 5¥¸!—Q7¨û÷ö°>è¾DÜ™óÄtüXX`.#·SOÕgË ™Ê„­¾f|¥‹Ui\¼%ߦʙ!ãt';~f´Ü8Ée$¿w¦Öá$ÄàõJѽè÷ûNê§ë¥Ô+¼÷ÛM<ÉsÓŽçˆw²ª§¢–ÝÕUXM ¥t»ó¿qã&â-qãùB¥\ûk ÀìÎÙ`aÐ:²n í,‘*Ç3+Ö¡¹Áxr|©!kö~ÚFZ^sÎñh óPù6 Èf¡Sû·ßœK"XHС౺•ü2z›M òÞkøèl 6¢H\O²å²|­:Œˆ6x,€©OO'éֲؼZ^÷šØ[œû Í¥Î{>e#«"‘k×ñ(ßZYÈn2‚n€ÃW·§5ô}q×,û9f]‡Â UqæfŸI«°øùlÔ’š®cò,®¶+1¬Šú9"G"k#~Ó~ück·ÅœE}/ÒX-bpàâºØ+Ý -xÄÆ¢§˜ï ûêgodº}ïº\-®ÑQNj «ÆÚ;T”IÈo¬­E‹¸/Še–²×ôÙ=°­Ù ¯ò–9p‹ÖÇÚ´fR/4²@ëbpÕU6#­=vÂïnÕ[þ¾ÐÙ„0I© ÿ‹ nÝoºÈËꬫ\/”Ü„—u²Ÿci©¤T¾Tnw .Û˜zàö…ÒÖ Í€ÔØüùꇻ„2bÝÍÄø^ýq3'A'e¹…ø/íïä»j¾bTÌ;àÿzÛ#ß» ¥²I.ˆ|")ºØ½C+—-¥Ÿ‹C`G=¾ÉÁ` RË}y‚ȹ†1,äˆÑéÖIÓaæD±o;ŠÚÜI0q"„S‚ $¾YØÐÈ%4Ñ%ºãÚnàbYýr.mƒkÄ9š(©«’×d‡9ÅÄñe«gpZuæ¸k\7'{?<6VªðT©-ú EVî+ ùûÍ( ­äÐôàžÀ¬ºÊ¹ãKF<á£ìèú˜»áß)X=ƒÌ«3ÑDrÄ< ÊÁÝ Ç1Æh4¶:Y;‹Ô1‡¬t‚=àû]ãDZcfHý¶høa–‘ÿT3W'A”>Ö.sk8uO<ÖS¯]òÏO <ºó‘ ‚l¯ÛÇv˜š¨Dìaåreýˆx€±-M­¥¥ 4Æ¿ÿCÑÉm}Ð , Ü9üôdMHl»¥ãÖ“4O–ý’--v- ÞÃW“@¤ÆD”»8éë®nÞh0-dj¹–òÜ{ò:ƒ­¹kVþ™F|îçoñ`dÔè+'s¯ut÷ÙU8}!œPV}„ߨºt¡ž×è3j`¤D? Ó¿XSc¡!¾:d^Û“ªs’$Å6}ø[tC,’¾Í™òz QbŒä¤Ñ‰ýž¹ü*© ¼ØŸUàâÄÀ)Hâ7y³ô˜úTØ<ÓØ‘„îÆ;R…—ÍèÁžGõ‚c_<>n­œ)èÒ´MB‹/'à*R¶>L“ÜJýDg!Šz-ÚŠýܯ£:ó­™4ÈSì‚6k¯þÕ‘ÍÌd‡Æ,f”ÿYöh8‡#˜Í{ãüuh ‚ŠZGõ¾¶d|à: Y>õ…X)|Ø6AUy9íX(`¼ísv Î ¸FØÂ hó䆹ëÏ ¬PÏ/ã,BͰùuEZ[)°øP»ê°½1*Œ¦ÅÔögÚÇÄ–,×°8ò1ÄÌ8'T™!ó  pí#ćۿË`º4£Ç’Ók×ÉÊ¿éD¤¹æ†ˆ4™™™ð‘C‹!RÄ‘YõçQgr,&òo6ûtBXñûÚoúÞÇ·R9Õy‡Þ´OäœæßˆÀ&zÏ49=,F*?ð¾k£~>CXï}gˆOKÜÕáƒ=É’Ej“~ØÌÒ[Od=ÓÀhŠÓ$ÐØ}êûlf•x+v„n7†ýÐáCˆ}È£ð¾¬Iñ–j›·­‰àæùt·AÛl?¿åñž3lˆN„Ýõ¤Ð\»V-z. À%ΜþIY؃(±7ì«… dânÜ?"Åz¤¶âp«¬¾7©¯S[§¯ØÕ†¶õÄIïÅ|ý“îbpeYÞ~‰„¬z]1•ÿ'³/Ì|JO±}ÖÕñæfRÀb+¹ »áĤÒ'Õî†ñ-ÀCœB‰€´  H)•Ô<]~ÅÄcšàºjÀ•^œL2û·Å#Ô¸fÿCD¤–:+{¦È|YjÂ"½í2¹:¼x‘µ9rúÆ£åÉ€Ïîj~³kô\+ ’:dr ¢ó’¥ Bå~s±,BÄsØŽ>Ø'ì F:Ïð%õ¶Ë¦IU‡)í…Š¼Ž_Ôè_Œ1?"XIú£”­¨ìƵñ‘RWÓséwlr’FV(Ð[¯ÙcÞSâ¼›&6xDI¨‹Ì†D!ÒC4{ IÞÕn+;[ÚÌß**Q¥QmeãoMˆ3Qà> xi±ƒêeÃó"–×’îßs©ßPí´%¼Zôñ„a¯Z»k ú¶&Ï·ÿU© ¦uKè”ÃúMâzð-€È-,6©©ï#aÚס«Ú AxÖ ¾ ©sýbà—µð¡ØV¯és‹X”5†%‡5سnÿB휵c,5"¡ŒWËÒEnØ xŒõï§àOby<ÅO“chõ8ÓFÞrmÿ/–Œ§'r:1÷×ÿ|ÂtïÜšX/˜ÑÚ~RëùË›€È]”êé¾´bÉŒy?ëG¸Ý(ä $|á«ôÏ7§³Å¹ÀªC¶9 …|?"þ¶ÁJ–9<ÿú—®¿¢b±4÷Hs‡²©JÅ}°|°×ðY¨äãøqwoFI_œé¿¿‰ëƒuö0V¦‚@2£4ÃB_óàwŒ½®[yFCN×ññ¯(;W–i™åß¹0…ÓRú:Ãf‹~y¾‹ˆ¶ÑõÖHØd’{äÃ+Ý@-xXžÌ ø MKT7ûÇ8e÷M–Yï|LEÚ †ÜþoVVðŸd.Òêp.TZâªÎZÎþKG¸ï«8ŠýÝô´Ý‘ÍåœÜu]¯mé§øè]Bߦ:…éôƧ‹»"äLMQÇÔ,æ¼S&e5WJ^À”Ø!©µœH äݽ)’ØõÌéfÁ´š`Uh!ôÂiª ïcòÓIßF€iõøižºË+Ê8o¨ðzW6­—­ú Éí2Eœ×·ÝÞ%Ÿ?Ç©>DÕSùæxndÍŸõ`–s­á¤,zKöå{1[{nƒ©ÎñGM@ÍŒ$4ó®¿ûhZT×…ø â¥×{]v,”­"¢ŽŒ‰¬3C­Æ-P€ô6Ã=ûÙ’eÉ.gÀìMèLFÆÏ&”@§Ç)ÄtT¹äí€ÑrÜa6йdö˜VPñUH"°{˜GåÁ2ö<ýÁG߯¤W©ªº·9ÍÜâ»+åxï‹ wŽ†Ç¦WU ßOd”`© ì¥9ɹpr’'xWŠ8ûKÛBê.’Ìì«G.éËìHWôG9fb mÞQT¸ ¹ÛjFù;Ío4ÿ'kdw©ú·z «(Ó­È^"×?®ŸIõ[°¼­ï˨畼aUŸ9Åø4­·Aäy ŠWi9ˆpˆ¡« ºÓKÉ£‰Óµ @5¡vÌw™ß/ÖQh}z«¢+sô¾z‚)–áQ› Qv/'¤3 öT\ØZ ˆá©¤ÿdЇ>ý*$ŽÖ }`„$¶q‚)6ên^øwZÛN޳d¡Wo6NŸ¹†W°eµkÚ¿IÆÕ½©2gGß–€JÏg 7)Vj©³úí !ÓßNTîB_Äû¨Q§ÓÐjk³eÝOœFï®ÁbO£w®bÓù&ɇ`¸E¼ lePÓd\¶f¸<kÀ$Yr|_k¦fÉÛ"?Û¢ Ⲹv00öxÚ$ ÙLð$GŠ˜óÁ¾@‡”h}Ðn¸"Á±˜‡U›.RÄó_…)ÍüH°]Šd1ºùuŸ<^]¶äkò­kŠ;‘)òÌmµyXðø†$øTh™3djfè/ª=~ôé_¿”] Âz€€× À…%ïûJ>.PÎO ˆ:KÁÿ'KH†brïÑ<ªhõj]øüd -–ü ÖA8½kBâj›&Ræúbª¡z²ªÐ::ÆŠT1 ]‚ù ÇÆÏÑlܦNÓ¤Î×T?uÙwWdÞÖ»XspnɈµ#óÊ>åýmã„lŽ{÷‘ ¼ÌUNÄó¾ZXèv”=éá€5ôåå~”ò“áø"n¯™Æ7¿Ý¶¯ Ž¡®AdX€N‹zè<ì\míÓÉæ ÂP7öF‰ì,çPTïÊ2´q´Þ³p”ó®¦\Ñ¡(TáÙƒ->OI×NúXóéøæ…ùÆ!öblÞrþã̉R†fõdÖ™Þ}>ùí¤Ñå+­õQr*Ë$6ó(x{¹Uo˜¦¶ìÎú ÿvÀþh¾åà2òx,àÙ¶L/LOí)F=£{cYâøO·Àz¢uõm†cumºÂerµ{à0XãÉ—.!Òµ4zOÆùS'V”. tÜM©ly}æiK+ïaJ™M ×èu ñŽï~›š)S…ZZ3ªRJVRí\Å1WÔY½b»Ðï?¨¶îôbl]”©H亳…ËXRn‰ÀÆK ñ¸í¯ŒÀ°¼ºÐëœÇ„kÎCΊ#lóϤ.eìcʵò%æ>Šn%ÆL×øçá*¼Dê2;ûÁTV[HÏ ëCª_¤ÀŠhk¸á>ñÎÁy•žW-¿""…1q¤²Qëwqáªôø ÎÖäVqðiÔxö*éZ4;hèã3½æbŸx(zî5Î]ËíT,Õ¼.m>l$mа®"[¢D&¸¬àZ–ý/É¿*‰eZÏ)b ô8‹þ)ÃØˆ·-‹éø¦_K9 \0ÑP ¢ Ym•:“QÓ Ro,5dèú7rèU;6õŸ#ààþùŽjÝÿ]PÌuN|ãüÆ eœÆ ¶§yMQ’¿\<'D¤À€_¤rßN1µY_&°ƒ+rŸ•j3±Eg&lM<qŒ®Hõ³1¿t€îÅJêå–pt]‚˜¼·Û’?v¸v4rŽ0†¨~Œm÷îŒÝ ê‹kÃò[¤&°Û›s. Öhôiûج%÷©>;&{ÜÀÈ/*ŒA=b#‰ý±…£ô•hûgФHOûMÂ,¦^c‡w•þZpx¹ÔÂÞ6P"¯Ôû<•< 'V!yØDb8År'ÖøS9QXƒ —6áfé‹™_>Ðnü3£Ÿ¯@^ë§Ôò”×Ê"„È”‘°¯/Ôõ—KçûwäóË_÷·irž%atBK,VE?P0ƒ÷uROä3¤GBo_9Ë—X%RI¿5ß¹#2òPΗÓË Æ»€7ù•\·s¿ o¨fžúÈSÒåž=£³V$óá@jn:À‘­ó¢ÙÆëù.Ÿo‰IYqÛ¦~¹¥n”²ãéarI}o8ñb˜¼”Íîåp’7 a,ίŠ+_M¬ŒE÷à'°?ü‘ݦBRt÷ÇpŽTŒ?\˜¹&e€•­Ioc¥<1³ý)æšó'‹¾êŹ嶬}Ü*Õ ˆ¥ò~­"ý[Ÿ«hÿ(ãõ9þ­Wý]þª?U'ú¶;ŸWPÃ}¿U‰ú·Šûzn¾Ý¾âýZ]ú¶~­“¾v©»õi7êèSõV½õRWÕ­ýõuûw£öÚWÕ´¿·¤Û·NÒ~ª+Ožá'I9õt/}»/ûi9óõøt}ºØÜ@ƒ÷jBëÒAw­FÀ}Q!ù»r΂ܥŽ[V£+u$§€Í ýdm+ÇMê0Õþþ}¯uÕØ ’¯Fƒ%+ HÒ−ƒÃ! ˆF¼WCÈnT¶‹1m¥¢ÕÍj4É Ñò3™³Ž¦2äîÈI´ã^Ú^ß›~5P6Ñ\æÁK4°Þi¦È¨Ctá›í'ÞUŒ,ø¯ÒhyöñÑu½]¤ÆÜ…GCÅv_×·ÿ1‘Å‘Tbú¤ ÿHJ¶ºC](a°’ú±ÿ$ óP²±ý«c+tÚý¿_N± !N¥@íŽ$é9H"ÿAïË3Š}ñ.˜{Å‘³ BóRéà-·>s-®%JÄe•0Œ­3kËyþߎ>*Ø^Çtÿ>Y)ÂRt *Ñáà{qî¢Náž$`Ì>âç=dÇÿg›K¥A“ºÐ6P G}Îþ&ŸtJ¶ÚõfV¥¨Î*Pü(öuœ@¶![DÍÎ8²ß¬„Xá`Ès–)°Æœ¼’}òBßWÃ÷p’7½Á¶vŠ™LD'[H?#l[èa‹Iú½èëJK%Òcd«€ùBâ£{”žö~Ê¡ ¢vC»hM cƆ.$× žzNõîø­oü"ùVgoˆ ªäó|ñ'ãwohs‡O”ÄNK¦?tý.óY×Ï]°,´Æ/{´ð×ÍhQÉ?G>ì§:Œ/²ZChC_ž£e+Ø V·h¢º†bfVîÃÈF;àXÃÀ6¬’ù½]2hò„ ®G‹lYj:¨ÖØV‰Iïý½æa¸²ÿo£?˜6NŒÏt®¢8½°lª¬‚ô±+À¼û~«@pµ“Ëòò !Zçä•Ï|Öf Œ|f½‹ë"oV /d/þÒ“Œ.€’ø+AÔ|Õ,üq2’ÏÁÈ„AÔ†Rà Rm@} ü×sÛTY›1ˉMÓŸÉ\sÁèã'Ð-’(È"¿è©Kîg#óß'-µeÀVÊ2éý$¿çö¿@½á‰óêØ˜–SfcVâfŒ¸QÃà$ñž>òQA‘øf•Ws»É»%Ý.è‡SŽfùéµSêý'B4HªÐÄÊ™ñ‘eT× ©¨OÿtL~¯ vk.(mD·÷ÊÏ/˜)åÍÇüŽpÏ}òH .L[i;(k{„€( ¥N/v%@8l2›”¯œî(¤ß–9Fõ¸¬5ÈažI&Æøg@áj Kÿ<Ù“CLÝpÂèÚ¸E 14°SïÕ%ŠD¼aÎt‡þ«ìüŽâõ”Nœl«BÓ‹–ÕCì£ïkk$Y*üs÷òK#ä;9Út«æh_tÕîÄ&˜&S!îÓA’œgfx6É5ÊMRêûÑwo¶ðéo7>-ù+ÊÀùø)G╃@º y÷]BØLYVÙ äLb¨ØsåÍÓzlIë*ÐNŸÓU±ˆês•Då/Øßl ËÚµÎ^]?fho@.¨öøkÆ5¤º¿å0JW,µ-§( ð@Ms†õ@^,-”ô¢Âªæ¦v@Ç“Hu(Ìʸ6êÈ낈qÑ>¶…°²IOŒM:Ø&FÇ rþW×?Hlá¤æðd£Š?NŠúÛ0Ý´¦¢÷ŽK-ç¦lƒúZ°5Õe›)Ðó‹=páêDÅáõM22%dðo‘2쟎=]ú±oÒd•[gjòÌEƒ«Ûe_¦^¶À¦ðµ3Ââl<}˜éø­Ë;Ðç‡S|kH§,yv H`ü£'N[¬~Ÿ_hñ 6:e†Ì‰_'×h[q®Útâ`„¬­ïÕ°àÕãܯüZÃo"ÈO–B;¯^kSž»ÖÀAÌÃÞ9âéÞ%«¦µO¿ °Q5åQ±ð¨.¬ŠlËÃ}n¾Ñ¿Tß/¿y+€Æ°ã{ ´g£9,Ž7¼×ÎjPm:{eXlE£ , g  ψÿX¦,PQµ€°Öb©'öDžB1ò«àÖMü_©”·ÕE2 Øgàçä’xªpVb„K­„›Øj)<±e÷Ý¢rËÌb. Õ° L3ôxG$Þs+b_±ÌôX_¶Š¢².7ýxAæTU7šSéÍ\{¡ú &ô ­A#üúš#Ù?§5ÒxÚ¨HàMÿ{þ¶\ }&ü <Τf.™H„Áuh¥oöðô)£ðïYpÄ^ãÐåêvZG³¤¬4Öú¢H•ÖUçïìv"ÜšiÁ³ZÌûC b£+kø¨¸Ö#p4YüÊ#¾´X&íi>}­NäòÔ»¿N©‹;S’#k¼È}û}óÔ ^Ë¡;ûªñs0¾µõçzS/w©prO¦p®Œ5ÚEùüñðˆæ;¦œº aRïÀá‘{ϺÂ~n‚Û nRëÔ¨¿¾ÛxZù[¿€‹è™QíÅN,žr+ûuòz˜ÃUÿd'y÷n«e›O—ÿ\Êâ~„N'«ßŒÑÂw×­Ù®]/(¿+™×†ížx’cˆ¢ï'ºØpH¶U´{-¿Ð#Õ¨r†ÆˆÏ€5^XøÁ;³[—g¢1bå{¡Ž*åIÚ©9Tú9sÿæÀZÝA÷¿<ð…-¤¬=¹Fõ.ÃS#¥@ItΩ`YÒöù‡þnž+]ÏWö £æL~ Œœî PBïãÓ%Íœ»û.bž‚H;ÒMð6¶ƒˆ„†SÅS½’5ÑP”ò¼_0w¹|q-óXo¨þ.¿Ifbv2о¿Àm&'…–zŸ0–TþìÖ¢ðóUAøŠ¢¹ªn«ž¸°8°å2%v6Uˆ»¥÷gÊ^±°H±´Ñ°¨]¿ˆ$}·ì.õý/pF°åð5¼ŸlP‘8Ë‹Ï9ŠXÿNM" piær"°’_]·¼“–>…ЙsˆÙ+]Ø—êl’¬€³™ÊŸø…‹•ÊÆ“ŠÛΙ—¼XJ»i.×1²Z?ˆâçay|DV{Â⣕ã—Ñ'RƒùAhƒ‹©ÞÛk“ °®nû‹Õ²½–ŽŒ‡Ö6øz%q|\Ò²°èú=tÃyoZÞuc‚Á鿸/Š>>©“ÕÒÏï#HF‚ÓlƒsÞV8¿¾z÷å¾®¤µ.Üoº…[Ø6 ½:x|ÐSåÀ˜Þ,¡_£?òÌB_.¬uµ¿ŽÑö¬¨X"û"Ê|>Bט%õ:ŸVØuex«ohœ“Ò°tÇßY#èùyR83H‡¡Fߎ ò0ènÚ »­‰‹“4 mn½>Xšr—¤ZÞ©DZ•õ°%4‡Á»hHç>1*NœÁ¯XœÞq¯õ6¦ÇÇÿu!ÁF›ja`ÉtÏé ¯|¨ò¯ÀÐpÙ9º/£@juÇH´ßúYË_‡¦V6yÚ–>⊲dà¶´qñOByWÔ€6ƒÐ»PÍá’!SÔv·»Ã'rl‹‚[ó…”gßêdREˆllkWðýË+=Àñ@r©žˆ(Ú",wt-àÌT¤úCÎ+‚ (eF,ËÖN6‡¶òžë›oLž­ð;uê$©ãÐ]Ó·ezî_9¿„·nBu”Â5ˆZJçg®õþà5M­”F ×ËÈ¢ÿ ¦»aH¦Ë>—î4Õ®NÎ3õ.vV‚i;ljC%æXÈMÛ½ö÷팵1©á†2JHáÓ(Loº)óÛۼسAxd¡Åm{•B¯2UX~J§ΨÎùm’ø1É'êö0ÜŽ±áÂãǰˆ…hͨj¤°_oi\—%õµãÏ&v$sAR[ûÛäL¬zÆ Ñãš[²`’öÀS^ ëBKMšw ^÷-ÿd0d–)1¥Å`hÔO-Æî;+oSx¦B¢¨¨®-rS#˜,wY(S—Ú{IRÆ: Ôù”Õ¯¸z†`RL©^så}Éã1Ëkü@šz`“®V4ö¨ •òΊ[#³¥J5ÃâY†Æ&\ò¥›z F‘&Šï5þ{V¼ÃAr‹Yƒ—(óÞ¥¼»˜4É¢¢†¥òÕ4vÈ+^lÏìl†Ò ¦õø³bdàGˆr¥Í+NãÞ!â`é_JøÑ)fꨕA].Ë«äÓà6Ó²50ˆDn…éo0ààz"àûÞ9>cÛé«Ó,I#N”Dÿ颖â«ïn5Ý@;®'Îïš󷛎J[þ»ð[âpümwÍ» KÄnŽ»â¡aãP)]v„×hùì4½v5ßyعÎj ñ6¶{«ÊâÑŠåoou…Êý‚¶BgÔ Æ%$iT fµÓ½ÁRÔ†eùÈ…Ø,¾>’R‰ålFšÈÇA8X´`3q¢¿æp% $—<ÐUMÂU˜–ÉCS„Iº×cÔ$Ba‹øÐºtÓŸŽÌéæó”†¥’:oEøigTÍüGÊÎ*V=D窑øÑ»Âirb!Ò̤î ~f ¥d‰UaõmÀB'Éùê¸ä„¶à<¬ˆ5‰ÂöoFqè”8 J õBtª¦ëÞÙ«ç\AÅ騿á_îlTYÚsµºWÐ0ÖQv7;™Õʬ¡·W5Wc±Õ‘x‘<9ÁÑ-ê‘»œ‡˜!*’JAºò°Ì†8ßˆíºžDû‘…•w*T’¤·@Q›k_j‰È]L||¾ÓSQw2·YÊŸy\=[<¬ìX^®~èÊÿ¡î²¬àv¸ 1¥Ãz牪¢%¨F‡õ˜ú³ ŠvÖYÀ y®&ÌK’»vrñ Ì2C$¾iPvÏ çrø+íx2^?ñʨÈÛ±ûíÄ¿‹VV'ñiµè, ÜfwóÃÊ™76äXm„¬ÝíÞ>ôú ¤ÚrëD^l é#®'¦©-¥G—:Ñ`Iwé¡2(°]—šã2°§è4¬/t|Éb]‡Þ—iÑ¿ à^˜º˜¯£¸<÷Ebî¬ÅWËS†4ž#˃®õUÚ _ÓQÀ·ÇŸSc gÁ(ÊïNé&5.lç¼!”K۵ߙ¬™ýóÈ¿‹æ%ì¨zbpP%ÿf‚ ò;b °ú“*$a–5ƒåti[׬ư·á@µ«Ìèê|Ú`—h»Dê„ZÌ+1*Ø6e€¯qÈÇ}T8©‡maÄÃÜFJj矱OÂÆÝõo÷› Ÿ ”‘Çm.“ùI07׬p¬ÊYŒÌ„ÍÍÃA€Q4ª.‡t^â¢ÃßÐyf} ôÒñ*[ù‹jÏ-¿ñçÊ8ŸK«wmYŒê§i6´Þ¡û¬ÿg›¦¾M¹«{€ª—ëüºðE‰7¯Žð²ÜìƒâdKHrÎ< tÁë í+.Þ ¾‰ùIÕ2zxK×ã­EÖ­â¶ýp|¨“rûPÈéñ‰Å—:Nš ?]#h}Ï[+EÇx€šÌl:Ì0Ä®D3ÿ" Û¬¸¸‡§³$çåuþ'6¼îà^^ñúÕòÊ"Ês[ø a=˜7ÙáXáˆúH³|EÁÕ¶ƒ Ç¾÷æÇUÿG;Š ê<€˜À­‚J˜°J8*7ÇÐ3·GÂb–óZÐç/Ñ£¶b ¶Ëa5ª‡¯¸&×Ðð9)Gú¢ù†ôF['­Ê+³"Þá§Õ) §ƒ ÕÏ$Ù¬ RÀ[¹ ß“.,Ž›”bÂð¼]oö)x(gþµZ_à¡nÂワTå¯uV,$dlˆž)—«íÏU¼–Òjzb¬JíðÔñÀLÑ\|e 9&&¤£$XÚÍ5Ö2s}t¨oá§”h…#ÀnÅ€#®]È6}¡å¨JQ—8¼Ö²ìUHó9¿ÙЪ¢²:ƒ6c²3Í«‡›^Ê0š÷£7ý!9U©¡=’ŹF·û·>§-TWªLܸ<î6Üã˜)2èÍ¿ÿ5uÅŽ•Ì)B•§t'3Ò€GÓµ,°õtÆÓVPçíÂl¡ƒý–?nAnù…Ùþ³á5g1î´ïæYZ‘WTJX>â`ù®á¨¶¼½Ì&#SB MüÚ³BÈ'ð|áÿx¢¼ÞÿPAáÚ}cú=ÅÎ RÑ´7‚ü‹ÊŒë9I£Ì;ÈdiÃD³I=´oÞ ¡pâ`SÜÇ1ˆÿ$eÏè´P¯šÂ²nÉw7 —×âUÉ ö·ªûxvGeÑ;§öð$öÿa® ºöÂ¥â¯úcúê$ßÛZMË–ULFSŠA÷‰Ñc{CùZ‰T¥‹\.}¥rÆÅÚìz_ÔiÀ"¾¥*—9&Žxþß6p>ûâÀ÷H”ÐÁf–bkõñ Ö+:„tÖ žPÔµB¹ø>NP¿ó†¨äJÈÀ´’6 m¥ËÎéTì(“y-W…NU®X¢üèWf¦ Å׸,ÀƒvŽiÒ_È}à.ßÇJ…™îºz¶³â³¼ÉÃ[?œ¢­DÚ[ÏïíÏÌñ"å)V¯¢)V/ãã“/ôNË-rê2ZÂN˜J„i‚4´3LD3pTp)wåãžÆÛ Tg~’§þçã9´ü™(¶wÆÌm…¯ôwJUq37I"rçjÿ^9¹cruÉTS†Ñ|X ÏÞÐ /wÑ3{*âeäxwŒåYšiʆAóË‚¶ ™Œd¿Áo2ïbíºÓ²;” CkÃ馿æ}»Sx?_éÓXUxóRXXHÿ R©Ù"k–3b»J”›’c†2é¿F!B†Âãå½› ;lCÖÿlk &ñ—ÝH™l_EPjLì×µ–I¡¥ÿ=®•ãý Ô p@ÅGÁbÉ.}1…Zš%„Á©§$Ó …õ~P¥ïúÑ{ÑõY…Ï|ÌR<õÏZo25‘þ%Ô·Ápük¯ã⻦á6ÁeŽhíÓE€C8v‰AÞpyÄ—'X¼ÿQ€¡¸ëfYásÖ±EB‚X[(F5ì8kËHH‰KŠÜbÒ­‘lÉñ¶ %YÁvÚ½È,(pò쯪dÞ"ñÇAD¾øú6UœŸ‰N,Õ‚@Ž4£ç#:÷µ!d÷dšòf~À(;|´_¶¨‡¯ÕÐßÔÀ¶iåö½W¡Ù=KœÍ ý~s¯Óψ\"–³<\á‰F¿¯Ê©»­x_r:ª€Ne›=ë]ýôšÖþí·[˜›S„*Ñ€v€J:‹žœˆåÌæcZ Óà"Ê­‚>sbËy”ßJñߥ:Aì]Ì-wR_-€·y°^¥-ÎŽWän3EûãBÎfcÓp¿@á/üÔ#z7#ëégÕ9:qgnÛ~¼!V$†f¸â`ÏÍažÃ4vïü4æU©IñEšœïn5dÄÅöo‹;­8r\­ÐNVÐÈ ÷eüüc0ë@$ê^K-µÑRYó;óíïsa0Al™H´ÂÒ»´Ô5·¾(¹½nüƒ­–0‘¥c†~дo(~)ï.û&’†â#ºÅ:# y,S¾Â_8¸ùÏë—N5Þ†ÖÀ­Ô9§Šª^¯‰­[rÂï§*œ§¦“m#aÕr@,ÛYyjïPFº~£?ƒÂ^ë­r2ÛF56ºiF§Æè—Y å–-ÈÒ$B#}ƒpÿ5i¾¹:qÝâØ¾Ý †ß:Ãh‰Ï)šø2"Þ<‰¤Ü©C‰YqçÒ\¶“h¡-tj+©—ì¤Ì®0‘Μeý¥4œn3 »>™RêiÈð CÞÞèI˜ûJ8’ÁX »zݲå:ù•ø»Ò„@¯·h<Ÿ¸Ö’:)Zî%s0¹t¦å¤¿ëêé¤qÉöâ"¿÷ÚO¬ùAÖß‹Fû%k뱘z%`’Ý iÔ²”5`°©i‰¶£‰¦LÁ¨Ðå‹™wŒ\Ѝ:v{kÿa»ÎMúeU®ì÷ ƒ»A"—ö`†j´î^Ç¥žŸ¹à#g¡bH•T±uå辚­xöOG Ï}ýNjPkÔ`0ç›o?e!*hãjHI—Hp÷Ì3ÞFÊÕDR9du,"B~Æ—_–ÿr¾ 0„ñ!³uE.vþ4 i5+µTœ\™À¦Uͺ"Zjšî°0Ð¥”Bµ¼ë(äŠ!þ¸Éüt×Ú›aKÙ†9ÖèŽ{@èN§fK´$áG¦62CÂÏ;T€Ap q4I¤d8n$Ɔœz)o§¢eõ•ÏêåbZÎË.6Äs3¢RÜEÂîµxÃêO¸Fðë*5É[$‹ ’lõòqº'[|m‚•bSÀmð†¢Ö¡ShÍn1ø[4u•~I§ïNÇÑ4”DõÙþή*gŠaã ]UÀ0BãÌ/Žnh,ó V;à³#û€Ä6•ÒIJûzi©Å¬”UZÐUå¨GÖ­Ž‚r„ƒJ©ñ/hG¶óú^!Í2pÌÔWZnä´¥*Å}JÞø­^48Ù%ž‚Ÿâ?ðUøL–„_âVV5FÈÁ9Ïꙑæ–+ÅÙ”üëç©Ñ!aCzÖæ„ÒwycI¨edqóµ.²åuõEý%p¬…Ø?OFZ9 jé¥`À¾µSzslwÝ”E_“Wàrç_aêož÷ܤ‚}§GÒRéN TÄ8žóì`¾üã·AKj¯‡k`¨¥pEýâ²|µ ;²ô·FÐÅm¹vÐÈ0ãauôÏæ1Þ©’=_d`H¯Ä&žšÏñ U¯^`nçNR:·^ÚOÐØû9 üsï‹ÈèWB8GåézKo]Ö/°z‘D»Ööªååùn<ÿB’ß<”bŠ¥®qÓ£ à;¥ÉXËS ¸‡—øÿ!Éf_8Ydù¼’+nœçjC5èߌz…ˆ\k' ú(NÅ4µ<ëˆ"JÈ©F7G?£°œý7©áš¼Ó8ðJ~ÌÑ’”çÙïɯ±‡¹Î‘¶Ws1ú_㟇™Ôg犘©´Þ©È3¤G"| &/lvŸW=u¥¦³œ Õ–bmr)bœ¹eô|þ?—zÐàžÞ—eL¡b-q}m6ön*>74£¿ΙÞP¥Žg)tÁ¨a\¾¡fÀb•ƒŒŸó­~É”íÚ }›>œR8àÞQÌw{™{ÒYC‰Mu!\1#z<UѰ±c­=ËÒ¦uÙ­ÔikÞ{PÀ¾âédÖÓÇ$ZØùtÙQh‚¦ ÎYÌ4ÙîœëÔÜØ~®ÀÃ.Fˆf™ñv`‡¿2%O¡ü"Uæ.1·ý¾H2 0ª' êX®©´¡°”×]æG†;LyNËjÚ¸]¯›,ÇZ.˜¢¤l8žL« bðͬº¯¥öÙ"ÍU£o@Sni~¡ÙF ¸mÛgµ¥[¨¥kÉ]F„´’`1xȆî{¬u#›¸dm¹8ZÑ¡@wo©®—¢ñjŒ£áŠú—eå¦=½S„ˆÕ”é~À&±A 昶TX”çp °`­úÍÓtÝÞÓÆIš¼Q¨Æôi¤2—Õ™ý‹ç89ñ"؇*ñ,ËÜa:à qåD@9×pî`äWOR¿öR|†w;Ò*¸EÑðÜ®Ç.‘?½bíÝe¤–‘féì¯~c¾·7aæÿ-0cƒþº´CÕ[³ã¡Ñ¸L5ÏØ#èS#\:.‚<ÆÓS›z~÷×f-ͪ²rÒÓªv ÷ 60#),"x¾Ëå]0쥘Õ^x`˜Ùöáÿ:LÀP;„·B°d,Qñ÷·n<é„c¸ZÙdðÙÝYh¬­8,–ñ zŒ&ª”fR3g=I‡ÍVAÕ¬{K¤å?Øý.¸;ÉÓnòÒ3ÔPê^°CKÖ‘ylÄ-ätÌ?6%ëľ›0|¹‘YŠ„F z#©vÇQ²v^ÀQg1\’j»qÀøï³¦I”àZÉÒ!úÔ—&uøÈV¥r+u°ý.ÏΡmHÿ\Éic÷Ï>B}ê µ¯dlA–C+¤ch«Xìë4Ð ó»cëº ”IHn-hˆ½³Ë V”ø{UµXãÀd<¹éu‘Ø pÿ,˜ƒè^Â8¥QÅmû>Åyo4¾cr¯2×ð2 U‹$€V 6©:YAT`5AðBËÕ†yLþò@‹åi:Z ­‹¢´¸ØÝ®ŽÐ¤ð¢öÅžV.üç.îJ–À"Wb¦µ9#`3˜<¶#|Ä^ƒ¹¢AÌyÁÞBºV`škj'æ;SC³©Ø!¸¥m“*ㆬfJ˜ÕJÏeö7v|TS§–ƒ‘íYŠ`²Ã')õ°5{vÀ<áHKõõTXá&鮂ùmx€‚‹Â>mðËÕ¢†}×µ5>‹¨—ܼ0ïÓÆ»×v} seXÕã@ËÃBZË炚#cMÀ/†Y† gòË|ÈhG®Õ碫(ÿö#Še+æá¢ùøUƒô!ÓA.Ó|UÖ½2‚s훊ü9ª}ÍL¬ÿ}‰<Àì®ØâP«Å}”ãk0W™ÅÖ`­$ †N˜™®%­„‚Nþ™P¿ääš¼EãL$åY(ñhyĶ€à7›T‹½aÞ‹~ÓÐᨨ•ÌlMÀè<ÈG6Þ,ÅŠ;Íuh§÷³/xGô,™'H¹[H.®ä$' l½çjofÙjñË›¯]oozÅç[ð™6õŠϪ¦$Å"o^ËÐò`Vü¢˜*#™‰~€Ù™Ì.4¶méí—Ï~Â¥+ÿ#óÇñ¿,ÎÍè¼^L™³?‹¡b"Ž_‘Â"2ì­90¿ˆ¥{-h¢KJ£W|îöÀ¢9 „0“>ˆWi…(”Ô´Y૜Áé–>mD¬ú2$ ȬuU*6i¹í·ésfZ#¨GÎ /ô–ôH‘¶ŸcОŒ¹6ú΄SúyO@·¦zç¸;ÂqđȪDú¤,™(‹»»1e¢Å[jGÅD’Þ¢\ß›¾®X¾{zß¢ç§ ú ±l&Üv6¢*{ó0–?—FPçÍÐ_ÜmíH.­)[,’,`qÓµÀ?á¤ø(VaQ4á°n_”·”oq¶zh˜• Äc–”!r#cP`æžïE!šÙñ<ÏîØA¸ù6£Ð¾è¤Á@ƒûg~ [%¾þaèrÔÿ#ác<X§óÇsÇ =“îú™ á1L-ƒú a–^ˆ_ƒ¯½å¶92¢¡‹žÖ'·o©ëЬÑH'Œ»ÈÞ«|Rèy¥C½OñÄ¡@}ÊTŒ\0.yþÊAC\xפTá»Æ9…‹Åu|³MݼáUAÍ·{|éÊSÓœ¨¹D)oq^ï²®õ4.Ñh##‡3.TcãÞ*ñ¿P1ë=ê'×**˜É•¤ùê‹@‚Ç›‘æ‚ó§p‚´kŒ®³ *k@ƒÐY+H4/åi޵SS„ÖD—Œ4p Îe£P¾eEb“ð=­Âä2tÎï¶ŒIœ½õ‰îH¨Œµ3SxÔóG¹^ë×Ü äÜóóÏmdr¢1 Ÿâ¨9š®øbä;Ö}]lQRúxÀì?Kù ' Û:Iop>,¶%d*ÿ_¡„ÉÓ¢$»‚—~¹òÛÞ½±DR%Gx|#ÖSÛPG/;æ›®7¥MoûGYvY豤žsŸLq5^y!…ùfåù(òõ—ƒ‚•}z©`ëáq£>v¬€üP/ÝknðË­À1SR×O'ŽMu1Xû2£^*žæ¿S™: w\ÅŽJ¶ERþnÝ+:|ÝJzÃY°×£ÃºPuÁêIßÂSF’za¤^ î™pZ5o¾š¨£(6aG}Krç«á²tðšÍAß$^2F¢WÀ­Ö‘hØ÷>}²¦åŽ7êGŠ.Õ-”‰‚-°Þ±yôteÉ -PàËf Ò䣊©xôü0Mæñ*ˆõÉ—ÍÙˆ×ÿ^¾RÝéµûøƒqð§d“X¡Ò¿o½æS8hSåÔ˜5$Èé–î1Ø–ì "Šª ¢n1lgW;‹`,é´¹ ×l—86›ª—"C(òƒ½opáS†ƒ$‘ŶâC¬±+UÑå÷¸/>Ñ@ ÀÒ&•&æ@”Ë}›°KP¥ÎJAè÷Öû'r¿úÕJ&¸8ã${þ@°•ã2#þ4×B˜À9<•ºsÌ"œï˜žÑíÖV¸Ü‹…·9Dðõ.Ñ|È™?ò¤+ÿIÞkßê–zD¯£2]ǿѦÍÇE/¿Hl®9êNéLÁ²J=޾_»qÀ®ÏY`–¥ý[²X`0®Y#µÑBc8ê ŠT^pçaØFÕî׸}Œ²V;þ¾òi6oU¥ØÉ´¾>W&ßN¬’0Ó?ícïË k^ò\VIæÀw=ÑÇbW¨3Ÿ4† ÆÚT函/ê TàqbAÑÉÓÀ»DË–çd«­gõûÊ›>£(çÅÐëyº‘vªÐ¹óÕ¨1×ä×Ñ[gÚ­@Luû}^†xìm*çä^ûfBýÖ†´d®a%½¸sÚÍ <[`k6нÐ+ ëDT¤ëD5c΀â²vÈT¡òÆá¡3Ïn§M[Ü) † içÙ¶‘rŽý÷,î3 ÜkÎ.ð÷;ôYÖŒÇÁ ¡€U¼œì‚mÁ·Ú‘ïÞÂ}ðfÖˆì‚øjÊß`N†Ì曨2å'®ºB)¥kågòEwMœ™»~֙쳸ð“–ã¤S61£À2é£%%€F€ýº˜¡ÐÁITú€ @ÑW‰LƒZi$ˆRµ’:ÖÅ¢Î[ ápÓõ'Õ ÃµÕ’á)5QyÄZ¤lƶ²‡ !(B„ùîÓ·PU’Åu fΖáM\TMtÁÁQc´˜°½¦¤ú´6J.}J#^‚3˜ˆÞ`¹²ëŽÐB?Ûɰ/À'ÁÒû!ƒÙt¹G!X3Æ 'S±BÈY´$ݶŒ|q.VÖºJUÓFv–¸¡ÇÚð}Uè[â#´‚u~†©/D9¯ 復5¬Ðö›qÜ Û2oôvÇwœ<âPå׬¤G ÜtUæ9±N¸~*ÿPÝ­i'ÞÌxO@ZºË¯®QcÕ»LŽ3…®ã&)¸P@Ë\äBwµ¥@Ì:¨ÖÈQž¸äêßü$¶s©ù5„FÖNúv([×׺x°Ÿ ¯ÜÄð)­Qˆì“¥ªþmîûÉl®›2Î&­M5)¬*wâ솦{vœ“$"]ûëõß@]¨<ºîórÀv¾? ³ñ Þ°•©h^øšÿO © ÷îØ‡×Š=™±GË?Šâ#¥Jp›±_Èìw«àPe­$ÞPE)mõ§¥æÆ]g&Ò6tz½D[SxécË¢YUšÑl<~ÃL#u$ $̲S§‚° Ü.­Qç‹(û]…aÒs E—ö—¹}ìë®a¹ Õ˜Eæ¶*Å8uRl~Ò{+œ}éY¡±¨îÝÛŸ°\v#ZÚûcƒ†˜…Ö•þ$13­a,¥Ï9~Þ^,–ãYÜtÜhôƒ®·¦²“ák¤›œ²ÕeUQPXÛÏ;î¶¹] „1lw=žnj^ö@•1‚Ī…‰@ø)±â’ "`‡9¡§»­wybXý"¦ºmÎ&A°÷Ñd[áG½[+u÷'#4n®CoxMr>ÖêÆ8D¶æöõe9rƒ³oXjl`ø³ðàÓ¢iò+tñúI»õ hî•Æjr£ß=‹Üyø]8K™Tûô„W‡Ìªaºq©B?Ã…„zµº®y±2w$7´ä–éiÈŸR$ÁôëŠußC(ÂF13 æF¼Brº1¥5(æ’$vl™¶`Ù8@È ‰1¯sM5Á—pnÉêÅ\#(ÉA£èz Œ”ûz±j)%¼Õ½°A#D<ïïn&Á%²ÁËl?)ŒŸê€¸ À´IU¿A¯ñ/˜À f(h‘Þ™PbÏ?ÍÙgõ³"ë>ä|ÓoWç+î²óh»7jwiFŒž†ó|G"uËýšøQ¢jU]ôÍ:T,ÑÍÔ‹Ò˜Hëõ!Y¡ ×üµ‘KÈç¼#|ÝY££N&ÈÿP"$TyÇ/Êf U:IYÇz×Õ¬ó¼Q‚ô Ü-úwýªfSz˜¶Ì’w¯Ú#žDŒ¦¸j’Èš;™Ýi«8«†ðH‡"XÓÆÎ¾‘Ù ìÇÁ+¼_•uá«Ýj9FQ×¢æÛHñ¥cÐ4)¹ý>=éù‡‘T7R¬êUž†Oœ­Ot½_|ã)[BÓ-/¶,¤ûö³uSíWäOöUâköî) DFc~•Ý>÷0ò1ùZýã xAwr\Ê»’@Ù ¦¸\LŸXȉY%?Àþ.‡óÁÇé‹D$çWK¼—ê í‰iç’ìíú)³Î%€_wSÍÇí ËXYîŽkÌ@jf¨ìèøÇfåó€u©Ÿ’áŠ(ˆ cÄÔ™öaóikuzTI‚‚ÝÃ:¡”„úçXég·+ç®á ýå]Óx°C\¥ÅúÇòÿ="c3Ú+îoG‚R* ½ñs^Oþò¹ý„н§—ÈtÊ¿!@ ÎOp”™¢{Ÿý»Yܰa¨h?+iœŽ‰¿/]®ñô_¯UQ¹´53F2>Ù™vn2#Îuª \Â’0©,ñœÑv·©Óƒ|ô÷¬¡Š5^» &áðMR­Šá„$ÆÂ¥6ýƒ(Ôq`÷0|xk…;÷e›¼1F LÍ:¨ºr\;Á}šTÒîNIA«ûg¦Ÿ¬Za–› C£QF Ü»’/ÐÏà˜}Ú]À[yƒIOÅ "ª¤d…]þù¢Þ°®w?Ël#vH^QÚE`€iÔè ·K$JÄÄGgÏWE<ÿzK´kØütŒ-—H”ø$r ¾ ë36Xo ÚÊø,–\ñÀÜŠ:“¡Bîõ*o»Ý[qžirõ‘UŸò~Sèüà¼Ì¨¤'Ùï} I‘Á"œÏtòëv¶)@rhò݉€÷ã”?¶ ð߇¨* u³¥•ú”¹°4o+CÁGŸ7·—{ãþÀ›Ý÷eµ$ä&\`õ†½“?ø?ø[ÁªžÌ8/‰Ã)…vâšrW‘>5Rý«›ó§¤yèžh’dΣ‘熜öì6©;4ö7›J·×%mÙÆ^”ÁªƒœƒTÀ•Èò’ûë‚‚=¤Ô PœŠŒŽþ=¼Ü”8V§°ØŠÄAi4\+¿þ*çéÜKQ/RÖ"¹!÷ˆ8e<íqÜ™S0‡šœ_%JÏiÉì…ßwÙY\WOUóåbÞÓ9ÖÏ]8ož0¶Cy,ÈU›ÛŽE7IÇ(?£&c¾âÉfªÇ‰Ôb˜Êˆne“¥¿3Ù´Ü;§b)UýëÆxaJ™…¨ é”:Å\[¡8 zSw¾|S)Gä‘Ç}¹VçA®T¹¡Æ>Ó…º±~’/mllkÛ¡Ó'ÂL£ET…scÏ„M §êy°œÚÿ!­›7Àú¯«–¶‡Uåo…ÐpýB‘š¥—á„ýäÌ€±*ÁoÙ̵^ Ñ>N`înÖ÷XY§Lø€”î›ùg¥´ï¬ÍÝW܆º0Ñ<ŽFVÌ7'æ2b!ri,C,î{ëüÀ*ºv$SÚ!vèÆý†?DLÊ<åP!ey?îÚ°'Â%;‚\h¢ô©]DLCµ€¹›ÃÚ6\I£ðmÿ.Ï©‘û^1PÉ¿´€Ö[˜M3"隘sº[~î$œM'ÎöZ.Ðs{jú¬:qH”>DÉ8ÀÍÚ@N¯ -ЏГ1ëÛñz:•ÜÝ Š=º<„1pBIá8W–ýçM{b? ÜKÝn#‘½Ìx!#ÅF…bßóÔã2™Pl(tªuû¯t: [~R™ðÁË_·‡P ®’ïV çùSfå}žæ¸è9Z!ǽ`Ñ wdÐhî’è¼ì}i©Çœ…ñŽ“,×Î7~¾©K^PpíFpZ©ÞG þ¬Ìøä³Ug£¢778€l/H2ÿb%PŠ‚iõ» Þ‘0ÐÅ¿¾ž&Î)‡±½ œ3wùbÂ5nµçÔœT ý;ñ¬¸äåEÄ$mN@Ö•Ëù'iº¤ê3T1¯Zûד³GC·“ð鮟PC*påžÓØ„Ck8¼ípµÕI_›bËoÕCXÛ"ú]…‰¬ŒN+†‘Sãžm{©ï"u™É¡¯Äžæ‘›:8‡Y‰Ãb¶¢ôZÁFbèÿ.?ïbúLñÆ%D¡=_ѧï“ kC—ÞìMס^i6Z…ŠtŠ˜)i5ïŸ-ï,üðkÕzµ‚1aäSoùú½Ãkåà°äô@v«Ò]²D‰Ã¶ ´£ù£\,p p¡šÎÓ?˜GæuÉ 0Ñ‹G\ÁV>òGe= ¦F†éãɱ]ËaàöÏb¹ÛÁ²‚ñ~0Ö@‹™³§ÒؾS‚ÛQ%cÜå™75öØŸŸp“HæÌ±Ü<Ê­† ­0–”5Î0K*ïœ, ^ Í%Àî|w†ñïëE}9ÀU?®ÿG7‰Ú%Ç š¾)!¦­¬€¬ñê©ïãªu”¶qM`NÆcZ£Å$žh.úЖX¹ü‘l¸›|TT=H}qrÜQiá"9î=gV¢,G¶ e !ü› ¹6_QÍ®{(ð Ãœ_î£[©Ÿ}‹:”ZNâÕZÖXòÒiïMŒëá¢oõreä¾Hšp1æÛN õ?ÄܦÄ#!TÖ_Á˜]¶UWF¶œhÉy×wB/)–ÉÆx£—¹˜M ‚Ö9†”Z"›3Œõ ÒZãôb Bn‹Ð ñ4ñÜÔÊŽoˆÙö/?ÜQù„\M÷ßbÙü²&µp©¨<{æœÃã·Õ‘Å©­NÃ!|¤•a‡—´PnhÚØoX(uöï+‰7ÖŸ¦IO‚²(ª5“}ò«¸³›8”|l+Np·ö8ÑŠrbš3û5lL¦Êì—¥‡½â¤…þmj¦"Å?ŽÊ;Y°ûK1¿¢~ËÇÏQˆòàþ£ƒ;ί°ÙtÏn S}ÍàÚ7î7"pö•9žý7ÚfO`"P–g£’awáúú µTzî&¤]£0È;«4áÀÅÒœÕÌó´è3XöÞnÐ:j<ÊVÓåJ¢c$R .F–S#ÎmßRH{ôŽœQwZ)¤’Vh.à Ž}ét¸˜õ%îÑL.›“ü¤’0â=UºÝdÏ“KZúŽLÓÁ»ÞZ 6ïø÷›³›ÖAÆòŪ1p)öh¶¥B'Ðr{ËnŸøäêujGN`.RQ›†åÃ/1—-Z‚ÑÜKÓoÓ% ÃräKQ]éÑ_Kø!ï³:…KqGx¼-WöÇ(Ç’`ÄSMf¡üßÏtˆ–Õœ˜ß4G#O„ BGO¦½q­O-´d܈·èçn©cĠت hvâ_¹ìIW’JÐK«4; ”– >\Ùn…}Eb˜È°´M'EÁk~äÓ.B* \Šáózo†n ²¸‰_“©T‹´’©3*ûXtE’Úa8vÖðd A{’î¢ ¥2­4Û­•c%ÏDßÞ\vJêðˆ0­®ú 3X¾•Oz—ì¸TÿIÂ+wEÞ2á®ø À›*êAKFëBíâRPlZídz{áÞ*7»ã·¯âÆímol†ÍÛÄ }žÎð¦ð]Ñ a¯ãé …Ò̷׬+ñT·Û_Á¶ñ92¿ÞÏA3gÐ,بm…¢=DM!#=Gœ;^'ŠgA— o}é’­Pä'×÷¶y¡6Ù¼úÏÇôJQЮwM‹Ñ> ?ĉÓˆÍ8+Õ)˜Û áZ]ˆGM¤¶†wÅÛëæ«Ë9gB¥—¹Bu>ÅÒRàootK[fzŒÓóî b DJg{^Œ-c"ë‚vxá»es˜õÒÜá_ñK ('$ðg¨æ@d”ê²O?Wu ÏCÔìkZ­*“‰fÊŽêf¡I€^|üt“½ÊHbðü{o¢ þ~žgõøËÄ2!´0¡ßKC×[ Ç”Ã03vàeM­ÆÛ°êq„·PÍ<ï2÷ŠË¯; L]Ùï—‡Qž\:E}[_Ó£ž±ÙC‘˜IAÑ9ºÇ’£‹½’Œî%kr„L»“ZŽÆ”°¡‘„¦$R[’æ–{ôwùyIæG~¡¢ICÍ‹”5f~Ô!_7øÔò/{®p’ÛPÈÛ¶áƒà~½:ÃdU×4{–¨X+âü«cÚ……h0ÜÂÖ ì˜C­bß,ù4HŸh®ìµ¬v5½#²—h(oÝŠAYÅM~½hJ@·âèTº#š&vºrxäK#ø±eFU/$›ÎµEÚÔÊ‘ÛÈxáî*ÏÊï§)pG9µ¢&ç nŽ™D Ãñ9™?”¨›x€9Þ"^P™’½Ê!œO˜~†4= ?ô”ZgÔ‚3öQt‹ãæ•0éq¨‚¨ôëkª>UgH¶àrȪ7¥G—]†_ò~­ ý[cŸ«f?QÇêxýZ±úº!ýU.~ª7õlw>®ž¿†ûþ«#õn…öô×}»gÉú´‡õk>~­‰ýF_©ÓõhßêßÕ]eóéOÕ­úºrþáú¬ïÕ²_äoá¶\GçÙŸ£Y>N“_:¯ÏT¾MË|ýƒýT6?=Îù:;Ï« o᳟D~~“ÿû WÜ<ŠÈà$úýÉoÿÝð¹d<à¿Ö^gª ™n´¹5¤@†¾žöCoÝ÷QõJ½q7Õ[ÝO¹ÿezÖ“‹cM”÷AƒGð “R-°™…¯bQ\i6XÖá%Á£F ÷º<Â.ŠKmk;KY­¢¥zþ…Ó6>k;Ó-®7WœK=‹ÈúÈÌNT?HÈÆÎVv£ß°œî–ÃîÀ©Ó¾Ç¢Ã†k}ç9$±ÁÇØU»äÚœˆi’Øi0RôlÌŒ÷ûù¢x(Ⱥñ3T¯óOÁ›gOæÆËMØw¥@‘ÇÒÐÒ•áoY®2zضbÜmÔÃ#”Q†KÝÃJd1‹£ð¤$ªaŸC>ö·»ÔR‚_Fõ²ð9|9ÎcO´oËn«²dt¢ÓÌðj“1PºØç*´v. ñ^YÁ«Ü…ZX¯PÂò £|UóR€toh@4 ZeÇN!ìJB™,Ý"Ð[ý ?þ;ô"Jâþq™ e¾Ž§%–I µÆ{e°–øiЩ••Äqa•Ûo‹HÜD¡ÊB¢Ïï²7PÃs vú»÷„ÜÔMךœ'±“52Í$z¤ÍK‘?Ãl L¦JXÞ”ª·Û”ÎJ0 ƒ°’{bkŽë §Q íðFÅÿ©/ÄUÏŒi­7ô ¶9ëÜÌ·`€àzŽ} À›4}$ÒHJœŠ%^=Uwò¾;ú·\k6¹ÿP<–>»\–Lö,: ¡V;sÚ©‡“ÓçIµõJl{¥¡hg¾ÐÎ;î÷ÿ^[=^´º°Å‘Ù! 9#M) —½ ÑÏã<ÞÞŒòÑ¥Äæ^8t”{²ßUãŒ/0Ã>èté5fï'ý~ë›Fî¬nâë wÖÐìï^/Z«³–SUq~6r“gÐP‰oÏ èZ¯3q§3Z# 3þZèoºAùgêtÉËñ(—uñˆI„чîݵ`o_, “ÖEa.¾Š'O–иIlˆì€ãÚf&šÜÊ„²—ÙÍü'prƨPy:¬Ò™O­`z6žíª®Ó\5ãšL˜ôÛ«×ì 7—{v'H>÷˜Sô¥}ð%ôÛ¹¤{rýï‹Yz»¿>‡ã@ì®÷Ü f—®d6Úý÷Y¯ä—jŒcf¼{+T^\ß$Ë ©Iaýݶ…°²4*DM:Ø&FÆéLÍ,¹YG4uE‡à)ë˘{¢kdmt+Ás„K½n|N Ýl¥™…,ê=×À“¶7`rßS{¸Û’GJDÅß‹{ÙaUuõ›{oç9ð0è%­ ýKˆÉL•œo^ú\¶À¦ðµ3æ¥`¤÷ÿ_û‹Šhr_hz/oÈ~ӿφÄd&𬵋“^ÜBm’©º;¡iˆ Ggn¬ »Ê8ÛÑÉbmªW)¥[® hÛ‚µõ÷,ûº7àEL–©ì²?ã÷‰4ÃpÊ ¹—ñàï0–x‡†¬äþ3ñ¾j À Ù¡×Á2dìßXDÛ·W|аVV54Ÿ¿÷!v-¢¸ÙÄgjÀë¸6d$`#1lí«3äV•€° ßQõäY…2ˆÿ!ž<½ÕÙóÀfuz@$Läø2‚u:kQ«ae’UºD"0¥ñ‚e4ßÈÒ¾†ð9µa4V%!3å¤n?³åЭÝΩËh9 ”‡B'¦¿ÇÑüpÓ‡ZðP(¼Ý0{ŽE'›‚zÍÈp?·°ÞϪѓýôa¸ѡÐ//Èý/Urtv¨¿ÙŸ†¾âéß„¨¨Vþŧkh B‘*æbDS‘-ná¡DÞxDî¦óVDÉæ_ùöj!ÖKn²K]'©-e«²ðÿz.è ÒIq´DȽ9v8Qx“fL¦•“Û44_YÓ¢/f+Œ¦¯¬ßi#ú›e:ºP£okem¼€GhN@ÓÏâD7{[HnKLö×gWáQñP‡÷ßN¬¾Ó?ûŸ«ªo@`ùÏCý‘aÿjÐ Êõ.Ç5Ds@ÉeÂøoë4¶dCAÊyÓi|Éu¦É#Àv­¬ÇTîÊw>Èó(¶: Äô4eíÛX¨ßô(‡ aÙÑð®QtÒFé¯73œÎ!ƒ­+µªróÆ)ÄÀì²ýZÏ /¾7½›6{7¤­$壑õ©ºÊ»OMUt¨¶i¡(¼q舻7=¯©†u{í‡37Hõ*åÁ„0½€N‹¥L±‡úÈæ/ËÝe@5~\©«/´`g U“tëßÇÈlÿ2ý©¿ôÔájöG¨¿0t&í¸ã¥í¯Ž1Ñ‚âi ž9$u󺪽ÁV†þ,4§ö%"…Ý`(xi Î|á×Uï 9ò{x{ÌrHcÉQ7^‡6ó=_ºö?ïž9Ü(oÍøC^åëÔN¿ìã«1¨Ð›Ó:>^ ™ôz#þŸKEåöüo,Ü­>§•V§b.%ÚxµôVd7Œ40¶ã{¡Ž*åZ˜pZ0X%ÒÓ‚;·¸ ϼ:+u %CDòu3è¨|ŒâçÀÿgÂãSl2“å¸)€t ãv=B¦õQj b–¾U»$ÈѤg²7\Cš{eÕ>nŒ]Ú©ÆŠ·‚ ëI¸jó ¨³¸%”ެ+˜øm’År]Ü#ÃÝžf‡=+kÖŽ1â *ss_0b˜7ºá…®ƒZðò© K‡-Äð§k€œñ¡¢¾Ï+hÎèñã84ïÔiÍé´âßüŠÕ!ßÖÕN‰ë=ÿ&á14œî´Û `  ùJm—¿ýRnˆ§÷€NÇûÙ‚["+ÑLm°Ûûä0yªùÒŽÂhz•GTUZ=©P|5”yÄ6ø{óªulN¿5]F€ÞGf|µxÐBV{Â⣕㞤ÊE 覭W²Ÿ‰…Ÿ‹874òn&®X¦«øuh{‚¬Ô`Läè¯>dŸdJ&h£ë'^jJ\K˜m‚l8"Rò†g÷2L,uAÂkúÛÜLþŸÒð<ÏÕGš)·—ˆ/‰ƒ¤' x®Ü¼ ËL…·æ`Ñ+dýÀmí!µS·¤žÙ¯KPë ±Òá¥ÀS`Û©ûŽÚ±±ÉùÚ´¶”ék^°Ìio¢è8cws«ùí˜Z:ÑZyOTq**V0[6PÖÐö†3Ðæ¢IILíÐô^ ‘+.…¾Ñ£g¦Ý ?B‚:âzÛ[žb|My¹vúÈEÇüô·ê„,Ý0ø-B»f¡! eŸ j—ІgÄ£(­UÎ:±k3>÷¥§ÊÅÁBÿE,ƧÊq˜õ÷¥¨5o…›zS؇S㟗N‹Ý~h÷.~7þ^ŒE.%ø(µ{½ùb$¤éñésõ>öq‹Š#+VÍ΋ͨ}ÇÅj]ê£o¡“t 4Ή7½W@©þÛxa‰ô<4.ʯèLñ‰Ò ‡?èþ#Ïuòí®]àÚ‡û[_#&±+hV/MßöHjW["ç¢#׋i‚”ãçô#®X_調Eë§—,ÔM¤!F×):xˆ\;ñ/k*bgFCBw£H%Í'~Ý-¾®Ú!Ée¡¸‚‰| „Q*ôÚ‡àj>£©IãÐËEbgÿI8$åñÈCyh÷çv+)qÔÄâs©\u/E寽3¸W5<œ~O!*[]îqˆ¤oó¢܆|õsŽ^8„ËzaÁ÷îG—`óÂxRÿ1˜‰2™Á¢°„wü8z&nñ® ºÁ¹M(Á=Á :µÒO3┬XNßQKOæ›®g=ˆEö;BdÉG¶Gæ^áÄèùŸä_Á*gÑ%x|f#'×⎦gKLÖÒaíqqZL=ŒÝõ5pùéiź+R±³±–/M:Gš•¶)ù'+6"ž6E½+\ïÅ›ÿz^ÐÙDü9U·¥¼3Fm6, }_ †ªÊ]ÓÛÌ|Û`‹tÎkËoÆ”x›nŠÐˆ®`áz“’Ý”ênó ¶Ûu Fè “‚Ç"Um£órD0kƒ†áП}—»v1÷…$°])Œ¯šøþæ¢. å ŠñAtñÖ—:8Zûüjß—»ö,2 —Šå5\D<[Ÿ.eo)d« ´ÑÍÿDò;Øî?bVâäü[E:ëEVœ¾»å²asIhƒç@ZESsXSòS±9é^óg‘˜^qça7 M‹:¤¦Øsð’çñsqöàÇIóM+vôߦ®'kù'Ó% ",ónj’…ì-÷jÂhÒ%N$‹Ð9Y1e(,]›;Z½8ŠÁéŠÉ™,6ÁrjH¬‚nÄó/n­+ÑÔ_T xráHëëôªuäŽIbÁ «xJîüºòÛ¸µPÇÑöùñŽ»BðEµ—>f’ê-ÇiðÝ<ú!_ÑÝy< A® Þ–Gsij¸~šWÍAœIm¹ ½ò”ÇG‘’=ª-…+$À§ØÁïhñLÕÃoÓίÕdða5fÀ@Þ Ngígd´Bül!¶9INë¸îúN,¡Ô~Q¸–:S ·y†lzJÏ|÷{ˆ¥k[H¬ý`Þ€(Ù/ó·Îá%›Ö–€ òvw«WzÁX‡>ër†Ô-d• ªáîš/Á=È ?’«ºžÎþ\¦ÇæóD€©É+çÆ‹ÐÆÔK¬$(Å\eÒ“Ü1 ¦ÏöúIÁxCµFéÄ;¹ßCÀNä:ktÉsItðŽ¡ŒVµWc²B¼Ü6>…ƒ$tݲÇ7ɦɾP°VÁ/„B¥¹ùUɲ“â«Bÿ¨Ù’H'õ©à8ƒÍˆ´q(E>}‹I!i`i_ɪ7‘¡Ãî£óOærÅ°ÐØD†»Îw‡‡6þ˜«<,?ض÷éxwG=u¬Ý(Ý¢ÀV!ǹlO…ûå´¡™ 5äXm„¬ÝíÞ>¡ü$0bt~¿C¼#íoHî¼ê'ÿÔ$ü^P­*åC·ÐYØ©ž3ŠÞH1Ðut¯%”‚&PB²°Î )vê&!ð­š;…ó¦p–úöó ð¹rË`ú£nLÀ½Å”rãÔZ-#ŸDÐGÁÜŒV&¬Ðnpt"*ÔC*æþ[¨S.jP d&ɨº®ËbïE›L<3u<–N•«Š3ˆSäôA#N¿~¼É±åذ°aÕPmòÜu×êÐX2˜ÜP¢)¥GE·Á½€©ì8[`hЖ¡Á’Ñš¤× ´¤—6Jp­'{d˜Ã\û}CóS ªÚW޾ñ ¸Fø)uE߉+ÞDx?Î&­?pŸ2»¶¬Xéä¨D’t 0ª-Áç©&¿cO™ÝÉ´›’Ù/øë¶9kp7Xþß¶O«Ë^m–}4Sþ§Ê0qß›¹¸›/*òÁ>V¡Å{ørs—?âr, ¶م ¬´ÁRz1ÏvüÕf§UkpF¶tÄR·hOmóC'Tä6 èy‰3Á¨.k Li;jšÅ8Ý©~<C¿ñŸÿssçĸ€á(ÚʆòÖ–Z›K•ÿY=# ‹žÕž,ä„^)€¦4ú]•D2„oÒŠ´Ï¶J"Ý/GÉ5…‚º…5ÚáYŒÐ†d”ã1®ÜÖcú•ƒÅÃVg€ˆÙS„ñÈÁíiNût¨°½•¡tö2Œ'GótçmìKLšÚ„rLj51Ë +í(hí\qU°JÿWA#ü>cUóÆÙ’Hò~†ªúKEžˆieIæ2UûçØ“EK}›û#Q^tf»í¶“µ2èöz>°§ú2¯Ü•ÂTÍ ' Ÿ¹Ÿ5FeDIê&´þ@"Ce\ !™og_âv¡x ϑԟ%®AA€Õ°µPÿÜ’£S^êÔ‹îÖ³ùNÉšæY|;î×Ù Ù爲|(Ð-²w¥áf1©S³¤.ˆ²¸ÚÍèYì&1#E!Œo6’v»kêMm%1ŽNÍ­_ÛˆðS1û§F#S•ÝÔ´Æïlнs4&¢‘§!‰qÿvú3FÞÊèΟŒ™ª ¹À5Rsæ~+†¬JñÃmæ üùbuç¡ö§4ÐþדW“{N¼­Õ#HFþÍÊ}OR5ÊNø%ìDtøÈop[ïxËRÖm«§‘Þ[‚ìcë,h!,™oš¨íÄçéÂð¯þñùõÈóúãM ¿ô˜n¾`™®„xõñPÛ?Y=”<8F/]øñ™©Rû2vÝezP¶gçuµÏà /韖ÀøøNüZBõø`_ 9*L2ay™0 ÅVJÓ1øL5Yž§±•Áhs|þk!äÈÙrýµö©®¸Ïᩨ¥òÇÚƒ÷0ê¹”Çu‹/s ƒ½XbÎb•ä[ëÝ^¶ß©‚Ø2 ‘'Æ›UK˜˜V e¡ sx’Ò\¸ãuù„šEdS#_^Süï'êLTÁ6åR0•uØ!æ ª‰ÔMìéöîò+èíáò·]û®õ(·‹Ð2Z…P¶€Øðmõ§Ÿë>Q²ºeNºÈÔŽ’`ê—ƒ7*™.>¬ˆ…'kpÀ‘î=˜mÚk5Óh¼“Š•ï*AœÇÍÚR }…†¿£lq$3b_"ãp¡¾¡†ôþù˾7Ä}\ñ˜KÜt ;ß~ª×›¿÷[^#—S˜*Ñ`€k("/lü²1:(ÚI¬ÅãÔ Œ’Ê.ÝC.C/“þŽ‚:ZÓÖØ2‡·ýkP;Ë¿ÄÄjò˜váIé¦d SpÙ5*ÙŒ¯šãùœ^Á‰íÒ'A€Cà¬Q¢©½O#”±°¯mWRx( Ê®ú·9å"Þ[ƒãð@cÌDƒ’ÉýD uÜq'*€ mùG Ã$Ö FÐ\ëâ–÷¬‘*ÇØZ·L™Z÷°áÊQªºìÜ‹tÁÏ,,át‚þæë³Õ¥x½€€9þ —3e 7‹ë£Yœ ¼ËW[Z1.¥£BsB@…î<ÓÍ)§tÍmA¡mTˆy¤#Âe/ ê·†÷Œ5¯n™š1¦5Ó`tƒ ÁÎ\u4Øê'+ï7×y¨€i>©Ù¿‘/ØÕá’ÚeÓe\TFëõœ2i’O×nÞ¸<ï¤XÁ@–k1˜ò‹ö×Wðçœ1GPûsDÇg«ï—2ÿdœÚN(çÈ6âÜi†™÷úø““'²]Ux9Ú2ôKÚ VZ¯å£gè A:éâ‘<­s‹¯³²)`ž­$ßjîäjsÀyÓwà 1†ÍA_ 왕ùL*ö×vþFÜzó}sÍ GÁ. žlíÐËw†ikorÛ|0õCù뎤jåN™¿(Óy¹X^æ&ÇRH#ÐåÑwK—ÿ`ˆîcùA9¹ºÒxöqÞT+øõEd¾ ÒÇë¥d·4c¼_Î_$þϡ٠Î#s‚ù‡&K¿Ò£Mªûì$¹\2Á§©™xÕÄ-¼Ç©Ëø¢e|ÆÆ%€ øy Ÿ"ë!`O/¼Ô·Q,/ (ý@e Ëú߬‡Š]ý,*æŠzøñ;40÷ã´xšGI¹+¼õ½‹áh >hn,+|¢È+‘=$ª¾„¤l„žìoåÔ5úù‡èhº „¸?&ÅŸŠ4>ê +›_™§QÐÝP«aÁŧù唄²H‰ïI'o/}'Œ,äd˜âBn ‰%#íA1¼ %Íѵúñ©ðÞ¹ðä]Q°Á„žQÃ> l`‘T犭/""ä"ÏŒ,¹qã§;—OûŤ£C¼Ó'ý§r®¦^¬¿P/Ê“k²ùÑv üÃÂUóN7ñ/F¶óú^"Eò‚‹iêR4ÏgGðá•0Wyç~ÈθÝK×Q…€(@¼ÂL( 0:u°~â>y òe¡dÔD^²×„‰Ë¿ÇcÑ=Y¾¥a¾Î<¤ÖŠÚÎÚ„*‹•&$àµ}­€à¿DÛÿ}Ã?? ÔØi—pW¨*Û®§!’ˆºëù³frë¿›} 9œˆ®?¡Höž©‹Yd³ˆ(NæDýpÏ(>KFôX4qrÝÅlD)cKCà3·{[‘6±„_|ÚÛ‡¤ Û˧½˜ê UùÙž‚þ¥ ãš%c†‹®TþÌ<›$!¢±V¬àaZùªÇš–*`ß¾8j„ÿq^`Rº§×}ÉKûÝ/´J‚|2ª Ôñ{¢ âûn³8Ý`DhœcíŒnŽÙÃzdÍ>^åb’jeNhX¦M \U)‘Ueí ð\ÊÿI‰ž¹÷dÅ;Çx¶×Έ„$?Ä;‡í^ÊÀõ™f³Ã)¦váDÀ ñÓ:(–ƒ\E\ÓêJ_WkY–’ÔÇBwFƒÃXaŒ5ë3zêº{l·Z6Aµ‰êaC n °¼#!T !ãõ×9î¸Ñy»ÄüO”>ïÒ¿ÞaS$ë<°…ikn)\ÌFåÖêïæùÙÀ¼~:ܲ'R»jÈ,ú®rÙNÊ:1{]3& €—EŽ^Ñþo>WP‹«Rq¨C%pXó°oÛ]$v浆»—ØÃÐð)âeÜ+Â4sÂ]Ý)VœJ†JæX¯_µà,0µ ÜqŸ©pjpµÃ’•bØ„x„  <ø|~õeŒÊDµl Êžœ·Ñ×ÁÛž]Èøs"Í<÷Ÿè¿ àκ#ŸËÍNÞ—¨êëȽne&Ç]q¿@ƒÒ5Âø ’¢å0~ªæ?Àê)bG%Æýáº%ô‰­`: ·ã0æü…´=Þ¾J=“Îíÿ9K‚²ëÌUÄò&™‘(¥ãZŸx.Æq·#Ò}Ùköé÷gbþæß¦ïé1t¢†±i#÷ ¢5‚ŽfgÝÏj|ÎGõÎÖ?åc5pɉžÊBÿ-*Ï‚³$BÙ–°pzΩ"A»=9ú$$ù ï°ä£@þø¼&¬ªhAì ¬³¸¡ñW¨ôM×ÃQ®2»Õš‰ð2MÀ·…‰7[í&|„ƒ·îƒ©•*!÷¡é„VWEXY åðRç•¢PBÊÀLçë©ÖŸZtÍݾãÜÖ†}lfé³Å*éÅÐMfÝVê àªI{ÇžL'‘ÖàÉ´Dû‡ñ"êKýlï¯ÐQ#­#ÍP~ámßÞ+zyVÖœ›GÙ“zKõÁ€ÏÂê¡ê 5ª²Rº/Ë{òS§ß¢MéIŒÂ³¼ÄÊÄu³Ž8kV-¼9T1ò7¤ °ý]Êç˜K@;ºC )Wú[ŠA.3  ÑÒƒŒµã‡C|—‰’XDLJµ—"T^JµßH¼ä¹*¬´Ýʤ#cyÇRîÚ–'ãåÏÞ<é`ˆ›•Á«yˆ¤ÒÐ<.†Ãy°/n;ê®Jv†Ñ¾¬ÍªÏ`•|±[%„Ø  ™6˜v"†Øy/ÏÙÙ•Dþ&n\Ú~‹3²O› GÔi –*4éK²ÚRuÕIVœÀ;/WŽÝÉVŽcÁ^Ù0{d^¸ŽÂ{b}u¼_1³ÕäëׯýÐÓ•ïóþ¢3ôX7?q‹o{¸uV®uW3‚8{WN¶Š£íGæ­þà1õü½‡kñ\È ÐE§ aá†f3ηðwo>WÁ$¸i:2M MÞÈ™’ãD/ wªYjËC@&ÊX!+hD¸<ñY‘¹l‹Ðê>UŒGãª_GìÎÄ5*«[2â{¢’h©´î;‰þéæMf.°{µcÄ’Y€]™ 'úo€¬RgŒòô’êlP›y¨ DÐáÈ™Ä" 0§üYÒLûzýWçIú>Ñßl¼ÙÓ4'Ò¼é})!4ÿ6”¶óôåœöŠýŠyí‘o;“ñ^@{Ÿz€Ÿï‘:PÇÆ¥€sÆ™+ä™^бq¾XD¾ #˜}Ú+ Í›šÂu.ÐðÇéUOXžfÍ;… ½Ã@ûfÛwxáFˆ°¸K†ùª2§T§ÀÁewŸœô8“;ãr°,$2óY!*æšìï¸ÍF¼ïÅß–‡«TÑ/c'Öû©]b!Í‘üÚìGðÏ‹šwNïùÍ ÒÆjüÉ>& jbÐF„IöI[AWýOè¥l*ÃůŠ+'gØš¥Í¼a ‡|…¾­£ðÈY˜÷>íJ L9ï¤ôT¥úð³û›ÝõIl­£Z‡.éh&r!³ä^,±îé´bZœÝ$=ˆÙß脊Áœ‘Uró^F8Xg `c„ˆëz[é¹»,ÎÕŒ.õëÂèWTؔӤ¥Š*š#ï±.%=Ð?å{ AXÈGNöû®GÈÝI:¼n!8ЮBC Y–„¾K¶ÿ0ö×ÂY“ ×ÕšðÎ(ˆvÜG€›Ì!È}¼ËàÍÁÆŽYÅIœ5Ä<»bêš¹4ï"žv3Ê!YAXkÅG¥vç<ʼnTTþÚ¾ öÔphºÒ |ƒ¡óîyÐw”³?jÈd8Éõ¤Ðr¤¤ÊX§tÐ8ÄM+ý ixI@‡¨\~ !1Håð¹O·ˆÕšò‡ûñJ_GÒ·-S𝏒¯#âÔÌ¥*FCeáíò;'µx ¾i!ô9Pþkz“²¶Â³%IÊhsxaXüBÁ~‡I¡ž¹0Ù5ZÜɧ Üm%ˆ[•GœÇÀñ=U+’oR¨0úÔ“T“O‡bR@e ’sÄs>p˲‡õ²¢äWk;Êö)s€Sð¯p g´ì‡ç4vâµU+¥#«ßáË”ˆ„ÿhÂ^ò—ªT‰Ù'fËýWR*[ øna"Ê!/LXø–Köòæ ꆴ¢”LÊ 8p2^jµ)žVjß9»iª °ÐÆCøU›FžÓ×&|Ũ«3ÿ|zŸG3{k]—Â!U~´ ^x n`®ØÒi’!YÌÚÛgÿ ‹!ªÚŸpcÆü6cÚ €«ø36ÎCG¥WO‡5S’Rû0rž‰CxØå®Žúµù¾_hÍÝd¤ùƒº άø¥§H6z¦ÓÃŽŠ«~×ÇñeO,DËS}eì›^ V׋5QSj ¦8ª4X[*ôç^Ò%âïZ‡×R¥ÙµØ_äìªAƸ-lù_:;Œü;sï!TrZ`^z;†nË2X d`D@u$·w¶Á5Ìcö/êË;0è†áaP³ØkSÚä<#Ø«©¦š®{y‹ &ðó x¢Ÿ(ÎÍz§¤/E®ÃÛ#K’>| ö±˜;—qS´ò8Ûñn]”Œlž'CƒïÛYh êØÝ¹¿eŒtUY±Ä£¶k›t=Äê0“ Ô3)ßy×VÊã±J:óÒ„\cg&Ä–3½©Ÿ¶=g!hI5Ð bΚ>¦ÁÖˆšÆ4û´XWØ>òìAެ¤ÄšBŸhãZÄXþ¨éƒ#†crŠfö‘,|)ŽýC›n̰ W¦æW%ÞÁêé?»XôQioè¥9øu'7úÆSºµA¤XìTg=é¨H¯°yóÇ“,]Ž&œï¥G.U§ÕMÑbP&²r­óå¥Å X$IiZN[DReJîÞ“ÌÞÇцBVe— ½›ö§c>ÈüyöìH÷­uS{ €lV2¶TPŸiáÐ~,n¿›‚:)¨­‡_ò°‰Øfr¼¬øª˜;õb—Q9îvHVœŵï ähšAámeÌ‹––YfaùÔîײahƒgé…|òj-šJú;CX+Tµ¦u¨¾AðR+0škø#_­Sëû+òèPšÎÒ4´EC„Ò…ж9Ïîu{!øG{g$ÛÃU_­If“£­V¨¢´r2¼<§ êUëÂýÂÿ‚W(a¶|púèþÅ(,…7''g­¡›Ö©+·\™yl×:&"Ö&$BFÓúpïÒ­ÇËêÁe)?é—)3¼ˆ¾‹^ø =º‘¹|¸€°  „ïßDûýh,ÓSu1^d£ŠI=â°ßù Rै˜a1´äØO±¦TÓj}º óòÇ$ÁSáÚ9¹ýJåéûâ@æKÝÆQ:!ÛHÁ…Ÿé¥Á Ž"Ö6Ü2¤ GpÔ?Õ^?ŸW‹ÿH—R¼#a‡Ñió?®Õ+µfÜÇ^dRÅ„.µdP)ŸøM —6s2u¶6ñ=£1.´@›¬JœýÞ&«>«Z/§ÔÚˆ³BŒ„ðLÙÎU’Xº|<‡ì6FIKLEC:Z<¶Ðcõût jîÅßB&:°¯IÛîÕÃ]h/åY-„^ÿ\Vi}ˆ1„…¡…f€MYm«  ¼S.;¤ÇXHãZ•‰{0œP/:caź4xÎ3¢DÏÛ:Cs Ðyƒûw#À ü¯Eqyþlî*«†‚¬šN‡pVg‰ÜX+²)+2nrÔ¦8æ&M±gBÇJÒð›6 þ«Ò‹Y»:XÜìLè5ŒŠ!¯Íè0¦ÿYuŒÁ\4¨Ü“+ø¶F)¨ Vm5"sÔbd’)A.Pb)ºN'ó5PÌC­ãcÅÎÑY+¿>Ò†³Ò„Go£¹ —öW¸…ì“¡Þ½ ûšó ð—Øœ¦€¸þG:—ǧfé¦a·9)ø¦ˆa:žà—ô5ý É"kkSê½L™˜À« —ò·¼—iÖˆFÄ|—o¿‡ÙLNÙšHÈoæó²üK¸ röc!~7ºa‚úÝ-™¢“¢ÑÜc0pâ÷OhýЍ½î::ÿYþ+$:¡ø,N[y6nÜÇÂyn6Ø££ØÍëò `+Œx‡’¨Ñ­¸K¥à¹¦ª:6€*u=Hùž†p¥ô×/›šBy 85•†º`HÚ„¤rȧâ»d®aÆñY‘+^[„—ÿG• aÕø@×OÉýÔ&>új®OFsUý¼@¹œ4éK¬ïD½5Q.©æ'ªÝ,6î;/t&ªÊé?›ƒ-ã2O`Îäûä»r$50W8úZÙãÛjWùÇÊ ¸‚ÍŽ Ô×ZI¢‡`Ì3ô¥ŸyE(ðr&ab‚ó!Æ‘®Æ#\À+ dŽ€-ÄþJÅ$N—›4öð”CäÇuKs†Iu5- è-ÜkôîÕÿ!¤ƒÆ4YjV¡lU!igþ&é•k¦FV¶šH~ÞÙïMI…r½[æ Þ¼“>5ß,<¤u%Kð›÷´<÷VëÄ9›WCÙõ—GU­”øtnv: ÂÞÝHR‡$°u?xÎL TLïÖŽḛ̂‚”1׳ÁQi?öñF…êJl‚—k¹u(ZÞŒ©!ðÄÂPæ·ú„ th¥cfp#Flšx½Ï.ȶb l™¾OuJEFvYQ¿u¶TËI­,2Ã\³/fH¹Îå*ï ÿ$¹ñÁÜÃgùaê¸ EGÑÕ•¨OJ¤1D¦¬‘Œ 5+î–lH( ëÜÚ/×Ù(Úyyб©Çc¼ž(AàŒ°÷–óhdkQy¦GB|t^­í‹þc~¥:ˆ­Ú’蘳"ÞŠZc«¦˜aåĈ9ªzùàÛˆ†XÊ’mO|§—ܹaIKm“Üè (¼‰w³I1U¡ì]—Úùý4WRéÞÁÙ^Q×kÞöëƒ ·ë°ü6qË]²8¡ û[®[ÇDõ„@‡€Ïò¥Ÿ&LHúõ N9püFC†½Ãêùñk(Ö¼èÀ2© p¤sÒø ÀøQOíš"é‡U˜u#¦cj.~v®|Ï!gsQ„rŒ éè]a?˜¯=Ü™"ÜÚ½øë«'CDz'o±D•E—4yÍÌA[ÝÊ–J2ŒsËÉ÷@`7¥]¡¨¨°> •G)³Ö!/c‚…Ùe \ßú“ÑÕˆÚ’i?ø-ÇOk ñxkfDsìäHÅE‘f:¤Ï´Y•:t[äQlh~%JÁ{™â°k¹ºÏ=<[ĽAd¢n0ê6]osѺˆ¬­ô?í*ÄôB=5¿:òÜçZÀš¬o¤ ³Œ#šàã #:¡yãÈÄ… q(³=ËDã%€:§‘®Ðiàª(U“ÆÛAÊjœSýg ËÒjÛD« $Þ±ô/Ír¢çòÐÏwj˜FÄh|§¥—Zµãí?Ê]VJ³4vƒþ<$Z«“KHþÈ œ+ÅËbú (Ѐ$ô\¤¢=#¡ÿ|ͯÚýU»»ÝoåÞÃ…‰}õ1΢€Ði_±‰·˜óûNIôÛƒ­l-”õÐGæ·ÂØ-Ú§BTÉïK„€yÈEó¥I®Ý8dë ¡Ð/=Ó6K¦øg|²uôÏ}Y†àï&)—Ž4‰Îþ¡pN¯T+}O (/Ãï6ÕÍM­ÙÁTjêÇ ð„ÈöN2"Ƹ¸Ñ0š³e…Ö%8Ž3’ýíDÑ#?I<Ë,ëV•‡ZÑ]‘{dWu™ñÍå®O0\¹æã¿TþÇý©TÑÏÃQ½Z>‘}[¯d‘¡”Ʋù"‰p£çN@†ÿr¡r8I“øëTXìóaÿ~¶9!*Üü~Š“FHF â®ìèP*~`Bä YÙ¦BçyÕGCYôP-»¦¬âý˜|¸{¥|zySaj,ßFåÓ²ïTXA×ôlòÿ€qylyðP£ºÈuëœ0Pc°ßa# õ¦/Æ“AþÆEÃÝ¿ÎôrCÁÍ\Ÿ±´ø$•.³Hü^V~€Õ·l‚né]•l®ÖË©š]Ô³óÞì6LWHG¹2Jˆ9z@ß×âÄ‘—?&ÜÀP¼V˜¶’\|¡¥ë”ŠYXón0€ÔUa$N°³©çñtÜ«ÜG–ì+¾˜rÕ*wàåøwœ·š /ƒ'@ H³õ†‘?ø}¼ïC°~2æLZ·¶sYÇŠ-Ó ¾‘ÅŸ.3‡UÁ5š9­ˆ¤¨OŒ@k¥´}w›y ù0²‘‘H„VÎ(|I<™»%´š|ì )úõç¨!‘ûÂÇÊ; °ïÂ8ö' 9?9£ÃZ—fisèêð0µky«ðE«õ# Q9Y¯Èàù&à¹^Œ&„îöüÓ Ï—À>âí ,qþrë"#µˆs­H%ÈDÄç­S°fƒIéýƼîyëeÕ€³§LDåíóŒÜ¤‡Ë驉ëÙ%a[ÐÎÀ€½ef*ïÞÉÈÖËø/Á2Dƒ "ÒM­IÂvõ²³0Àµ¦1\ì5ñVÆ3c Å4žbù‡à*üÿ6kÓ¢×7ŽYý;FŽÏ‚Õ9È%lNMþÈû`qOžÑŸL¾.Înd¤0 ;*¬ÜZm|û"ðÍ=¨õŽkäˆ&¼ßÿrÜ AH#£.,ZW¯sâœ÷¤ìWD×`ÁÝ ?Óa·ækõç^ëÜÕòNÄyøßHð V×¶ÂjÛ>¬Oh d)X² $ö¼m¡0!Ä6k²Mâ*žUÇ[ j;ƒ`(+›rˤñmú!Üh®ý7>êa«Cs†‡¬YžŒ}(ÒtÉp ?Nœ—8¤nãS|‹Ö/+%Ÿè`YE *ÀËÿslH|Œžïæ‰ÔrÊþ¹Ûž°'é>€_ÚpÌló·lÄ„0FjãÑòhÐמ·7< Ú ûž.9~X¯ÊìP³Ï寛§ìž‹ÊœH²¯ØÐ3h©Æcàøà„÷‘/†ÿ!s\IïÙmMx:IS±ñi©ÍH7?›¼tUæ)z˜p%ÅÜ… >iòf!eøe§44§hÖé*\õ_¢•ž×ˆà9–è¨^@Í¥ð|ŒƒÒŽîžlùå“[îQŒ„B*´øÅÑOɦW—èÕKhÃKÍØ£#•ª¾ýçAp¤‹“Uey0Œ§äÙ¡SoS/Ôí‹ÚÖ ;ðÍÓ9ã,ÛvTù ª¥áqò ?sæÃ,[¼Þ;2?ŠŸqt`§/ÞP8Cº3¿£Ù)eÞžÿ?Iu„©˜ÛÄNkdq4ÍoIpøVìû~ˆ±ãi“2â–06è-uãq3k—8ÄÃň°Oßiæc²…ÊÚš«soÔ6PöÔý¿{â´SµÑ)9'Jd­o¾fåø§‘)Á¼ˆçGÂÂkdëé&2ý´©KŸ6Lôœ5ð[ ìºô&hí§>¬"¯¡Ï⇬]ýĬÈ´§]âͨ$6ŵ‚ÃÑGZé‘Úÿ*3º½¡á把°éä.ÂíA9ZÍ\§N6âi£@®BÜ(ˆ7ƃê¼YtÿW}‡öÓG'ƒ(8ßnA%*'¢uˆü˜@V&ÞÆ°^¶§¡ˆëŽ“§ŸErŒ¬Õ «ûç]sòÛTôz'b¡îwq¼7 Ü©¯‚Œ›órru¦ê†f´^ì!µÿàGæ?¿¤Ø»êoÉ•EJ2sßó}¶à%T.8±Û;\½q«2Ôa“1SXÐèÇŸUp Kó€ÙJÚ"iÆÄœ¡ó{ž»Â«–5,{Ô\TýbÓSG%Q½1-áL.o,!R~$úÜõÃPßáÜž¸zE©ù+~Tã]½Tï´fÙ–Ée2·ªàÅÍh\MÅX5 l_З<xf(ãá 'ü­«±çaüd¸åc+Â_ð°(ý¾2Å‹­Ë%¦\8hIû„²êúû4¸,?û´›§Ù+™Ã ò¥,ãEa³ÚOVrø>äÄ[AŸô—K¼ò¸”JÙ±6Ÿ9…úþÆ „k3 »Òs–p0³ÊOf^)1ä¤Z,8«“­+B^îS~‘< ª†&Te×#f²ñI6L“ùóÏ@QH_¯üä?M{øV®Ç:RLÀžó³“NϦÉ5ÙêBtiÍ7¦.?ÙÉ{é'2$Y„;ÓÞãÏÀh{o^º¢hñsW^KÉÂa#VT¾¼&j¹jjSÆãˆh%ºÛ¸0:QïdÁÐ﹇Y™+í@Ó¨±Ÿh*ʧ)Šüy~wÍíu~ݵz¦}£Ä=äŽ]a¯Î©OhÚé470"û³ËHhˆf›¯j•„:Zž«N—÷(œ‚‚ZÎ’7Š0H?ÈÛNÃê“ûÕnÂ0ƒœ„9ôΑþiSp{’@lÊYy ÝdÔi²ÁuôÿlRÁG¡Vçž&¸ –„]Rä;HF½Ö}@X÷W‡r»Ô-†+à „Ã…f¼ÔIòbÛ¾ø íÓØ†Ä§â)j$ÁÂ×Íi‡.GŸZƒ0\‚ª†µú&I!¬«:ðNyÍú®ë53ß)';>ªÃ‘ØÏ³åÅ'N€X‹X°ƒ& OWÐÄôÊëWa 6$$h9Dns¥·ÎgO±»xë,H#±î£ID! <ͱ4ÂxÀ›ã$Ù²)¸Õ‚Óÿ1vð0ÙH훫G<ª ?“í˜ú-7¸­ À&¾×v®Hðó¶¶ÛEËèêèÉ!Hè½FU½_i]ª"ú዆õ~7XçA!BÆ~m¬å›*k_Èz@v—~»è[ל¶Jj l‡7ࢠTöÒ=ÀÖ¡>`Ì«ÚΪÞá ç8B¬Ÿy•ø‚Ê_3pûõïë`3ûL€Q‰’PiL¹r.E§åâlÒe!Ztü9q(¶;JD‚s²‡ÉSúäÆÚ=7›íè fzäsþ˜]ߊž’±ÛÂ1+ü¢V–ÉØ´éÊU,W( aÒGâTpOè2ÅM¾!õì»#[…„ N‚þnpõ? ³—}žÓõEü"ùcÛ(™ ãÜ6ë ¤<°yÂf² xÃå¦-`ÆN‡V«b,ÏwbK?”K–K7ù÷ŸühÇ ~?ò²± /C&¡ÎÕÊ”Ò+µòFcÿh$óNHÇ$ùñ{” ¨ü¯R#ͶO#=Ù/ἎòÌ!>³ÑÇ‹e¶qÐð.1ÃYmÈ)£ –~7ÕÆp1çÙQ“Í-ÅòÒ Š.füªLHr«þõ°-C›ày®Ý„¬—!àÝö´?ÀÁêlmµÅÑÖlŒJ8v¡¥¢fg6[Ö•z¯E¥­y+óL;‡q}ÏÐÇMsGRìÂë4ÜŽ_d=#³¸TZ¡Šy]ïZ¸Vqž’@]¤Jj&ä°®hürIg[U=ìÌ×› É7ð™¾ßßô5¤p80y„/N@F‹}Çñý´¬>’§ûkÛ_¶ÿ6Ä_ÛeþÚV‘>}ûl^?µóö½¶€ý´çí§ÉóÜ¿Û`/í¬?k×í{ýµí¯¸aðëðøtn|õ¯ÛK~Úh¾§¯öÖkûkê`‡Ã¤ßUûj`åFu<öó´ê!5À„ÿV eJ!¶8k C‹]?–¤LÉu–Rb–àiÒV×& UA‚‚~nnp†‹¾âÉÛ(pÚ5ÊS@ S!{Š>*«B­–ÿ.2ÚfBÀ £y÷N¯÷ …:x߿ǹ4ªº”¯j–隺\•¨M4u§5Ô]þ#¼¯eÅ|ÿ:Mufýó <;†º›ÊÛÉÏðß§Ðä~B f¿ýJe›!à©b*ÿ|ìÓuâS‰3ÌëQqÏð‰Ï€ž·ø>^x+ë¶Ã1pàaµ‰I_Èý&Ç9P?’`oK—¾oBúD»µa)?‹ »· ¤5H“UVÈêoèGúSלeZ 0RŽYkÙ¤¿ïj¼×it¾ s¬Z 0òZh®:(Ä ?áÔ˜4‡I?B% ÍÅ1iÄz˜Ôì"aôº“æ}ýi‚l7<”(Ì(­¯ËD‰XÒ ÅøÙU§ž(²“Ñ×âûŽ”H¹*e*ÝêCË]À‚\4q =Õ+¸@[¶KJ*q>àݧØQ¼æjê"nÒ»ŸQv«…u‚ÖÐ[ŸC|¯Ž4´ø`›*(Žé¹ª¾x`ȾåZ‚†io‘ FÈ?܆%ÃzgÖ‡ý͎ϱ´HÙ–·@˜Šš²ü¯ÖÕºá~¼Nö´bMÝȡǾ ÃÃOx)IfêëˆAc.xdˆæ^÷§)õŠšïÝJ×{{mEG ȃàÅÿ~òD)ü-mõHôRLTxù¦ï©æ3¦}é¯Åʬ¥èü§õf‘ºòsâß¾qDawÆ;n«­>v­ “¸1½˜Ò7‹ß7½‹’±à˜i˜ä=Ÿz8c .NÝåÂàªsÓ˜2ëó _¿jTŸ+Õn¬N»¬l‹9j»ÎÚ%µî¾ê¾øÉá“Ö%zׇ-§ÿÆ—Ÿ*Ô¦ÈXÉ2ÊKpglƒq Ï“ýÒ8[Q¦z"äk‡®6Bl5™1àY¸»²c“àµû2VÜ)ºt–è¡ ÆÜG|‡€Cg¶¥~e'òB˜IÓÌ×u8“ÂÑ‹ÞVÏ$ >½>|§K ˜ã{`ŠàþâË'[µzvh–¯LM¸Œ#¡<@”œ`èe@r&&óÔb¶ð‹Ô·m sëú“]\=ñÇÏÆ½Xì¸GUÕ*´¸Û·(+¥ÝÛZõ§˜ZªÛ´úôœG(ÉÅšc–fìû³!™†Ø y´K›ZÝá8êŽ ye~ZšŒ-[ó_4b/{¿9H¿ê¡"OÅ’y=ê‰kÜ‘´§°A¼%4Ïv|Æ™"!ìQQ:I瀥sÌʆU5Ø,X7kv†êG…Õ„c&‹½ÛöTy°=ÏÞŒh¶3i:Ƹxçv ‰~W¸ïNVÛãeò3¤7uÁ½gÝä¶÷E–ë¶J*’]pÕ5ìbÌRKÕ¾åÔü‘8]ñè2ç›]6®è®­³bµ{ Pešà¥Ú|Èp„b'] þIårþÔ³¿µ‡ ÝþT`á†CpÓÎ9ãׯÕcÚÝ,ù€XyÀyl{«ãgó‘·Œ‚ýˆr©"ÁÿsV‚],ªÙØÀ6ÿ^B¾óýalºÃìzô5°! Üâ2þÐe®ÖN  С , k7TïøGg¾ôÌ&ÌÔDf±*F¡ÍKŽ’äæŸ¡÷ù,Ä:bûƒº©7øÓâŽDn1éé{»x…ÝF,ÁG—zï2Ëka RÞÓ($‹áÙc´ó—õ{‹Î¿¶MSH§Ž)Tp¥*U #)!ø/uI‘ ² és/~vjr1’»¿2þUмûÿ…÷»¤fÔ¶Bkú#ùnܸ›Àìy‘R)F2@Êã˜k,_EÄU ÷Sº³üÇHu+OÓCª©û£W©ôöÙ¢ñwÇ6Í÷—œ™T2¯XURPS€y–•6ýtß4wOŸ†r”£ê7eV¼Ä’öãu¤˜òjÉ YÔ;èÀ £“,7ôzM÷Å9~öè:µH/¾p>îÊå¯ù2{Ö{‹2³cñMp¡^JyDæ¹=í¢@¡'=Cî€hF —i-@H­ˆÿÛó§„–Siî,ñ­Šg5©±µƒ˜¬déXp¨U‡&\±,ïì#wѸ VMv´K.M²›KXI»ÿôn“Èãò ˆûö´ è3ë†ÕÉ|wËf¥ —½!k@ö8¼¥ÀäŸ)êŽWs~~ɇªºÃp·aEdµÃÂ9³w.ù’«&ÒRS{+JPg{¸jõraø—“5D?0¬L!œÃ)Pb•G3qvàEZ£ÕŶ\Ã\Vo ŠËõ‰îÑÙFº¾VÊ\Ìg|_~¹_§¦—Ùð.áÓ–@é'Ó·VgH3ExŽ¢> (Ô™€´˜ÈR¦ŸÌ2 —=•¨ØÍò˜ts·+àžÇ”¶ €ÁÚŒ øA7óŸ± [ˆ l䃩«½ó#w+wÀÙG›…ãVBH>´$—·N9¾O0c$T϶~¢†ƒµq ·&Ew%ãB;M•ËsxUp:¼å§o' ù¼1;ûC 9…ÚEš;±bTÕÖ ¤oÆAFÒ ü&¿¦ç5›ö÷͢뽲ɺv’1èð•®^ôÂ#ñwéî:!Qª+…¶âJ¼ÚZiÚ¼Õ¦¶”dÉ ½Ç·D¡‚•×0±üÌöO×zø f ”îÌ>äÂgØã‹Ïá•ÞS5Æ)ŠËÎ?¢ ­¨GçÒ,]¤œ%¿¥°âmtbG×n™.«m‡fâgÙÚqºE\b4ÿ6åȪR%3Èêàé¥Bt²¹éWvZbžá Nj°úÅ«"´ý9ƒEJz·JÜ0b`³N7vµ¢-#³õ•»¼g,íWÁ"œR#sš²K·BÑŠWبQpx—Ð˹ÆYg;@L$ýí5]^½þî¬ý|(Ì«XŽÐŽV#N—:X°·Â#,M=í~ U‘þ¹C=ÕûvýèÖ“1(o¼B\öÿÅÊa„×Wf x3“Ží^pª®ÊÖÛŒ¿ÍÂãŽXªW\U»s8Ê¥Ü1òm¯‰;†2³×—ó›Ô¥XÓ† CûÙ ˆA_Jw^ó¿ëÌu_2ò?û´Äï½ÖÐÿe‡€¡ßî:‡RÀ–úß;]ÊBÊ%ÛqÅ¿IŒûŠþtSLÝì!¢%ˆpuS9Øãé õ)ï,Ôš*ÌZ“KV6ŽCX†ÇøcÇ÷ ™ŽÆ:|óâ±ò#èšs%µw>±îÞû?îiV3º¬3‚€ç]¯±C ü캅x¤¿Ä…e°b Ê öéLQnóáqÓ˜v Mƒy,Ô™¸ÅÇ{ø‰ Z3‚Bëx üß–’uûO˜*uªIÕqS"†ÍµV‚ýã±* Õmg®,õòHQxéø³€¤0YE]:lYëÀ[D½]s]iÕ PfL €°|xr»!-¬¾z®ª÷¨eFX½Ï¸ñ¶)4š¿¤5^r™L8éDr»ü:oêчɄö‚z;rèÔáñ–h#Àb+Æþd§Ù®ñUhWï 9¹Úê‡jÙÂñ}¨GöL—Ç¡5½BŒ™}o#jØ@ ©Äñ$ŒH²Ø,ÿÙipe-7.2.13/src/ipe/controls_win.h0000644000175000017500000000437113561570220016476 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Special widgets for Win32 // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef CONTROLS_WIN_H #define CONTROLS_WIN_H #include "ipelib.h" #include using namespace ipe; // -------------------------------------------------------------------- class PathView { public: static void init(HINSTANCE hInstance); PathView(HWND parent, int id); HWND windowId() const { return hwnd; } void set(const AllAttributes &all, Cascade *sheet); inline POINT popupPos() const { return pos; } inline String action() const { return iAction; } private: static const wchar_t className[]; static LRESULT CALLBACK wndProc(HWND hwnd, UINT Message, WPARAM wParam, LPARAM lParam); void wndPaint(); void button(int x, int y); private: HWND hwnd; int idBase; POINT pos; Cascade *iCascade; AllAttributes iAll; String iAction; }; // -------------------------------------------------------------------- extern void ipe_init_controls(HINSTANCE hInstance); // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipe/icons/0000755000175000017500000000000013561570220014713 5ustar otfriedotfriedipe-7.2.13/src/ipe/icons/mode_arc2.png0000644000175000017500000000066213561570220017260 0ustar otfriedotfried‰PNG  IHDRשÍÊgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<3PLTEÿÿÿ?Bá?Bá?BáßBÿÿÿ/šÖPtRNSŠX?ŠÃéü¨>ÍXåwÙbKGDˆH pHYs  ÒÝ~üSIDAT(Ïc` 02áàãC“âCDé hÀÌÂÊÆÎÎÆÊÂŒ$Èœ\Ü Ü\œ<¼ ~TeØ%<$5ʰEG€ÓVÜÕÔn5«÷@%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_select.png0000644000175000017500000000116613561570220017710 0ustar otfriedotfried‰PNG  IHDRJ~õsgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿ‡Ì¿ pHYs  ÒÝ~üoIDAT8˵Ô?nAÇñÏ®m‚ã„ D¤á_GAAQ! å œÑÁ8€G AJ "B "‘E(B@EˆY¯Ų8¶wEfš7š÷ÕûýfÞ ÿ{$qC攑Ÿ2£j X5ñÍKŽMíT‰|°âd=r^Y¼áš³Žÿ I-Š,ñöˆÈ_ ¯„¤Å0~E?öãU 2Ã'æE/YŸµ_Y0‘H]ò¢IëÒ‹*Ï dI«Ì¬•Tb]ÖÖ–]Ѭ—´cǸ¯­U6Qs6¹(žzÈ{vý‰Z[kÙvÚ>Ûµ§oT"S÷°BèŠ~¼ ᦠ:u§Üà‘»ÖØvVÍ•†Ç’Ëxβóúz®ëömºÊª-ß IÓhÞ‚†LÇÇwÎëpÛ†/М”ëHäºuåžÈÛMLŽñºé„s–…¯>Ù¯’4}f-8¿ñz€TC¹|ü%üÏù}ù:ç9%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/paste@2x.png0000644000175000017500000000404213561570220017107 0ustar otfriedotfried‰PNG  IHDR,,„ZgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ðIDATXí™»ÜÆÇ¿3ÃÇîÞjoï¤{l|'ÙÖ©°šØRe8µ¸.…€@š”.ò¤Š« º@Rº0 ÃnR$AšÀŽ`Ù° ]„;Y¯ÕÝíí’Ë÷ü&Å.¹$—ärïôp†óøÌ—¿ùÍpÈpN»uëÖ¯ü1Öª*§”rc¿¹wïÞgçéO;/0€o½µÓº~}¯²Ðwß=j=~üÓMçfg©tçÎݶí÷4MëÑ­ÍÍîoWWMH) Ë !0úè÷OÿÂ9ÿkE£v»ýõÝ»wÃsüQï z—E”n~øÇ7v~¶Ùh˜ Ì4M(äRF¥Àœäû~@¹N ž?}ú²Óÿò÷ŒA£q?¤ð«?~òS)ðÇõ®4ZêÁ«­¦&8/jÆ•&¾ájïÝ|QA)@! C06ÿÂâ<]דî4MÇWÿù×¼ûQ[Ÿ‰¬Rè$zxàŽ#W^ÿäþ«q~ƇIÐ?s¥Ñ[Ó ˆ``ÄzP\ ÖŽXC·»ß÷æÀŠ`óy¦ÙÀjw ¡õ¦†V ”$ôà˜ Ð]¸¶­è›ç}Ÿ+(!Ĭ—ó¸ùËßáâÅKI™££#¼øâ>4MC‰ig3iTJ&"*Ì×u:nüúØÙÙIòƒþþéŸÐî ΄ÆS*ÃX%ˆØÝ½!”štî8.gŒgϞ²†S%Ë.ïõzh·Wr}¨d; ¶£bÒåJÖPx¦bºn‘ÂDTéŽ .ªg®]Û«T±.x~¿o¦R1£žÂE°qãD×õ–„+W¸ÙlNÛU ñJ·äæG¥¨Ó•ƒ ÀááA%h6] ·{õêUèº!DʇUý½DR!§r —]š«£AÕ듺®CÓ4!f.¡k« 8þ:N…ÆøS„аµµYWœsž\B!>V¥ }8Þ-)œ]šû­aX[[K@c d8ÛWMàœÐ‰{Ä9Rƒ“ ÏÀ[­Öt F!hú¾Ž-X8â`>Ð4ÝÝË©’Õ¯? UÌ9‡e[¬úöb/1™©RJp>Û³2/Í‹'Uüú)KDx´ÿ#>ÿâ>$o.<™^*™tDÎYÍU+;©ò`ûÿ{„ýÇûƒ‘”‚¾ïÃõ躱ãÀ”.åV¼ùI-D¥D\1(c¬TÍ£ã#~€í­„àP p'''xuÒGçBÁqÿ .‘( I(%AÕyý¦a¢ÕlÁ4Lض Ïó`Y^÷aÙ×C×@¥UO:5ñáº1µÊO9çà‚ƒˆà8Æã1lÛFÿè%ì±…Ñé››@`-œ>DQ@*JÌ+\õúÓi" Ïóáº\ÏI…ÓÓúÇ}8ŽƒÐó±½µ…N§»ÿì .¡f)“(!’¯ÛøÐC‘YŠîcÃa" XÖ–e¡ïöa- C4L½Þ6Ö×/¢ÑhÀ®vá,p*CX²‡.¾ýö:Nrþ >ªf<ž¤“\΀HJH)A$ElÛÆÓçÏD¡çAFÖº4› †@y<¨Èͺ™Ó†UXXµ\ÙI»EãøŸ8ü×bY߯Ìe2çaq«*ÿ<»ÌëÓ ¼é5)D`ÖAš— ê¸`ÀAæ†o45˜:A©ýŒçO6瀒çªrOPj+“!µL†ï-¥¼P1MA8>|âýc÷’1:µ¢†à“ÿ;E;ÿ<•=8‡A½„ÖŸŒÿ=… ¬+jÚoï˜ïlïDRé `’PoWòšŒ3g <8¾z#6?œ61Çëù[ºŒÉÔ5÷ãïÿTÓ?k´ N%tEXtdate:create2016-01-20T14:40:38+01:00ãåÃS%tEXtdate:modify2016-01-20T14:40:38+01:00’¸{ïIEND®B`‚ipe-7.2.13/src/ipe/icons/pen.png0000644000175000017500000000046013561570220016203 0ustar otfriedotfried‰PNG  IHDRÚ¹¯»gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTEÿ€€ªtRNS@æØf pHYs  ÒÝ~üIDAT×c`@òÿ °±ñq‰!‹CãÝ>)Án%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/stop_32x32@2x.png0000644000175000017500000001122413561570220017621 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð‰IDATxÚí›ypç™Æ_wÏ)4º8t I€ HìØf{#ˆñ±1à8v¼Îºj·¨M*©Jm\•Š·’]×–1¦ÊÙr*NUŒqì…xÇÆ±àØ ŒVÐ :`¤3£c¦ûÛ?4#zzz®ì?ûU½õöt÷|ý=Ïû¼ß5=‚kXž„Åøƒ ®e½¦"%üó÷࿯U…âZUô4Ô ø ñ–[JV­_¯ aªZÊì°â÷Høtâ¼”H` «‹ß½ù¦!c±Gÿ þçZ´[½•<Ë!þ¸ò¶ÛŠÖ<ôªD"(º>c†‘l‰óÖs†‹¡*0¿¾ž’‚ÑÑÖ¶iat€“WÛö«VÀ6X‡n¼ãßí7ªSþ>@êºý¬jHDÞ|Þ¬“ϯ©¡¨±‘Ž'øÍž=×D W¥€m°BqøskÖønß´iüÿ8#c!R ì?B„åœÕOŒ c1,_ÎÜÂBq¶­mãZÃho†Suž‚•ª‡oX»v&ò~?þ#G®¼ù\Zâe*]gÁòåû|¢³½}c“a|Ò ù«ð¬Ô„8túu¾Û7lP¦.^Äô(H9I³¥Ÿ¬°o:7 ‚”,llÄçñˆ®ŽŽš¤<Ù g®;[à&UˆCŸûÂòo¿ï¾ð~˜œÛ°iɰoxºkSHIùòåÂçõŠ®ÎÎ/¯‘òøh¿nÄÁ¸õ®»ò>ÿÅ/*“.0tìXeom¼ ÙÀgL…øñT0@yc£È“Ð$å‘ÐuÍ xnV„8øù»ïÎ[uï½ÊÄà C~˜ 2™ï#Ì-E&5ÄËd €P*…×åRz»º¾²FÊ@÷5#` Ü¢qà¶{îñÞrÏ=J¤¿ŸácÇR•#x[€¹¤€å\"é&„T,[&\š¦žïéy¸IÊ?4CÏU°nÑ¥ùö{ïõÞ|÷ÝJäüy†?ú(}ÃsŸ ÀLç¤ÅOÄ•PÕØ(ªªžëí}x­”‡›¡÷Š Ø «TE9pÛ½÷zoºë®ð--3^–^ܶûÐvi ÓøÉ`EQX´l™p8Êùžž‡ÖÀþÐwÙl…UÊLä=7­_¯DÎc¨¥åÒÔ1Cn;ÇÇ)îìd²¨TÓ#rh-ŽÉIJ{z˜ÌÏÇP”dðñ :,Z²D(ªªõ÷öþÃØwús&` üª(Í{ß}ž›î¼S ÷ö2|üøì8Ÿ‰w(DyK ž@Ïè(¡yóñF_IqLLPuú4Þ‘òÆÆ/.N%Áâ#ÃÃ(Õ B‚6Ø×÷Hüî XëOiÙV¸US”æÕ6x>·n2ÞÙ9“󆑹¥Râ¥ü£˜^¹’s{ö  AyK j4zEà‘U§N«­¥÷­·P|>}ú)Úô4Öõ¥™ Ÿ=ËØÀ7¯Z¥Ü¸j•GbÿS°<£¶Âj¡(ûîØ°ÁuÃÚµÊxG?NŠtºñÙ=6FùÇ3õÙÏÒ¿czy9‘¦& ÷ìaN?¡²2[%È4Keg8LåéÓÄ/f`çNôòrBwÞ‰oï^ úû+,ÄPÕ´ß—ÄÓÁ餶¡A‰J鼨ßÿp¼Ó þ¶B£¢(WoØà¾¡©I uv8q"§1Ü=>> ~`ÇD^BdI ‘µk)HPZz‰„ «?g8Lek+±º:wíÂðùB`äç^¿ßþý 0æóa(Ê¥è'V–&"&¦ Ã940pÿà—ûa L) a¥»¸8ï†;îP½½3àmdž5)/EþÆ|ñEðz“¦¾±Å‹¹°{7š¦Q~òäL:Ø-Í‘oo'¶t)_yYP€¢(!P}ÁúwîD”•±¨¯5Km%c¸³“‰@€[o¾YÕ|¾…Üšx^ª&…‰´krkãœ>¾`¶oOo&áâ+¯ i þò]O"1áSSTtw£×ÖâñEd<òV3æÏgpûvœšÆÂ@ %òÖb¡¡!!–4ÌÜ=ç@ÂÈÂ…8úúÈÿõ¯“iŽš‚ØÒ¥ ýüç¸vt X¶¾ÓÓTöö"kjÚ¹Y\l[¾ú*AÀç³|Z<–ëŠíM™gòÊJüõõ”lÛFá‹/&7ÔBHlÉü»wãôz©ìêBÕuçÔUçÎa440´k²¨(m=Â0(ݲ…9ûöÑ=w.ã.× øø¾a:2¤ézv\ Rœ?m-…Ï?OÁK/¥U£¦†ÀÎhùùT à™œ¤rp}Ù2Ï?ùùöÀà·mÃ{äÝ……„œÎdÐ f2²lȦO\H0çÎe¨¼œ‚;Èíµ´*B WUܾG^•~?F]#Ï=—>‰@))þÑð|ø!½ùù„ŽK¹oÓû'H˜5)mç2Z&ð‰9¿LÌk€Äuó1()UeîŒPU">¿-uõg,^ÌÈöíxwï&ôoÌ€×%âϼt³AásÏá9|˜^‡1óÐg‰´™Œt×2`o&H^ X+‚@a!RÓ(ýÉOP§§ ?úh øÄ±^]ÍøãÏÖk>{¬ëþฎ¥Ûé$Df¹§½–FèÉØÉÜñ"l æå¢Pú³Ÿ!4ð#تÀ®$E_×)xöY\--ô¨*!ðh’û,X›{ÈIf2ÒÉÝ"Qa£† Û ªJ髯"4ÈçUB"zIE×ñýð‡8Oœ GJÆÓ€O‘¾¹?0ƒ‡Üû€”Ž/¶—€¦!…²Ý»AQ˜Œ“`§„$ùë:yÏ=‡óäIz¢QÆu='ðF,†ŒÅf}¢R¢kF8ŒnY˜eî²Ïö›‡ÃAÑ믣¯XAlÅŠ´i Á½o®'8?5Åx,–ÚˆDˆ…B““è‘ÈŒŸšºyï,-Ew»‰†ÃIé›vHêùsoÌ!ùúüù55(Yö„ÄV®ÄøÍo(v8õû‰NL ‰ŽŽ¢c¤›ÿgñvm¶Ÿ 𤕔6¿Ú¦¬êLæ‚E>ÔÖÞºLs{EQ’,i®_UEø‰'p—”PSRÂäéÓLtw ¯|:­&`2™‘§¢PUR‚¬­%òýïC|‰œÎ¬$È ÷»¸ËËYq÷Ýh‰)ï•‚O3 ¤W@"2"%NU¥jÞ¼ð?> Þva“‰„ùó ?öžE‹Xyß}WLBÒlðrR ›ì­„H)ÑT•Êòr¨ª"òíogŒ¼"ªßŸÜüYΛGä›ßÄSYÉòQ­óÿÀ'aËF@Öœ·SJÜ‹jkUU„{,ãÂFÇk¯á~æ´#G2¦‡1>‘¯9ÕÕ¬üò—³’`6s dU@Nàm€#%§“EõõPYIè[ßB¦‰¼¢(Àñúë¨--ø;:p¼ý6Ž?ý)-zYáÍ›™SWÇgy$- éˆ1Ò( u4 0Œ™aÐ|>ÃÐçr»©Z¶ Y^NxófðxRf|æÍ íõ×QNœ õ­·öô¢Æé„h”Øm·¥D*Q—QZÊø£2ç¿àÆÍ›9ñòËLOL\ûa0iq‘eèsºÝT­\‰¬®&´y3ÒíNm®[{ã ”S§hݳ‡`ÏÌOw}--tþþ÷h‡¡=j«€Ù*Š‹ }å+xjk¹ák_Cózs/sóå{ÿŠÏ|ÊÊÿêW‘.WRÄ’8öîEimåÌ›oìêJj`ß±ct>ŒöþûhŸ|b« Ù&Ú´‰¼ª*–>ðÀU) ) ñÉI|55Dúúf^t²Yòš%:>4D‰Ï‡£·—èÒ¥)H4\{ï=”S§8ó«_1|æŒm{U¥ÚéDª*²±1eÑ•øììêUåâéÓ¹OSf¸ÆŒ©©‡‚ÃÞºåËïÂ…—H07 „‡‡AU)Å((@–•¥ä¼ó½÷P[[iݵ‹@[[ƆŽtu¡ÇbÌõzÁíÆ(+KÙÛó?Ž»­O^z‰ Çg/…ŠŠ TUå“ÁA¼Ö Ÿ&°F׋ôzV¬Pç”—N`>AJdx MNbø|sç΂w<ˆÚÞNëË/Ì>áG»»‰E£” Ýnô’’ÙçºNœÀÕÑÁŸwìàbàM£¡¡§ÛÍþööh8ŠÁ“a$‰€fY? 6]ôû ê•9„ûû“”¨\‡‰ 1Ý×Gàøq„ÓI‰¦a`á~ÿ}´ŽZwì ˜Fö醲±®.bÓÓ”!].ô’’ðííüù…¸ÐÒ’µ.UÓ¨oh@q8ø][[lhb¢Ë€[¿çRR QöAh ürlxxã…ßâª*5¯¸˜±Ó§‰Dý~¢L÷õÆ…0âkìѳgÑ|> 5 uhíÜ9Îüô§rÌSë8>ÖÙ‰”’Ò‚”`gO­»v1pôhÖº4‡ƒ†%K@Uy¯½=˜œlwÀêÇႯíÏã ܯƒ›ºZ[}K**Ôü²2F[[‰…ÃÈÄ…̓ƒ­­8 È/-åÌ /0üñÇ—ÚêGÚÚR2wáB>ݵ‹¾÷ßÏÞé¤nÉ !ØÛÖ™š:9 w|†­X3nÐ=e:.ôzkï_¿Þ!tsûö˜È Józ‰F"W> T¼¾lu9].ˆJÉoÛÚ¢áéé4øûï@ØcÖ×3ž²*òxo\·Î¡çöïω„«}¹uº\.ê—,a*ã·íí±H4úîxà[0•_ÖW7¾%ü]pb¢cÏþýQÃ0¨jjÂáñüŸƒ7›Ûã¡~éR&¦§y»­MŸŒFßš†/e—ñ¶øV(ð{ŸÛ]S“Czd:%\¯ˆ'޽^/u „&'y§½Ýˆéú®Å°ùAHóÊúð4 8˜ïv7Þ¿zµC‚žC‡2¦ÃõðyyyÔ54 ‡Ù{ö¬¡Æ‡Ù'—OÀ?BÙ2Ø—ïr-ûÒêÕUQè¶p½#> ~Îêêë „B¼ÛÑ!' cÛðïäùD¹œw…5Àó ˆ¼S­ëë:Ο/^ZY©WW3ÖßžØÂ¾Ž >ß磮¾ž‹ccìíè`TʧŸ„gã˜D®$äJ€pnÀÕôÃ{ º¾º«¯¯¨¡²R)©®ft`#ý«€_\WGÿè(Ͳ_Ê-ÿ5óG*a2%~{Æ×Ûr!@‹à‰ã! štýöžþþÂúòrenu5cƒƒèWHB.÷±¸¾žsººŒ3RþçvØ“¡ÊŒJÈ•->ɀч–êú­½…õ *ÅŒùýH@¨*Šª¦úÄo&owÎê}ÔÔÖÒp°»ÛøTÊ'wÁ»ñ(Û™÷i;Ä\:Aù'Tà²úùPô/ðì\—«nãªUªwÎÛ}ÃÙ ›óæ=Gi=o²¿_þ¡»[ÿ<ñ¦ã6•Á_Ø€O±EPòOð£"§³z^~¾eíly¾Ýû:–gis-*%çÇÇø7à° ¼•³ÅÈP.g4+a¶/0;ª øKð5n ŠŠœéŒ„œ1E^ê¤f°Å·[EÜâdž¸ä ²Þý5¢q›6y+YçWò¿Áh‡åØÚG$Lµ˜Bromâb¶×NäoÂb‹š¼9Ï®æ“Jœ;Ðé€'ÌJ€¹ç¶ëÈÒa&!F¿–XK¨Ã¸9òfÌ%ÑøD¯Žýj_O2=Ãùt)nN³ÿÿr=ÊÿüÕ’5A4B%tEXtdate:create2016-01-20T14:40:39+01:00E’Èç%tEXtdate:modify2016-01-20T14:40:39+01:004Ïp[IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_label.png0000644000175000017500000000152613561570220017510 0ustar otfriedotfried‰PNG  IHDRn½¤°gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿ‡Ì¿ pHYs  ÒÝ~ü*IDAT(Ïm“=OQ†ŸsgfwvW$jkhÐhüŒT)¬,4˜¨…’¨€þ …‰‰‰–øL(´R ­DÁàBÄdX–ÙÙ½Î̵˜ ÷-Nqžœä¾ç¼ò’;b¬LÊ8“[º†üsæíÝ€Aó8 Ž˜ï];ÊàþÎ>s€CöÇÛ<Üè«MsÇΗЙ¦éq¸%öްtËÅꂦEÍ-\Å¥'_?mjÔÑ|‹&Cf•ÝíÖ莰=~¢4‹FS µù‹¦…OrFz·Ár¶ÜÝÅ-ªÄUž,h&ÆO¸± ¶GÏy¿h¡™â§æÅ’i¡Ñx%¹»–NêW?Ñ„,)^™Ì,£‰pQí2¸yòð+ÔÐT‘÷f’g+taížÜÛ[ãÇJ3hZTW“çâŠËDӉ𕒎uXNv•»IŽÞ°Æ$…-ܘ«@zÖë W|õ…˜9ã瘠ÁâTÒbëÏýÒ;ê1²GY5̇É)óÕ®4¿©!¬Qr,à…eß©0¢@=èó¦¨×¹‰ŸSoÃIÒOÚfXŠJŽwì‰YbšÞšfNUõ9Lï‘‚á²’Ñ]¥e\ D}¢!®xâ‹/¾xRL^Ašß—1›þik†,/¥ˆƒ`ˆøÇlWR”Å %||Úhã-«4 ‚¬®RË2(Џ¸¸4šf–6 ü$úѽ£dU%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯tEXtSoftwarewww.inkscape.org›î<IEND®B`‚ipe-7.2.13/src/ipe/icons/paste_32x32.png0000644000175000017500000000254713561570220017406 0ustar otfriedotfried‰PNG  IHDR D¤ŠÆgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTE\\\``^\\\wOrMrLuMrMqMiFqL`A\\\™™››ŽŠŠ}qqL]]\¡¡•¤¤™——ŠpKŇ'ƈ'ºº±«« ¬¬¡­­¢®®£¼¼³½‚%Á„&–zˆŠ…Éɹ¹°¹¹¯¸¸¯¸¸®··®··­¶¶­¶¶¬ÆÆ¾ƒ~‘Šy¤r"ÿÿÿ___¨¨¬¬¢««¢ªª¡ªª ¤¤šòòò¢q"ðð¢^^^˜˜—ææå¡o"ć&ããâØØØÜÜÛîîíŸn!Â…&ïïîm!œl!¿ƒ&ÈÈÇÇÇÆÆÆÅíííšk!ííì˜j!¼%îîîìììììë—i º€%ÅÅÅÅÅÄÞÞÞëëë•h ¸%ëëê“g ·~%êêê’f µ}$ÆÆÆÄÄÄÄÄÃÃÃÃêêééééýýýe ³|$èèèûûûŽc²{$ùùùb°y$ÐÐÐééè‹a®x#ñññúúú‰`­w#þþþðððôôôÙÛÙ‡Š„«v#†Š„ŒŠ‡‹…©u#ïïïÕÕÕÖÖÖÐÐÏŽ‘Œ¨t#ùùø÷÷÷ÄÅÄ‚„€¦s"ööö‘‹ÔÔÔ©«©‡‹†ƒŽŽ‹‡‰„óóóøøøÕÖÔ‹Ž‰‚…€€€}‘‘££ £q"‰y‡Š…ˆŠ„Œ†x½‚&?X5tRNSÛŠü‹ûû‹üý ™ü¤!+173¤ÚêŸbKGD=ÐmQY pHYs  ÒÝ~üIDAT8ËuÏ÷WÓPÀñ¨±P5Nêu ¢òkÅ#Ô* Ö*5Õ àjA"Ô:PqÖ½ý}/¶7ýþÒsr?ïÞSIÊ#vyR®HÅV{š_@Hå\V%!ùâdÜx¯ªÚívÏc±ŸêªùüÓ„‰6(\ óÈÂE‹YKXK—‘þÉSh—,/²båªÕµµkÖ®««[O6l¬—]Y”Ò†M^¯×çó55mnðS [Dlm&Xó¶í ;ìä °k·Ó…½öÙ`TªJa?Ïÿ@UU…Â98„išÖ¢)FP3j{­(¡…#Ž @U[%jk§p Áq<Á··œ‡O¶G(œBp:»o†ØóH¤ƒÂgÿÌq{¬ëÎ!8Ϧ]àÛ/vvF£º~ɈÁeW€ªÎö>6Ì.¸ŠàÎq{lšÝЃà:PE ³íQÖ Ã¸išF[7ÜBp(ÿç¸Ý4#­ñô"èƒ;ÂqÓÔƒýVÿÝ܃Xö8ßL²“C¸]üyæøÿÐÃTêÑcáÄx*·†“©Ô³Áçx#Îñá„õòÕë7oߥPÖ{<÷[#±ØÇä§Ï_¾~À÷ ösà@:ý;&yäý)*ž,I%SJ]9*:m:[Q2£¬|æ•Ï*+ž-ý àïjÝY%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/cut@2x.png0000644000175000017500000000643613561570220016577 0ustar otfriedotfried‰PNG  IHDR,,„ZgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð IDATXÃÕ˜{p×}Ç¿çœ}Ý»÷…^Hâ y8 ‰WÜòÆg’L7u(ÔŽ?27)ˆAœæNmdÀ¸Øž8-!±jÌ”f2“‡§“&8¢¡`ŒÁ6`e!Œ$z¡{u»w÷ì9ýC‘¦z¥þf~³3gç÷ûœßžýý-ðÿLÈp wîÜe*Þ“Àó›6Výp¬wìx~‘¢©oy‚¯©zfÛo‡;×Ðð);fÏ.ËW}n÷îXÞX`>ÌtŸQ³`þˆ®ÿ$¥v↼k×öJÂØý æ-¤sÊ+|L1_ psóåïç——•#?¯ à¥=»þzÜ€c±UuýðÊe+ƒœs”—ÍÑUUùÚ®]Û+G»{w,ŒÆ–,Z²¬,–/_dLyaçÎÅãl˜êƒE…E……Ep]Î=,Y²<¤jú‘<Ê~aJàÕy•sýŒ)àœƒ€bnå¼€j°çÇX7˜1}f8›uœ{˜T<‰äææL}ñ¥kGûÂö•²Ùåºã¸×å˜9c†àËãìyüÓx"Î… ŒÙ¶ƒ¥KW†Ey%‹ù‡(‹Q]UkV,[Êf! ¥¥‰ž(¡í㜵¼=gÏ~˜ñ!€”Bø}>Ìž5; û«‡(ô}wRQñ¤‚‚âº@ϧãèÑÚdÖ²6Ž ðÖ­[;¸pŸ?qâxÊ0ŒAY¶1o²oU¿T=óv>ª««ó©BcË–®Z– )%¤”PUõŸÔ{¶m¿SUµíȸ@º'»§¹¥åÆîPÖp]‹- úýÇ·›oøÕ—çVÎ3¥”ð<¯70% x÷ÔÉLŠ[O ‡cØÀ±XŒ;¶ýxíÑß'û³,¥D6ë`Jé4 VìØ½ý–/Mõ‹ÕwëºþÕò² mpv}>Þ;}* ÈWŸýÞ³Íã UUÛŽd¬Ì™K—„®kã©T÷¬XÑ5cïÞ½{Õ! ¥†¢ÖܳbU8Î Œ«ªŠt:†K—zÑŸ.È€ÀN;?ñ_EU@Aÿ#6ͦ–N¶ßlooæååÃqœìš¦‰ß×þ.É÷©õë×gÿhÀ[¶li”ÂûÉ™3§,Óô¤Ri,Y¼8@@«¶ïÙ^ÕÕÕ¹ŠB_X±|E(™L øðù|øôJ£L¦Rg7mú»_Œ$þˆ Oÿ£º:+ëØPÕÞ „@6ëâ‹ ÿÄ4™±|}weÅ|¿€çyR‚çáÇþ¶ÒηFØH'ÔÖÖ:÷­^ÝÞÕÕyÏìYeºeYÎ9J'Of>¾]²lq›ÏðmX½ê>3‘蘇púÌ)«­½}ßæMU‡F<â ÀÆ›^ïèìhºÞv †a lx<Õ÷¬Žø ãŸï]u_(‘èùLÍÍ:Y\¸x1•Œ§·&î¨ !Ò±íGkkßNƒPÚëÆu]„ÃPTT¤uwß ®ë̉DÂ8räwIÇqžŽÅb™ÑÄ50lÞ¼íŒëñßœ;–&¤”€žž¬\±Šœyÿ=8®ÓWühni’݉îO6?³eT[aÌÀàX=ßy÷ÔI‹1Š¢ ”9îr̺k6êA)í+co§3Yû›c‰7fàM›bíRbçñÇÒ‘H`g3HgÒ¨¬˜‹ÖÖk 8}ætVqhë3[ëþO ™H¿xéRCO2™€®kpÙ¬D¢K—.Ç©÷Nâì¹Óq$Ÿk,`em¨ÔÖÖz_5•¯·p¯ä‹ºYÛ¥ œsOB]Ýy™¹Tÿ¯[žÝyx<€GÜâ •}¥¹w±Læ#öÔ2Í_"-E÷ÅÐqü:ŽüÚO€ç¸Òæ?wßkîÀ{5@é“ Ø@)Pó¥ÄvHn8B¦MšF˜®áÈ'ôØœÿ™ÆØ¯WFï ÆÓºJ€×2þ qC¦) eÛLJÙÎ9™ ±o àŒ¸X PúóH )ÊÉ jŠIHï–@ëÈXæÌ˜ŽcMS\xKxûöiu¡^?¿°Ô¼Ão¸a%½É¹™èï:(EãÕ«ÉÖŽŽ„Íùƒ'oÇsÛ*q±oꔚNÌ …tB8çH¤Ó`”‚Qаi"cÛø¸½%kùÄ=^ ,wäqN‡ HhzþDÖÕÓƒü`˜jºGt'“ÐTŒäƒzQ~~¨³»û_Ú~&å#Îð›Œ=¬ò£%%AF)²®‹+ׯÇÎ3„—R~©dâÄhÈï£g;×y^þ`ûÈ—”ž¬ÈN‰†sH†s$l›×_¾Ü*ßø²¦iŠéÓÃ¥ ºŽwÎKfç鵞wàV\·<8þ¨ R¾6= BO¥¼OZZ:mÇyb“ÖzÞ“®‹¯uvrJ4U‘ÒØ |¦Ez<…ê‰Eç;®JGJ˜†KMM)áyËÖzÞ·×z^Ô²¬Gß­«ëèL¥<âºXTQd”¾\,°ˆJé›S C”RØŽƒ–ŽŽŽ•?ï·{hr=¯÷gEŸfoáÏL£ÃÈK¡€Ë¹º¸Òÿ!àÒóÊ/\¾ÜÖÉH¸.–•… U=»…¿›Þ¾æ3Œ¨¡i.·¶&!Ä—®¶;LÑÅžF)¤”XÜÔŸ­<"¤!B@Ó´ìÀ´Á6´9BÜ{¶¡!)„MB¡Â™Àƒÿ#°ÊضœœAgJ/Ú® )Â~¿¦÷µy¸)_ilk³¹mcÖ´i!UӶܸ0¥”_Ð*cèL$8â¦Á‡ÆûAÁ„ AC×q½«+b?z«Ž2TmÏÛßÒÖ–¢Šòò ôûC÷;!^n¾~3ÆRN; >Xæºî! {÷sj ÐÙXàà·e{^8œSX!MQÈä¼nnδKù÷{}…ût0pø?õº”{ê®\ISB0«´ÔÖõu¯Qº¹º?†))mB€0 ƒJ ÷ó€IHºž'€€aBÜqwoPãÏɯ+ÊÁ¨ßÿ÷ËÊÊLPŠæ¶6Þ‘L^þ?^jÛªÍ9‚>¢ùùúúŽŽ³„›˜YRb”ä婞”héìôê¯^í|Åóþ6Þë‡ Úì/^¿fï9ß°©©é ÆX~Q8¬,ºë®@sW×2_KËÑuB¤‰”Zåôé>H ªªèN$Ô: ®ÏŸ Ÿt€r±šâÜÜfE£†B)\!zWÖ×;.67Û×:;Û÷yÞÃGîA€ýÚïWRÀ[Džb¬¦tâÄ‚²)S|’sо²HH!ˆDPßÜlŸohxk-ç Z¸ú-!VHù[XÖ_¤Çôù|*c „R¤-]]Þ¹††t›eýÛsœ?ù~/,ï[‡ÛwͰ‡\´ˆŸ’òJÛ_mm¡†©®ëÐtÔ0p¾±ÑªÿôÓ¦“œ?ðî[ì@Vo’W=_Q¶Q)Ÿ”„¤”€å¿lô¼Wb½'”Í¡:T$nζ¬JÊ{Z#ä~ ø)¥@ÚØŽóõ.ø32Ú©Þ­€‡úíï0Ä-Àß–ü7c…}&³%tEXtdate:create2016-01-20T14:40:38+01:00ãåÃS%tEXtdate:modify2016-01-20T14:40:38+01:00’¸{ïIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_ink_32x32@2x.png0000644000175000017500000000576213561570220020433 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð 7IDATxÚíZ{pTÕÿ}ç>7Ùdcáb ”$ŠŠ"¾¦ÖIkUJÑ;§Óq "ÎÄúq¨±¬ŽÔ)õQë´¶¶¶¨ƒè@Ç'4˜ÝͲ›%»›Mv÷Þ{ÎéÉÂä‘lò›9s¿lÎ=çûý¾ï;çìÝ \À7ÊH;-Ô×C™KÐö‡À3?g#íX6ÐXkÜRäÕÃÅ£»±ÖÜù?i熫¯4n"‰·ªg—)õ8½ýÉq@ó›?´?Æy4Ö™K!ðæ%Å »¥Â!•,“ª+ÝGi'‡ «ë\µâÏe)êÊ.æ F°ý`Ò&È&îLü;Ýo\fÀýuÚ|Hñ·)E_µÐÅ];ZSèJ 0‰UM€H÷wðÀbýr)郒<–³²ÚTŽ÷´„89—R6=¿Û:Ù\ ÐP«WJརœ^òÝ–„?*°û¨åH‰ƒ°­gúß3nJ á*W#ú§ÇdùwW›*€?&ð¯¸%‰ ±jë>ØãR€û»¦2.vºušp×—ª2‚?&p8Ìq4ʹ„|ì×{ì}Ý;æh¬s—¨L¼Ÿ£ÓÄ;ç»4·AðÇ8üýÇl`Y»L ÐPW,…½ÃШ¬~ž©çöFÞØtr y×@©?æøÑµ( ÝzÏÐhúw«LmЇõ’ ´vr„{—R6mÝe}zºqÆä.ÐPféU̾m®¡Í,RÐåðÇ|1o„;>›lZ›¾n¬1—õs¡“a¼©UßTih—MR{k>Ú›ú­Ç98‡LÞÓô>œq%@}=”Â|c–^?ËЪ§i'jÞh‹8HÙRäúvZŸŸÉ˜cI*ôê/á¶ëfêê·Ê4bþèÉèGÒ&’{ÃÓ¬gÏtÐ1³4Öϸ§®\g5kw‹S¢ìâP)èž×^;õ¡Çé0&2 ±Öü…$ülá4]5]C<%ûVüÞ…¯=&À$ˆV7ïIµœÍØ£þHCñ IüòòÉn˜¥C -ÊÑh‹px#Ä`K‰··îJÝ~¶ãê h¨1ï#‰-sJT,©@ÆŠß}…' Ã2R÷žË£V€Æý{ ²yF‘Bßž¥ÃP蔚÷G{¿ÒK!‰KúÁËï#2nh¬3—J¢ßN-PhùlùRóþ˜€#$¤B’|ì…]ÉÎu®Q'@C­^)ß*v3ey¥AE9_|%¡,"ì<>Õzò|æUÖ¼'õîPÌ=â4TCã)㪂¹Ë*tmî$ǺÄW¢?1¡Ç6Û;§YO Õü#}&¦ë/áškfèêü)*" ‘Q÷½Bæ28B8B¢-i¤êÏ·î31b?Ž>ýôS+ÍÌÛ"Ä­‹&¤”šr I[ÂðEO¶<“AU¤è±‚×½¸“· ¥#–vw窂K]ë™±Âþ]Ýï ‹œRó. ÈQÎ îhÞcíj?FD€ Ïn¸‚ 9;7'GΘ^A‡›Ø®–  ð;bíðGxLB¨[HÖ6ïJ½3¾d½6on*\ÝáÎÍ+½²n ›9³eeÓ…Ña”!pø8¶…Â\B¸Gp’hnÞzd¸üÉú.`qýEUU&ν´J™7o>JKKQXXˆŠYs ºòQ´ønçë8Þ-8 _´;õ“áô'«lÜôÔRÈÛgUTjÉdRJƒAD#QLœ0†gøäZ! Ÿ¤[?lÊø!s8µظq㟇‚×ëE< Hö@ÏŸä˜ñÀ¦¿„’ÃíWV2 ©©ÉÍñ†;7ª,Dyy9ººº … …FávçÂð;‰xl¯^1«Wf÷¬ì®\ýy¦(e‹תH&“hiiA8Fgg'\9.|Ñò_GJqÈ0Õ=ÔÔ‘ ¿€,dÀÆgž¼S±r^ÕZÕeUàœãàÁƒèèè@8†¦©8|ä ‡sþ¡p¨&›äa΀M›¯ —Ê˧£¶¶Š¢àÀ…B‡Ãhýòˆá•‚ü¢ûW¯^mŸÿ¬£D€çž{ÎH$ão¸sÝêòVÀår¡¥¥@áp)+)ƒ¡¤Äã¯}¤)Ûć]€îDl‹¢¨snÿΪÇãAkk+|>:::Ð ‹®xŒ“”÷þ|íúWFŠü° °aÓw¨qùõ7¢´t2ü~?Z[[ ì8Éd"A·®Y»þœŸåFhÅŠÅW_½8ˆ½|Ù¥U²ªêrêèèèKýv´óÙŽÃÛ!ø kÖ>zp¤É‰Ë–-[nšæÃ†a,fŒ™ûö}–tçåùIŸÏGGŽ×ןßëòcnã¦uë 4ñ4Îë$¸dÉ’'MÓlöx<å555jII :;;ÕîîÚÿùç!køÒTó–5kÖDGšt&Î9ª««dŒ­#"TVV¢¢¢ªªâرcðz½ø×Î]LÓhªº9Ñc­YÛ´nXÏõY`öìÙ×xVÆ‚Á lÛFOO"‘8çB •L±>útË믾¾€ž1„컊>»5zO‹'ZQQQ¹”òUÇqÔ’’,X°{÷îŶmÛ ¥„mÛ°, –eÁqìÿlÿÿä@~ âb€«À3>VÒ„•~W@q¹\nUUoÛvq~~>JKKáõzF¡( cBÀqX–…T*…x<~|úG_œ¦ñl>‚¤ >²™õ³u"úã8UD„ÒÒR=zíííPªª‚ˆ ¥ç¶m#™Lvµ··Ê ?y‘aD2msœJ| ûœÈ$zºÖdYÖõ999p»ÝhiimÛÐuš¦1¢Þ× ÒÄãñ7lÛ6˜ ÉÁˆqœZ‚"Ãæ}£Œ¾g ¥ßƒµûüˆÑh©T RJH)á88ç'Rß²,$‰}~¿ÿy)¥ @˘‹2Ú@gØ€!X<ÓŽ ñtfÔø2¾:kšÃ0 i4M;Qÿ}%pܲ¬m¡Ph¾ššƒÕû×eAÿ¿ësN¤Ñ¿æØŒ“[Xº?)ŠB}䣊¢tQ€s¾/ȈÆ@Q>ÝŠŸYûgS*çŒÁÒp° ³Q?{ 62Ó÷lv‚aÙÏô%©4¡´ iûtÄÏD€¯; dî¡|KŒ±O'Bû.à. «ø?ž©]cúRítEXtAuthorJakub Steineræû÷/tEXtCreation Time2005-11-23wf–Ä%tEXtdate:create2016-01-21T14:13:05+01:008µ# %tEXtdate:modify2016-01-21T14:13:05+01:00Iè›tEXtSoftwarewww.inkscape.org›î<tEXtSourcehttp://tango-project.orgïâ– tEXtTitleBrush Toolo-6vIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_marks_32x32@2x.png0000644000175000017500000000146613561570220020764 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞbKGDÿÿÿ ½§“ëIDATxœíÚÍ«UUÇñÚSj(¥uÓI%æU›dP*(M ‚À¹„ƒÁФI‚ ðeèD„œè 4È®)‘FÑ»%¾f§ÁÚ§³9÷÷Yk߻/,Öý¼ìßsöÙëíAAÁÿ‘e>k0Uàwg ü`OU¹Ç nÆjÍ«è´? r­ÅaIt=ÖuÁ†b-èªSø¡!æ5¼ÜJM]`#~1ø¶áY¬ÃÓø¿V×ob{KMYtQ€S•ÏÏØ2Âæ \ªì¾ÀòLÅ,t6Õ|Þn°Ý]³}!CÃtVµ ^ªú8Ñ`{ßùe± ðxÕ‡[cØ]õ“%É–bnWýÊ1íûvãkK±«~5Ø®ÄÖêóÌ‚ÝÑ ý|Xúzø¸Áv_e÷7žÌц.†Áƒ5¿ýX1t}Þ“¦×=|V&¥Œ. 0³5ßoðÞLJø²ví‚ôÔtFWSáU8Öó4i#査ø«À/·7ð>Á»xJ³Ãó8®|uAA”œ ÌÅ&LK›–w¤%íçʶÂû¬’fƒóe· l4ØÀn×¥UÝDAÜiüˆ v›q{ r´fÊ`ëú~í¬ô-ËjI|`ǻ͸j°5¾>[A Öj>´¨·c™ñ·á·Ê÷šÙOB]üm¼^"¢ ‡å/‡weæU„E?Q»±œöiA®á"¼i‘ÅÃ3Ê6D¾*ÌW/Â?Y<¼¨¬?µÈùîÕbík«5Û”àâ\ÁÆ þ›ï·¹^Œñ Á¶uNË ˜ýÂÛëþ£Cg•_€éÌ£ÞöMCd'l¨’+þtfü¦¡nIáiÖ$þ‚¼­ëÕÒÁh_ük#ìvH3Å^Õw:ì³]úsÂ\ÂïI'6Ä}KZà4 uý'á@AÌÏjp9ž—Îç'¥SÚœÄåq×ãûy´ ‚ ‚ ‚ úü _jÃä=="\IEND®B`‚ipe-7.2.13/src/ipe/icons/undo_32x32.png0000644000175000017500000000337013561570220017232 0ustar otfriedotfried‰PNG  IHDR szzôgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs  ÒÝ~üÈIDATXÃÅ—[lTÇ€¿ÿœ³ëõm¡Øq“€Áq(¸„’¸…¨à&%!}0j”<)•€@µi$*µR+¥!ªzI+U©ZJ_š†ÔÁ‰zIÚ¨E¹V”`.áÖ Œ 6\Œ½Ëz½—s™¿ö®–eq×&jGͬöœù¾™ùÿ9爪òÿ,ÖÌoÙû‚üàð³2ëzœ™Ütà%‰åO kÆÂüôº{vÊ"c䨼%ÝmÙŽ{=ði tuÈZÇ©>²¨í; Í÷‡®;€ÊØ·SžŠÌjúãmkž©®ª­ëeeÄÀ›R] ¿›3ïÞûæ·~5¢ÞûÙSXá[ø($¦Øß!MµŽõÖüÛ_P?M(ÈBƒ‹ ÎGŸR`ïoä^;RûjKÛk+g7J>Œš$`3±s‚ˆØa›óû^”8 xE ¯­Ü¤'ÊRÑÞòÍÊè§µ}?â„‚ìIÐ,ªÙ|ªi3FàÇñÝÜd‰KºÃýÿôÕ¸o{ÞµY‡§%°«C"a›Ž9s×<ÐÔúµˆý¨?€âƒz“.5— ü!0cˆUƒ]ñIÄidtð_þ…¾Ï}¬m½¾T–@×óRk…躹eýâ=öÓ‡@“äEÀGÕ“Äß…WOP¬áTÞ‰ÚwÐßý—ÌøhϾØ(íí[4[J Ÿ†mèÂŽ‘Á=—a9õ¨É€IƒI£šA5‹1Üä%ájbxão¤:inýbdÎÜÖU³góã²c k§´;áèˋ۞¨ŠTEÅÏõƒ ¼ñw@ÓLdÁÔçØu8чé}ïÏ™L¼ïîU›ô`yAØ)KÁþûÂω~üvÛßñðÓ麗Ôo PMƒfÐ`?s ãž‚üXvŧðÌ í=ð|ÿ¬‹—¬Ó+Žï’'áª Ú ÁÒ¾CÛ{Î÷üÖç&Œw&ŸPºÿ±ÝïÙóBêôÑ¿Žý»¿×õYNEÝ×±#+ò—ÙãDªU¢7,¸!–æË׌³>+.ž~çõÓ‡Ÿvj¾„Y^°Ù¾— ÜñØêÄð¹‡.œ>úíÞç?<Ò‘»§jõäð† }ˆh}c•KÊX½I3Ÿ]σÉÑ3ÛNt=—VkNõ}€…š‰Õp¡·m“¾ö¹º-£91ûÙñ®?d|¿ »â6L0B¨ÂKX6-É©êÊ ú„›Ž僮ÎT6"T³5ãWaûÍ®zX·j}ràøî”j £&‰…OÌ@`rK6ê‹Æó¾pêðë—ãÏ™‰L(]ÎU²-LžMŒô«Ø "ã¨R7c€•›u¯§Ú:øÁѳçO¾ë‰jÉ'Òºu¨áÙÔåKžH¬*2cÈðþŒd¢X"b~#}=|fdðìAcL¸û!q ª-"–1Œù^ÚƒH‰ÑxÖü­, #"! „suÃHoùk]—ýç…ÿá¬OT%h€çbC ßòùÕU¬ÂƒHDdR*W¥¨_\‰F‘D" è-8?’ý Zê+kBÁàÉkd$óÌ=ðÀ¨ªÉ1¸U/U¥X&‘ȃs­ùÆfÚ«kCn(bN ÄfÇã™}[w°‰— ™œ¨QUUÍÍÜ.‚Ù%ì"¹bóÜ÷XÙ²Ðz´¡1œJÅÝèè°9þÝ_òô»GIå®™¬ªšœÀµÀåô0·ÎÃ~ê1V77±¼:J6$tf€·¿µÝ.à‚s}U WÀ*s®Xå˨ºëÓÔÝÑ­750×÷‹ÅÚµŸc¿~•KÅЂßA~ ŠÐfŠ@¬©Á®«Ãi¾™ðÒ[¨®¿‘Ê* Ç3øC$÷t“8r‚lP‹D_õ8.ÚŽÿšåŠL(çZ_‹€2Õ×qQZ^ .Ep €¹½¾&D¦ûy>)U >Ažæ€ÿçèTÉäÔ%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯tEXtSoftwarewww.inkscape.org›î<IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_parallelogram_32x32.png0000644000175000017500000000115513561570220022112 0ustar otfriedotfried‰PNG  IHDR szzôbKGDÿÿÿ ½§“"IDATX…íÕOhÏqÇñǶ_͘ÅÉmQ£°ÙÌvÀjjþØÅrPÄÁ…‹âàà8M¡(Ir‘¢µ"¡ÄÔ´ƒÄEþ•BLk$¶½¾¿-ã÷Û¾û!¿g}êûù|Þ^ŸÏ÷óy(R¤ÈÿNÙ4íá ¡¯ñíO‹ÊÇêl²GDà ®c?–´$¥Ýôã+Và3–cZQ›õ×p5+ìc°'sļSÂÁ´"/KV»<͈íJšä°/poJû2¬ÄÜod$ˆ¨«‹èíè윖€ZÉÊ/¥Uû3h "Ö¬‰ˆˆèéI- ñs 4³gGÔÔDTU¥pNrêWš^Ð<ÙÈdUnÆÚ1§^ªûXû€Sg¹û;–Ѿ€ÑfvãþSƒã_AG.•Ãìü䨖„w8ŸAé„^[]]45²Ä¹Pâ4nâh: ìÞMu5è` L¿d—ã¢ämÇh>Ã̄ޅ ô÷s7ùíOh‘Tº!Ü’T¸¼úÑ-’ë:ÎF<§æ!›$ïÅää;؃u8Žg‰©ÀÓìØºvfåòâÓ”‰eß‚ì 瘿W’$£Z²+-hÂŒ CߨTZJ}=##ôõÁ»æ§Q(3±¾œADEERéÆváíßL>N "ÊË#nߎèîþG~m©d¦6™’QÜÈ1>ðb)ò÷ùqùb¾IEND®B`‚ipe-7.2.13/src/ipe/icons/fit_objects_32x32@2x.png0000644000175000017500000000600713561570220021132 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð IDATxÚí[{ŒTÕþÎ}ÎÜ;w–}±l0.R²Z)¡±¦¦Ô>,Rµ­iQ›1˜˜¦56¤V¬ŠiÓ–ø‡m…¦¡íÒÊZ´>Šºh‹P¨Z+º°¢,Ë2÷1÷ÞyœþqÎÜvçqgæˆõ—œÜ¹sç<¾ï|çwÎùÝ3À'öÿm¤Ô—ëÖ­4MžE)™š'yRk¡I#ô„Wv¯Y³Æ¬HÀúõë;%Ûó”Î=ÛmŽÚAÉÑ̲Ûx×3e ¸ý[:&v.»îšoI±Xìl·92Ëçóص{}éÅçOÑœx~A ÒøŸ’¯}qÁW$EUqÊqÎv»#³˜,cÞ¥óÉÎþç&dçØQ’JóIUU‘Íå`{v¼ü߆+Ÿ?ãHr×ã ¬÷ î ~" x€õrBS`œS>öI0ö9~€¦)øþ5—bòÄ$`ã‹pË=}¡H(; Ž;W^;7.ž|/‹n^23¦uÁК‚¤® ©Ç`è*O ’{–ˆ+5Íù1YDRSxR‘LÄ`hJP—¡+0ô:ÛXµlΛ˜ òööt`ã‹‚cÃë€U×öüiò‘D|ãKÓÑÛÓÁd¯ŽCWÙw‰´˜¦šq¦ði/¡³2“ 6Ä’z †¦¢£UÃõ_îNc\ÞÞžübÍB®¤òVr¢ëªëæcù×g—-@\9o*öD&G¹ô•À7ÄÕÆ–Š,¢EW!€0È¡,‹˜ÙÛ…–Dù°ÝÅŸšˆ_­]ˆ”íÕ1 r³|ñ%U)J".™>ï½?Ï ‚)K0 D  ¸¸«zˆ(Ó§§u⩉€Môt·Â´=¨ªÉ2õ´†ò½† tµ% ×°¨Xn¥‡µîéD`‚ѼH²,‰HêBÙõI=ÖÔX3,Jð@Ä ø([}{&6>*vÎ ¨­ì: ÖˆÐ¹jŸ( ÒÓš<—­²>F³©%,Þˆåòù¦Éæ¢-?RüLÃ#ìtí±¹0æùYŒ¤ÒH5ð¦x¬Uu‚®Ÿ µ±qÜ þóÞ ÄU ¹<‹à$´úΔ2×Ï´Þ8Q5ïžÜ{ß)û¼4E¡çÝŽâ¶ ÛáùÙÓBÒ…4œJ£ï¹C8>âÀ²}˜ŽËÉÀr‹‘óûíûðìËoç=ªÆ‹mÏ£XýÓ>¬]þyÜýðøÙ‹¼R °Q€‚‚R Ênx804$Äú’RÀõ²z,ÞÛlHù°lfºð,Óv±ñ»Ng²=Ü?¦ç#}1²çàQ|óö?A‹³!cðs©S6ð·9@O÷Hb8Á´&ã8>lô}æO  ¹s5m6#˜–ËHq|üä7ÏíñõX]{L.Óö˜'Öë„ç/3d‘`ÎEÝÐk KAïùí±GA;^ ÓñŠœ.»÷3¹š±ÔÉSŠ”í2Єmž)ÏS‚(àËÓÏCk‹Vø q²ˆy3ÏÇñþcpÈäjàÎ6íôYï›¶L¶<øJ8Z RÊÖ¦åá”]pL.LÛ‡ëçpÕe½˜Ôa4RYÄU—_CSÙ c¹H9>R¦8ÛŠà«XèWc•¬ ÍÂâÇó³¸áª™˜Ò=!’£1qEÂwÎBûÏ n°( ¾éGdpiºðý,n½þ³èí鈪h@<&ã¶o“:“HYÌd³oŒÊ’*¾†5;Á7]ÓºšrHJɸ{åhq¹¦]a%•PG<à¡­»áxÙâ—ù‘¦?ï8ˆÁãfÍíªé˜\#öÊ¡A¬Xÿ7ú-ñ¦¾½xàw;#-3ò“¢V® i7™ü7÷íņÀŸñ˜à^®„FÏúÍéù¦P aå½Û"¡™àñ+A™²Å| ˜lZÑp%aÏ•²¥ ¦cé‚é Õ?öœ‚›qƒ?‘h äýãCC“ÛÚÚ¡ª*:ÕæüQ!¬EU¿ ð}K:qr€À/&@ >ñHßã¹W/:::Ï*ø(Íó<<ýôÙ|>ÿÚ#?òÇë;Ç-'VݲbeggçrB0 —D„Xn:ý÷gŸ~ê®þþ]G8Übp€ ÎSŒ'L.ض¿¾#_gÖ²EW€ÇSzL*ù·Xu p™ƒ9IÑÎ93äøçL.¿¨¾L. ò{‚V5™ ÏIÈð4nëXÏø>|Bèèëÿ¶Ö5wøÖ».tEXtAuthorJakub Steineræû÷/XtEXtCopyrightCC0 Public Domain Dedication http://creativecommons.org/publicdomain/zero/1.0/Æã½ù%tEXtdate:create2016-01-21T14:13:03+01:00[eš%tEXtdate:modify2016-01-21T14:13:03+01:00*8®&tEXtSoftwarewww.inkscape.org›î<!tEXtSourcehttp://jimmac.musichall.czifã^tEXtTitleView Fullscreenl²mIEND®B`‚ipe-7.2.13/src/ipe/icons/redo.png0000644000175000017500000000172313561570220016355 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bPLTENšNšNšNšNš—  ”Öå>å;jÂnÊå=}Ú"Œê0‘Ó+Žä:‰é+“åBåFàÉLtRNS  mIÑûF "µøþï(þûDüøÝïø¦îöõï^ mõè QÖËH#§j6 o…niLA pHYs  ÒÝ~üIDATÓmÏeWÃ0€áâî$Hƒ¤)¶aE‡ë ï„áZ\þ?I[ ãôý’sžäÜ$šò´°òCY„:ˆÿ^P2±ëEP\"„ØIì½ööŽíD2% Ì×rHglû$kŸž%SÒ+<®¬:¿ÈÊ.¯®ÕéŸ)ps{—¹pœÇ§çÀlxy}{W/ùªÎguM­\Ó9ºúï—‘àï› !AŠZZÛŒ¡ã_G¸£³ t7J‰¿0톞Þ>f¨§ž#¢›ý0084¬ŠÆ˜îºbcFÇÆ'd–ãyC83&§¦gfçâÖ|T±t„å&[X\Z^Y][ߨÜ"Ø¿”PsSÅu÷ÊoOŽ?rüöÂ%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_circle3.png0000644000175000017500000000072213561570220017752 0ustar otfriedotfried‰PNG  IHDRY ËgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<-PLTEßBÿÿÿßBÿÿÿ1‹?R tRNS_¬àû{!’¥ؤ åbKGDf |d pHYs  ÒÝ~üzIDATÓc`À LÂRalÓŠ œíwï‚Ù\{@ä½· *á@H ˜‚ÃÀ€PÆÀP Ä0C[€8ˆÄT Nb!E Á†ÎAQ†b€9’Ѭ,eÞápƒœÃ°DðÞ½…ðï» ÏõÂ8 oûÞ…q°ã:%òë0hƒÏ¶¸4Œíšª‚#ô¯¸(+[AÝ®n,ŠÚó¥ª(JűZ3™è6m×›¢ŽjÐeÀƒËà1EÓrÁg6sr?,Œ×¿Í?%l ÚÎQpÅ–Òe0j.n{<•n“­ IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_math_32x32@2x.png0000644000175000017500000000171513561570220020575 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞbKGDÿÿÿ ½§“‚IDATxœíÚ[ŒSÀñ_çÌL‹S¢!é¤áÁ¥4^¡©kh<è!H<”4â.H"#Hˆ4))I%âi"x"i4܉j$¢q+ãn<¬=9ß™sŽó}sfdÿ““ùηö^k}ûÛ{íµ×2™L&“Éd2™L ØÄT‰ŸŸ16›щ¡dâ†ïWbA‡O K±«qnÁIÇÞ¸¼<÷«§†7ÅÛ›Ä1}è:Ïã33üœãP|#á,îSßý¸ _§f›³ñ·„Í}êÁ­}{4îVfW Ø—Ð~ÁñÛ[ lÁ[8ºM»Ûñ¥¾•Ó>ƾÙY)fÜŠéí‚vKð{ògEE¾ü‹Æx°¥"Ï`Qº>6Ùú® Ýº$ÛY‘miŒJÖ½¾?‘ìQzf>ÑsæÿÆ¢Xq8.°/=Sëܤ#“âßeŠß v— 3“Éd2™L&“ÉTË?ƒåÔ¬¶îÈBIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_parallelogram_32x32@2x.png0000644000175000017500000000220213561570220022456 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞbKGDÿÿÿ ½§“7IDATxœíÙ[ˆUeÀñßѦñ8f”Rˆ]ÐÄL+ê© ê!’„IA"ˆ®¡/Ñ$ÝSˆ¨H*©‡(DèFQIR*•:^/IY9`ÎLãåôðíãÙgOçŒgï3s¦Úذ¿ý­½öúÖw[{}äääääääääääääää4™B« Žñ#¬ÿu¬Â<qƒ#üÍ1Ã(%®~|†ÇpEëLyfàˆ¡H^û„Q²“[aèHІ*ìÁrlÂIµ1ˆ/ñ$®1JëÇH|ä,‹îp=~ŒÊSp3nA'¦×ÑsXpÈø¿Ö,qnM<î¨TëKÔ½_à»zHËÕ½¼tùyxŸã/µGÇI|‹ççµÅ•”xªD©ë¡¦µ8Æ…83z]ƒïw[…ýj;£„ß±KpÑXpÀ8¡ËîÇùuÎø¡°{ÔtÈ ~K뀳2Yæ¡÷àîÄuîÁêè*â†è 17.xŒ ªÞììdþüJ¹»›õë3šS›q\¥G–Õo ³ð0>Ʊç’=¼bE©Š®®äXRV4.£!SðŽÊHú/fÔy&ìÆ«ÂN2¥“÷|bù&‹ Xƒ‹£òAÜ/Œ‚ÑdàZv5øÎ±òM–5  ‹¢ûS¸‡2èËÂ@U©»›½{+å“ò™;éjÕ+óò¬ ³eL3& {ð„¨ü•; ið.îà^aëkÛC–ŠÓk@)ä.«'¼˜Û{¸ú)àA!èi%îbÁœ¨0™=/ólGè”6a‹N²yȓәG»øyÕoª¬EG1;•–Fp‚¯›Øˆ´$“.w§ÖÔ¨JlhR#Ò2½*_FIí8 ½¹±»¿Ÿ;âY£È,´ è¹Q¹fÒ8dÌšUOoÙ’C’Ñã%•žïÕi¥îžJ0Út IÕ2]ØšVYjlã*ÕIÍsÒêj€éxK%•·VØRS{ `ClÛ½»ª: ¦/Ò^K…´ÕøHHb|_k ãð6¦Få=b¿µi9-1 ¿œé‹›¼Ž³ëˆ4’Ôþ¡j¢Ð ¾Â¢m!¢—“ëBâ›3µwXRnƒñ¤æ Úi«á’šÅF¾}¨Ž3GÛq& =ô~ªãŒ’¡I͆Pb[³ÚŸçáÝD]»ð¯_ˆ Ÿëm-ðxÝ3‡Ü& ×öZ‚lÿ³±£²žB}™­ÓÛIÂȂ蚯,Jœ\‹,‰­oG²fM\bg9þÅÌÆ#ø}ÅäŸ:µ:Û·/9v¶Øþ¦R¼„…­r@+ãù2ýûÃVÙšu0Ò\úúX¹²RîíMJ43Àj=­ÜÇÂh)ÿ{Œ•5à8žN</™ŸNrâóþð(Ù•““““““““óŸåo‘ñ³¼Â|êÍIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_ink@2x.png0000644000175000017500000000347413561570220017570 0ustar otfriedotfried‰PNG  IHDR,,„ZgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð1IDATXÃí—mlTUÇÿçÜ×i§/Ú7Š–¥Û((,»@[w!È"$ HÜÅ—(R\4Š@¤›ý0Én\y‰$FawuÃf]ÝÍcLÜ($hZÐ*»­”N[Z˜Þ™æµ½sï=÷ørwRhK§ÐDþÉ“sîÌ9ÏùÍž{î¹ÀMý€µÙ«nxÖ«†·.Rÿ€½ÑPWÒ3uêU«ÛWÖ”˜Œ¯|tò@¼Ñ`CÂÖÊëU{Ÿóæ»s’™Œt¼ý? LHà†yòzY¤oüf^¾»+Ìðå)3AAÀ'ð3uÊ2QÀëOÍqž`8Ô•Jpð=ûޤNeÆL˜ÞT¯<(Høç³óŠ ÆÑÜgÚtÖ]qÄxÙ9nBoôª÷‹ùûúY®"íCWØJPJòö„nðJ³%Î?X}¯r‹[!ð‡ZfŒsþÊþ&ýdöø ¼iž|À…O–OWŠ<…þÃ7gL®3;p¡ÒØ5ÔœÜP+O# Ÿ-½K.ùq©ˆ¡Cc'YÜftÅ{ïMà µ®J*ÒOL•ŠgÜ.¢+Äà1œŠXqJðÇ·ZôÞ+Í%×öIožGáöWµwŠ·ý¢Z¦Ç5†ÍÂqÍ2BšöÕ#½ç¥ëêðæ¹%2·›gz¤ò¥5 õ‡ºÂ !’(}ÍÕ`¯+ð‹PÌ㋻˅I«î‘E˜].·5û›pq¸<×åI·ñgHJý¨²˜V®¾W‘ºÏ3øCü!“ÙÁßÞhÖ?I®qwxíZDV>ö‘Ÿþj–ªžÙð‡.¹;hp›=eRêÅ‘æwà’~ù¯·æÑÚu3\®‹ƒ< k!ªs€ð¸Áè/}‡aMà†z¹Ñ%‘Uë~¢¸SŒ_.ƒ`‚C‘ „o~ëËÁþÑä7à†:e“*ÐÆu³\…½ôÈõ‡†InóûšwF›7ç7ï5_¡õmëŽXÏ‘gW×X·¸(Žküa ]!O1 |]ÖœzáZòçXNÀãš:wGqõl¢6Áê‹Kî†& <>hÕWù²Na#•KØÝ»wç "=zÇS”ººÒ‰¨Šþ¤„ÎŽ¨( ˆëü‚añûþ|”¹Ö5rê0'Ö›e¥ååK/ucpPGs4Á'ÝuŽœïþú¢iÛ÷¿ÙbøÇ²FÎnº={wþZQÔ•Þy \–e¡··ýýý¨¸}2)˜¾„[xä/G¶±®“à]»~?6ß·háÏ󫪪 iÚÛÛA)ÅwÁ3 s ñïÛÖ6¶çb­1—„Ïç“©(F ýg›óÍ¿õí~7°9vºþTUõ£ÉuµõäôéÓèîîF4±µð¹‹&³—5nkü*W°cÞ¹óåÕyù/{PÕ4 ЂçŒHäÂwfʾ¯±±±/—°Àð{öüáN*)ÿ}òñ§‹LÓıcÇp²·g 9奄xË_$×°À(®¯¯w•””<@¹õ|$ñÜòe‹  µµþîqË4?OÆõ5>ŸOX`ÏŸ?¿¶°°ðÚšš J)Z+V® Áà¹¨ÅØm/¾´ÂGšóZ4¢mmæÌ™Ó$„T,\¸^¯‚ ‰L0ÛþÝö­;¶Ž7,pu‡ ¡´´´¼¬¬¬ÉãñL©®®†,Ëàœ# ™L"‹jiiY›ž“¶Ó}Û,ü·]MÎ&¤ôgBºuQJßgŒM©¬¬D8F$¥Œ1躎d2Pæv²,X+«5Óí¨€iºÀ"‘Rúªaun·mmm°, ²,_6 Á`ðpØéh6Ü•BJCg®‡•à1«ÿ<ç|#¥±X º®ƒ1Ó4‘J¥ ë:F£ÿÒ4í5½¸þ§œáÏêó¬þ°¥’I(âÿ]~ ÀÞÌ÷‚ @UU(Ч”ž%„´éºþŸx<ÞîÈ‘Y0»f‡r:sítwDçc2Äu\"¨#®äàPàÎà„ÏÔûˆ5’}˜8³³s8a³Ûkzø©›FßÿÇÔz•)ÝP%tEXtdate:create2016-01-20T14:40:38+01:00ãåÃS%tEXtdate:modify2016-01-20T14:40:38+01:00’¸{ïIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_marks@2x.png0000644000175000017500000000110213561570220020106 0ustar otfriedotfried‰PNG  IHDR,,„ZbKGDÿÿÿ ½§“÷IDATX…í×Á‹MQÀñÏ{™Ìb”óY 51 D„”"‘ÀÂJ™ÕXÛ(E6Ã;–ÔL, ‰BlÈ‚…"É0McÆâÜ©×sï»çÍ»oXœoÝÍûýÎï}ßí÷Îï‰D"ñ/©E䬯öˆ¼7x‘7„aÌà9~D¬éˆC˜xΕÔÙ€û-k~â"úce–uæ¾h†ðkq°Çp›qDø]Sž’åœlù¼ŽÛYìp²U Âã‚Ø ~ãZŒL=J¹;jhàmAü3¾mSÊRÏãÖİR.e)„a{±''6Š>LTõeUôðVLá;Îcöáæð,“þo„a7Þ笻‡5±21“n#ŽFä=Ä“’œ>¡5¶`ZØ9^DÔN$‰ÐÀe|öϯÂQq8rí˜üÉÚ.¶h6 '®¼1%ä6s!˽Þ"ÖÀkÌbW•² Ï,o³¾Žñ,÷–pqÄËL¶õœÜë…y_6š”Ôi–¾ƒW½%ŒÒ˜³Ä™ˆZÍ7Œ9œîT&¦Ñg"kMGä¬Âˆ \Ã~=¸Wà—ò7¼­¤NsÏžòwOWÊ¥ÙÉdz6ïXý¸[ ûTØžÚ1–Éžhù¼.lu³ØY¡/BÏÄUáÐ=Žãân õ6Bíb‰D"‘HtÇ]Ã÷¤£"IEND®B`‚ipe-7.2.13/src/ipe/icons/cut_32x32.png0000644000175000017500000000434013561570220017056 0ustar otfriedotfried‰PNG  IHDR szzôgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs  ÒÝ~üÕIDATXí—kl×Çÿ÷ÎÝÙÝÙ]ï¿m‚íØ€)Æ(AóhZ%jû¡Ž i]5«B©*ÀvC´ ”Ú1Ô´iÚ¸O¥4iC…H­* ¤hƒeClð‹õãÝÙÇÌÜ{ûÁ82[é‘Η9gþç7÷Ü3w†`ûùž]Û #þr,bzü~S°Ýõµõ¦iýXeNmÓ¦MÑñòèxÚÚÚL.ø¦´Ô´¸Çë|u*Åkj^›Њ””Ô¸€õâD¹ãØTúî¢âEêêUkìùáÎ]; &S\JIT»sï’Å_µ¯Yõ5»BéÖ‰î½/@MÍŽ%6Õ¶pfþ,&%ÁâE‹í›úödêv׬÷xÑ·$‰DpýØQÓ}àpÙ?®_SÑdSI~Kã¶ÞÏÈÍÃÙ3§`ý©ÑK¸§wÁã{À¶©h’É&66æ!—¤?œÇfäŽé™|°ùÞL÷$8ÖÙ\Î^E÷—xH¥¥ë¸Ó J™Â ³s—Ó‰3«ÑA=ô!SÈ·$>¤©v;úÕ9tã–= J¥Ë²¬¿1!~U Nàà;„Ò?¤ø|,+5Õéu¹ ô ¢½»ŽDg¬?¦vóo‡<ä½t·÷ëiÌcwkš{°¦°ÀÍáatôôD{úû-pþü:`ßþJéKTQüEyy.Ó²ÐÙ×w+¤ëª¢(¶sæ°H4Š‹}JÜÊ*ø›)p;ãô“ ¼©‘Û ¶]éêŠÏëbÀo÷Óî°(­HNLdpãæÍ°—ó'¾ÄGãXês»Í®ƒ1Öqwë˜Â:\ŠM³°|ôzpKbYo0#²RSm¥îP(-Ÿž’¢u÷÷G¸;Æo4EQ^Ÿ•ÐÄç{ïœïí b9 ¥»m,„^¿Är²²œ6ÆÊïàœçº].葈àìØâ^Æ>ÎHIñªªŠî`Ð4„øÍÝŠ¿î MUU‘äó%%(ÊÁ±Bˆ¦®Ç¼LËʹwb€ÛéTPôð{`GQÚ3’“™›Ÿïl*$€$É£^„¼øY[›>kÆ G²Ï÷ˆ›ÒŽ`Ý3@¡t¡[Ól”Rà‹×õcøcÎÊÎþæ4¯—œjnÖ-Ε·Û,ÈÉñ8T'ÏŸ\ç¼áËzë68½kŒ%±‡± Y”V,˜=[‹™&Ú{zB!]Wcbå¢EΡáayº¥åÀÓ†ñ$>*Àj™3åÓ‚œ÷CééÔÆ†ÃatôöƺƒAÞ"¥»°aä u##iz5¥« m™©©Jnf¦#Éçôôõ‰ÿ¶¶†Ú,ëñW€VæØ' õ@Qc»1ò'C ¥AÎ÷¿/ÄÞ#@èv±Q'c\Žq€/›ÌØSà<ƒBPz¶Ë4_Ú œ» +Ç; F…é]Eé}üö”Ž´` „³2bLìûK?{Å4›%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_label_32x32@2x.png0000644000175000017500000000417213561570220020723 0ustar otfriedotfried‰PNG  IHDR@@`¹UgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿ‡Ì¿ pHYs%%IR$ðÂIDAThÞí™íoGÇ?³ç³}‰Ûµ¦©q U⪴I“6rhm©”‡ÒR !Û¼ä/àð7 Qhh£‰J¼@B¨)HIjH‹iRZã§ølçü|½Ý/¼w·{;çÜÙÇ»Îjwvfgç÷ý};sŸ”OJCÅþ²õaýÕÈŒ æqÆ_æã#„á).Õ?¥Ó€lŸ÷”›'¨+á½G—½Él#a må^Êœ`¼,wÊ×A®óÇ‚ô²Rï¤V¾)íq;"XÇj°Àý¨ߪÒ¨±Gõnn‡âµÂÂêÜÿÀ€œ[žæÞ8²†˜4XxJ««|À‡êÝYmJÑ{°…ïí€5zÌr˜MèV$'òji”¼–ߢ=ŽúÁÖ«®­ÑCGÕ…„n3HÀ[åqoŠäŒŽØƒ r|û²½Þ}L¾€Óž¼ÅRyÜ"oßöM^ÐJÚãìv¤Õ+'Üó‰\cÙåµèPùuÞ.±ÇUß¡m{¾¦2‡Ë :ñ *ÇŸbc§Ös˜‘4ߨ5úÙ =4@|âÙ¢ü2²9(Èo犦5’Í.¶ÊµÜ'§wî°’À;|œ 3@´¼±žÚ0.Wº,æÁÆœiןfÒàÙ³¢þÁÄø?«¹œÑ Ú±}^i€R£Ç «`Ÿ\ ¿0¼¡åõyÏäÐ骱Z’j8)2ƒ—˜p­øñ ž»jtÄä^N™ÕÚœžÝïõºãTïý„Û>ï1À€‘¶ÙÅþÖÄBŠ´W©Š›Ò;Fñ»ÔÜ é!.ß~ ðŽè-Rk:xÈ„ Æ!Íd"PXXáµR[å~ŒûE»eÎ&:â_c*Ã5L¿Ô×Jö®3 óA= d;üO…ØjZ{sf“Æö8S¶šz¦ïIÞFoKÓZ-ȳ¼(ýxwcàYé;Äz›šš[¤‹/ÝÝ#Ÿñöðß& phñ½› ºÕÌ‹n?ãÛr½¤yâeù€½ä¶bà»)ë„þÛk%K*±H­b@Ý8:tR]ÁKè¦Ùˆ´âî•l¹5R사ý[F{â™ð°<|)<¡óLSé ÓØŸQ«8µZ²=ÅÎÔuc.x\äÇuÊÿÑê¹Î”éA Žçg£¢L¥ÔÜÉŽAn„¾…Pà&œàJ†x¿¿Æ¾t‰ü*½l”ÚQ'|žÝÌÆª€‹¨ ®ÖmÔû«b~”6¾j4 ”³hÐ_XòäW´ "Gœ½è`AäüÚO»“#Ú´JaL.&M°‰/Z­Æð “Âqn¡°ê º¸~eÞ¬“¸UÍÀ÷ÓºÛš,;`B^«¿ËáW7ÊB@T¼Æçêêñ6ã•­X¾>ÍOâ”yÐ)à”-¿9oÀò{:ÊŸþ ŒMJuè4›Ç6ž Œ?—*ÚÝÕÊÏÐ.Ãò@'ë¤Ð)ÆXXF|ÆÉ`ccca‡ J,Tt×h®Q\oÙUÃWöñ.ámpqø \®íÕAÓŠž%(V@—ÅøåóÒâ3‹µçü:—Oaá`ÓËሆÕõ‡|ŒvùjcCDléºyׯ¡Ðž¡ç?ø “:†ž’8 'fbôûhü*&âЪzÀGã hœðÔØøe¡v„ÊŠ4ê„:ôÝ bŽ˜ (e… qB³ÄÅ&c : ªã %ˆ°³y_•ˆJm+$ÛŠqÑí+ˆ- â *`üØ"‰­þ¶S!Ñ¥ý™°AB¤–˜ú‹Ši…M›ºœBê*ÿKüJúÚøvtEXtAuthorAndreas Nilsson+ïä£tEXtCreation Time2005-11-24ég%tEXtdate:create2016-01-21T14:13:05+01:008µ# %tEXtdate:modify2016-01-21T14:13:05+01:00Iè›tEXtSoftwarewww.inkscape.org›î<tEXtSourcehttp://tango-project.orgïâ– tEXtTitleDraw TextÏ ‚CIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_label_32x32.png0000644000175000017500000000234313561570220020347 0ustar otfriedotfried‰PNG  IHDR Ùs²gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿ‡Ì¿ pHYs  ÒÝ~ü+IDATHÇÅ”Ïk\UÇ?ó~ÎK&I'I­%š–¢-XZkq£àO¤” »rQ”Ò. XñÚ‚ nº(u£Ø•(¸Ð›º²R!'Ét:?’™ä½wï{.Þ½w¦Óiš÷ð÷¾s¾çœïùÿ÷É~.\9pÆMûwÉßöÎÒtFÚ[¥wÞ­ÖHIHñ©½Ñ³‘;p^{¹ò7ëÊ8!Åæéòê[òæ_#¸´¼C‚4_H¹,Œ vÄÛÔƒä€y‚DßOiGÁ¹ã• ‰ V‚¹Ùü;˜|ʉ”ß;í?›:Š]¶ýÞN??S3¡/ß[ièdRŠŽ< ðé¡é†b ‰ø9ú©T²§\z\½'b„*Þ_«½Ï`éÔÁjVNç8>á6ا^¨üchk­q›Û­†0µ(UíÓÛ¦PX˜ 6”r]ˆkñ7Ds2¸¶¨>ûT]P²T ¿ˆ¾¨Õ4‘ßÇžGä/©¬(Ոͻ4XÛüW˜ÆÚ=ë]|$Àô'©`WºÑUý}Ùu\•;=8Ã/+-Oµºü•b&ò‡úZ¿© %^ê `}wîä-U@·C˜ÙRHó‰žú±ü}tòá>掶HÔ'ìš„t@ZHRR,¬ç£7àž=Z]B*/]Í.èo}›˜‰Ïʯ†8?_ð¶LÓòð-%ð­‡Iœ;´wi£Ä TFœ7Ëü)ø ûJ‹†z³Ûƒ$£OÓˆ76UÔ~'g¶>’úVéínN¨ %÷îDoòЉnNœÐ{9ûui‘è^™/¯šnnÊÏiÒ¢M‡uÖéЦE3½Üë½Ì«&‚ü'ÁDÛð|¿!cË0” åï÷ ãfì¦6>?fÅâá‹„”y— .669 ÕëQ.Š'uÝmœgD‘¦ƒÍ[¿¸XX™×ø:E|òøøx@DHÈ¡¸±ZV}–f{–NŒ² H"bB¦e‹PÏ‚ƒ« ]lll,•‚æ7V@1!!bh˜Lke¦‰`°§8ÿßwÆÏÐx—»tEXtAuthorAndreas Nilsson+ïä£tEXtCreation Time2005-11-24ég%tEXtdate:create2016-01-21T14:12:10+01:00Iåg§%tEXtdate:modify2016-01-21T14:12:10+01:008¸ßtEXtSoftwarewww.inkscape.org›î<tEXtSourcehttp://tango-project.orgïâ– tEXtTitleDraw TextÏ ‚CIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_shredder.png0000644000175000017500000000066713561570220020236 0ustar otfriedotfried‰PNG  IHDR6šqgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<-PLTEš¡M;f;Ý tRNS#?NZ3(A&eMÔ pHYs  ÒÝ~ünIDATÓc` 0bÝ Å@À}fo‚²O3ì9³ÌfÙsf÷™ÓÁEÞgΜÙVasì9s:jç3§¡Â ³j6@Ù`½0óO/‚™É}fWö™í`6Óîå L¯Ë!Š” ˜”ˆöˆ )b‚Îö%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_rectangles1_32x32@2x.png0000644000175000017500000000101613561570220022046 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞbKGDÿÿÿ ½§“ÃIDATxœíš½NÂPÇ|¬¤¡‰3‹K…Õprõ4Ž$¾ oÑwŒq‚„0 ‰A®”Þ‚h[ ‡æž_r“žûÅ¿ÿôœ´á‚¢(ŠÃ”v ¨¦ØÇ”à;=§ª“¢õ¥5g¥,-@ç Hžçž]Óé:\,ô¶‰1¾2¯Þªžgb ±ÐÃiµû¤÷ê| 8o@²` ‡Q<ņ+0Æ9êJKmÕò¡€ïOh Ȇóìªx ƒ”ßá<Œ+0?ƒk¾}](~5`õasauyÀ§7Æ ‹ó) H F   -@5@Z€4j€´iÔiÒ¨Ò¤Q¤H£H F   -@5@Z€4Îæ,àÉ`ภã4zÖxš7P±º‚¼îó›ñÿ߇O?,Sž_¸Ûµ—ó)à¼Yk@å±:иµ;Z-ðý(xyI´×>´3®Ý›Þf‡ïCÛ’3™$6ÀùpÞ€¤)0)$ uh×ëŽ X>ö!ÝîñE}Èç (ä·“gE<Jˆ¢(ŠRd~+9åÜû±úÿIEND®B`‚ipe-7.2.13/src/ipe/icons/snapbd.png0000644000175000017500000000053613561570220016674 0ustar otfriedotfried‰PNG  IHDRÕkgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ< PLTEÿ€€ÿÿÿÿvn÷³tRNS@æØfbKGD Lò pHYs  ÒÝ~ü3IDAT×c` €IF0ÅÂs€Hj-Ëë? À)FˆD1 ÄÅ€l, XkŠV¸s%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_rotate.png0000644000175000017500000000206213561570220017723 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTE4e¤4e¤4e¤4e¤3d£3d¢3c¡/]—-WŽ/[• J‡pÍpÎqžÎqŸÏrŸÏ4e¤k˜ÉO~¶N}¶N}µO}µm›Ìÿÿÿe“ÆN}´N|´h–É`ŽÂM|´M|³c‘Å[‰¿M{³T„»U…»V„¼V…¼R¹S‚¹M|µO~·P¸Hx³Jy³Jz³Lz´L{µL}¶Cs¯Eu°Gw±Hx²Iy²Iy³Aq¬Ar®Br®Ct¯Dt¯Fv±>nª>o«@p¬@q­Bq­Br­Cs®:k¨w[ò(ٟ׳µÏ[<€&y¢j5‹ÏYJ’¥àÕek¸çœàp:5$OW­¦…8çÌ(¿–k®¾%X¶¬†—<ÜçMsqÑŒ»¹qÑrÍ¡é7EܼUµš¼s€@‚©%7pë7×:Ü®Œ‹•`çŠUL>' 4„|Üð{ƛͷo}Ò™;vüKçÝek˜÷¥ D¬+áH+7ixŽP¸™¯_¹J›;÷F ÉSËVó‹Ñœ&¿0!â D ‚BQßò­í{¹lîý\}ÕÑ?^¶šFkšüÂ$x@O]h  Å»ÆÓ›™U~‹ݯ9úÍá4j=Æ~yˆ¸W /z¼íïs´å¦]ÇÍ‹W9Üé™—EÒØ½´†’³zîg¦P!–>Ê,Mr„9šÆ…J1U(œ 2Ìûž¸bÁýÔz ©,”²PÈØVY(«§§P6ñV‚¡“üi³Çð·Ÿò+Aå£Ë¨ûB¨ZÍL w  Éw:\fqÉEæÏpääL$݇ӑEVF¹cÊxÿðã(i¢P½â¥²@É,\ŽlÊŠnGJ“Ú7¶Nœ8EpKM¿0–¬b¾®ó°RÜ0vìyæÅ³owN™t¹9ÓÐ5 …ivaZa +(”Ri~ ¥L”R £ßߤ²Ð„‹²¢[Hsæ²åíyøð» Å=5+øÍç Àãal·‹Ÿ ø›’És­+/ù{Ç„ÂKA)‚á&ºº[…O‰ú±d¤Ï½éïê±­Dbõ¡ú@X2BIáõäåÌf÷Þ'y¿nƒðÓ5Ux¨Ï@Õj.S‚ÿÉÊÊ˽þº‡œ¥E 1̾À~Áz,dŸ8e²/æ±­AW¨‰`¸)£€`Ú¤o3µè6öz‘m;~'•RðåñÃgîŪÏú(Š¿[ÁËs.¼%ó¶o<í—3oÇ^Nùv‰úPÈ„«Õ?&··ÕïœRmíutGN£”ÕÛÚØG$êcæÔ;)?IÔÿ¿Yî¼zᕼ²e ‘OÀÒÕüxúº¯Ý§_±à_D(ÜBKÛ6ÂÑ6bóy£õ S½z¦è~ è9&ñvÔ5:lûÕÓÑu„òÉÅä’9Úñ㻊º‰Þvy%¯îØLàS°l ßð«oÞP#fO¿ƒ¶ö:¼u€Bˆ ‰¢b"E¼ÉÎõ †›è 5Ú—Pä$¾Îý”—|‡ââÙúƒó…â–…WòÌ–-˜vmg#~É*þøíÂkl1-Þ­t…{ßìP‰#}6¦ y•Ë‘Íô’ï1:ٱ뗖DE5É=ádmF Àã!+¢ñÇ fÜ Ï™ñqÚÿ`=Bè€%A€R  T¬ô“5pôíÏ…Â'1­Ð ýIsŽeþŒÑ„›õ–˜Þ¶ÆNiQY³’wk7b5™y®»â!-<Š/ðAL¼’1)‚>P±Ž%2‡b#ZÅÖABõƒö%3½ˆùÓW`ݬ«}Àh´¶J“k×>ÈÇCé€%?¥BÁ*¯Y¢išÎ‰¶}#-báÞ/’•êß“Ðb‡2ü@Oˆƒˆ~¢FÒƘÌ2æU,'Ø}šõµÁ`Ç1©qíÚiŽ–Ð<|^ÁtYV\©ð½%#±¸ïé;ªïGO*럡g_Ùeý˜ –øÆ™ÅÜò%xÛðzmµaD»?ŠEk—Ò6\-)x`-çaò­ËÜ­GÍþÀþ¸x…V\ŒH(qAñ0p9²q»òp9ÇæÌEÓ\($ºH$7ü¡× +H0ÜbÛÂq—2{Ú?Ñ|r6ÿ«)¥¹ÕppóÏ ˜Šž”8Lîr:ÓdÉÄ+õ¶@]|AÒãð±0(Õó™ zc³ËÉΘBškJZ„Â>:»š GfˆìÌ ógǘɘûwtŽ{L›4þ:f–þ-G6òÆŸŸJS/§…ùë5¢)ëIµpû39t‡çÁÞŠžŒ/4P1áºî&?g¹cfbšašZvsððfóèñŽînŸ… U€WAñü9ßÉŸ?;ž/ jèê>3ŒK'ÞLyñwÙwèE¶mÿO%àé´0?öx©ˆ‡±˜?¹øR Ÿ$jtöÆ~ŸÄB =m<Å…_%¨Û÷¬Ú¾ë?G;[‘üV^‹¸Ùóø}t,­æ%·õx’TÞŽ÷é?K*Jîdʄż÷á¯yçWY³ÏH„@ÄÅE ´¼Ü ºÃ§ˆ½ØB!”Öc2K))\D›ÿ ë6<`øýMÀ_Ïõ‚¢”‰×¿§_æBç‚Ò{˜˜Ûßù7>Ú·Y¡ñ5UeBÐÒÕÙ¦IiàtdõËYé“ðu¡#Ьi’_Ž´C—Ìðèl`}­ÇwwV¯¤õÓŸ2%8hYÒÙñârd'Ì‚L÷y44íEh|P½œæ‘vÈë?À뵫MÓŒì”:‹×.¥óÓ)þŠ÷„F»×ÿ‰‘YfJ%­ž–=“öŽ&KIvö\/Ú€¢ŸQâ?;5¿Éú?=b™fäõ#§¹~íR‚ñ6‰/Ÿ€5ËiŠ?74î åd”=£M û„]w[Ñh·eXœ"æYºM±=®¢±¹Ž ›~®LÓúý­ãŽÇ¢ý¨€Iùß ´xáð±­­-šŸsaH‡WàhCqºÒ£t‘l¤“¥¡`+ª{ôIþ¡)æCv×j¶Ï¥ $• ÑÚÆ&‡«íΖSïè ®vyÛ?jQJ:•²²³³ 5S’ïHh—¸xO¨h˜å=¿5Èv°ºý''Êzb¸—ò¯§3RϽ½ç©·«@äη„px#F—?\¹©ëLƨ;HpçÆzª{„§H:v^`W·Ë7=žakƒ}6E´Üš32O•N¾l|QÁ_æyÛ÷×»]c›U–Uwà¿`½uüÑ$:£|´—ö„}aS6u»ýeH³`—¹û•Ãû1¦ÏTÞÖŽ™³*n/ÈÎ,ÑOùêêórfæ¶wÕ¡à‘†=»i¶4œ2ÀH„Ê@ùh{vã/-íêRú)­¼ô„Ò:"âNÃᣛ"ÞuÀçC&6#š’%®øÞý“M´áþ¤-;+C–_Q`šfg†+/âë®7•£!ôỜBlbì¦"|0.5€¡: ¢³uô í~ï®Æ1…9]ÇÏrQ+0.·4\l«Lw‡ƒÇŽJaäG#®U*çì$ë€íñh>ù„ÐËÏï¬/™”²pÂ4•Ÿ¾q¤ñ-Ó´¤Ñv#Éýt›û¦",%±vçR |DĦMoü¾àÉ¢ S Â`š˜ÙõÁž7#ºŽ‘6mÎïÉ:«9—*€~Çí ´d£c âÀæÖ­[;***´²²i™ee ¨­Ý0Ms`‡z„Iì0Ã)v÷ê\?K¶H%áœa¡PHmÞ¼9‚•••Y áÖÖVk¢ÂÚ #ÙˆŸÍ<{FÈTVVº/¿üòÌÆÆFóùçŸï ýy“lÙ;„á™pŸ¤#¥Ûí&>zôˆ$ÙÐÐ@¼wï^Òͧ¦¦Ì¬¯^½ÊùùyªªJ!ívûp¶e^èïïÇ‹/PVV†­[·B‘UU—Í]»v º®+f3ØxìØ±!ŸÏ‡»w¥CCC¸páBÖŠŠŠ Í÷@ `–`ûöíCH)o-U^^«««ùìÙ3SLéD8??Ï“'OšïN§“Bº\.F£ÑmË[ò^pêÔ©w7lØ€ŠŠ ÌÍÍaÇŽÐ4ÍtšM™@nn.\.>|ˆK—.a||à÷ûa³ÙÞ¶',»×KKKI’ƒƒƒ ׯÛí¦ÏçãððpR&:dúoÛ¶$©iÚ2Uà‹øÆëׯ7›Íðð° ].WH§ÓÉ3gÎp``€$933c®•””PÓ4’¤aÝ5 ëúoãYD£QàáÇ922bíéé¡ßïOÚ KJJ€ ¬H)_eÒ,Ë||l³Ù ( "‘HÂ)ˆD"ðù|8}ú4ZZZÐÕÕ…‘‘†·Û½{÷¢©© ãã¸~ý:&&&ŸŸÚººwH !&Rð©ÍfûaíڵܷoŸÙÑúúúJÐÕÕ•¶]ßúóM®^½š¸råʆ ‹\ßüO",//Oa:±h”TT°  €==_'¬]kkûo\‹ý÷©Tx<ž¯Ž=ÊŽŽž={–ØÚÚÊ'Ož¤^X`‘ÓÉM›ÊR2ãkj¤ËU’þ߀äžLQ2[ËË NNM3ƒ%”`éU¼¢ªªê'·o߯óçÏÑÓÓƒ¹¹9x½Þ„‹h©ýñÂgèÄÇ¿ø%òßY‡ ¶©··WMµYªââb꺞VJüx~ýM¦ìIÒXXX(Nu ÿ…·=ÛjµÂjµâÕ«W˜˜H<5$ÍñÍŽÏ!ߎ?kþW¯ä@UUX,€¦i…Bh¿þ9JßÛÊŠ+¶x™ À/^ô9räqaa¡ƒp8ðù|hmmE]]¤”ðx<æ_þåK! ª*6nÜ»ÝEySY)%HBQ,ñ͆axü5i fggב Çù²Z­¬¯¯OÉgñŠ€ï•nΆþ750 ó7}Ù/Y,‹ˆa÷îÝÐ4 ÇO©¨xy"‘p&ñ™¦(Š7åb ȹqãÆqÁ]¾|9m6ù‡)ΉɌG$)¥ü7ÉܤH*£££¯›››9=9àëͽgÏÞ”~ýß}ÇŸÖ¸xª4% RÊ@¶õüöŸÿH8¶ÕÕ5 ‡#æzàûïù󸿦vé§S ù$kE‘lþô“e=dóæÍѼ¼<¼t¹¥[×õß‘üµ”ò#’»I€Hàïx{H)ÃBˆI!Ä””rZQ”)“¦ Ø$9®ªêô‰_]u£óÖÏbšV ïríéù3xˆ*AÍŠ%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_parallelogram.png0000644000175000017500000000071413561570220021251 0ustar otfriedotfried‰PNG  IHDRÄ´l;bKGDÿÿÿ ½§“IDAT8íÔ=kSaÆñß9ÉI·Rª(íR,â®:Iý¥)‹¸¸wŠhñ ºu*ø‚/tª““ƒˆP¢’š“Ü'‰Q“Ó.¢Üœ×óü¯çå>‡ÿúkU9Á?‡›ø‚÷ˆiÁI‰—áyxgðûÏФÌÌk'´ÊBïâáHøY¬cO1ñ6wØbXIr¿ zoqz‚_Å%ÜYãMqp±ºQ©<˜]À;\.K(¸D4›++Á)žac¨bpý¨ZíæµÚǨՎ‚AbiÚŠ,û|œeíVš~ur· 4ƒ—hŒÛJ-ˆh4"êõè%IwÚÕâžâ2Quø¶¸H»­÷ý8ž(Zëpô®áâXw¸â~õÈq›x­èã=¬b;’¤išw’$^°UºŸàÔHÍÿd_À-<Úâ8_ZêÅîntgg»ÁíRð´j³Ý[^Îc?bn®óÇÀA󇯬\ö¯®½pò„ßé¢QߪǔjþW ¦„„‚ JxÑí9ŠK꬗~û'²Hö¾ø, ˜$^Æà‚R'Ú»wcÁS/åÌœ±ü{…4þúM8²íÓð0`.݈%‚J€<É8C5˜M"€ø¶ÀÀ E$Ú¶®˜9í9“É$–7žÛy¦æ >ã+èÊ„¾\±&‚:JÅg§MY&Œ;ÇRh/‡Õ2 ”ÁÁ!…o¢­k×À¸ ÎÔXÉUbÄøÑËàî»ÄŽÛÚ¯0mq}.>t°Ë“,ÒßYÍùë¾?ÿ—ÖÒ’ÅTV|…»–{‘û¡19cLãZ¬ž„Ö˜Œ¨2€’QOCS ØßPïW´ðªÚõ8ôÐÀÕµ(¤ OÌú锹³×š¤ð ø‚MPÕÁ8P»ƒKŠ&cÊ´î‚?t œk&Ž]…‚Ü™ø|ÿkÁHØû‹7Öã£Tã ÷‚}i3FcãÊåoM*›°ÔÐë=)Ò Î5ppœÇËÛœ`±Ïy¬MV|ð \À}{—h˜7kù¦ûÂÂ'*‚9ÇòÃzCÖ§Äša4ƒ¨|æƒq#íi×­/ jƒ± ~[¥Z0Bôm<Žãw]ÛçkãL)_he`k6l„SMÖ§Dá>X8¿zr~Þ8Úuë(‰-N,¢,á¡¶Û¿“¤ˆª6xWÿ&C.f•o@ûõ3Ê©³Û;¨†ïÖÖ ÷¾ÀÕµ¨]4suùħMîÏâ[ 9f<ÖÆx |òvJíwõ/š˜3¹—š÷Dÿ}a÷U9̼í‚7•%+°` ¿_4ÿekŸ·* ƒ@@âÿß«œkñ¨²`q,UüˆªÁ!}[-aÖä*œ;ÿ—Á¦«_ Z°ò½õÓY2‚7lÄ §cÚt›µ}Ý'âO­ÛËMb/8œÃ X`Ë)†Åä€h æ`"Ýhëڀú6¤ï<ë|sÒ¯pâôÖP{Ç™†þ<·m-”á<ÁÄ€µ³¿Uiñ/ƒq ±}KÉhGQÁP"âz×)õËû¢Ý=Iê8‹ÊÍKýVäœ!õ ,÷%ú™7Sÿ9Ý"õô\ÚaŠ`í¶µIÇÆý‚9Èr§c:éö‰Ÿ±„PŽüÙÈÍ3ÿúSäËÿììjê&¦`ß–WÑú›-(rhj ÀEÉè÷ŸOôé´ÏEÙ¸ç±÷Àk¡[ÞŽwëªP“ÍÖÌv¹`Ò“] +¾øvˆÝ@…ù³AIþüIe0öV‰aü±Þ54B„P0¦ Ç{ªŒ-ZŒâ¢b÷¾ê o §¦¾ ïe‹ÍV pæå:TE %„SØ,ã`ÃÇŸ¬†Ã+6mÀÑTß—•†¯#ª JÇ<‹ÂüyøtOU(ò®©¯ÁŽ{Áf3 «É˜GÁ¸Â@(F;*pðXm(X_— šªÄŸt“‹Ÿ‡M,Å?>« Èr¨²¾î›L¤¨" ÆUPXLvDåA´¶Ÿè­Û€­™ DÀ´Ò@¸ºçUTŽ,Ýü ï dx4U¸=ƒ!'þ`Ð`µŒÁ ÷9…0¾9›òmePe°½^¿e‘ŠÁf»\P¥-ªHªÉ`SWa2Œ€ÇÛá @â‚&e€ðÅ^¬šZÿ©8üfWPRçn^æ¤ï<|00|äî;ïµçMóP"t ‚ER”¨êöÀƒØ–2&•·ë)Áç»a;râÃÖÖëüÉw\p뮿…¸#«Idˆí¼xyw‹³à)óMž¹Eª"O‡MF~U•?ÛÀìøi°úœŸî}8±ÄgcpúÜ>ã7&-›*Šö€¦EE“]¼reÿ鯓¸™¼ ’ëJìR3v?9©ê2Ñe}[F0Ñ LæÞ&ZšGΙñÂä~ßå«NûŒü Í÷Ÿ<¤KÂ&£©ßî¿®oO““úzZpò ‡tØÞ Å,ö¶:ǘmŠ—84¦úähÀ G›Z¯5AJ2@IX*(IÖßíwá›.Aòô66/-Vö2“-gÌ`§÷ˆvóZ¤'I=V@ê(¦ƒ¥ÅàÉàäNõ‘&hk+¢Ý~ìjñØñm£ K•‚‚IŠÏwŒwºYX$®×G6"I*ÓÖ]'$›zCÑÁövwÏÔ² ’—;G>~ø”d4ªPÕ!ƒÇ~;Ý©ësF\ªzª›n¸ÍŸˆNGG‡vèС’’ºbÅŠ--ŸÏ§%A“3OQ¦knrw-Oªý›n»$²Íf£‹-;::XKK‹*I’þ'±>Z©V`¸‰°t`¤é‘ɇ{º;^MÎfCß±‘> w g}nfåáð)Q٤ŇN5‰a!÷“²>èuÐTèÿíô_ÕÏ#9×CÇÐ%tEXtdate:create2016-01-20T14:40:39+01:00E’Èç%tEXtdate:modify2016-01-20T14:40:39+01:004Ïp[IEND®B`‚ipe-7.2.13/src/ipe/icons/snapauto.png0000644000175000017500000000053013561570220017251 0ustar otfriedotfried‰PNG  IHDRÕkgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ< PLTEÿ€€ÿÿÿÿvn÷³tRNS@æØfbKGD Lò pHYs  ÒÝ~ü-IDAT×c`Àx„Ú‡BAYpQ¡¡,`°PŒ9F°Jt*44»S"~Lv Ê%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_rectangles1@2x.png0000644000175000017500000000070713561570220021213 0ustar otfriedotfried‰PNG  IHDR,,„ZbKGDÿÿÿ ½§“|IDATX…í™±NÂP@O ØuÀÕ„00àÂÆêÂÂêg¸;ÃG8@ ŸáD"51ÆO0F’L, Ãuh- B-ÈEÁw’—¶·}y§ém“{ Ãac-ž€rœ¶zJÉdVÄÊÀYœœ’K*V äóP­ûž“ }¨3E§)ðšújw‘z]":i‚ ;I~'©ïä°>%<ºÝ`4ŠÂç0¼‡·{€ë­fF)±~4wë À)ÿ)%Ú@®•ô HnÃó/{³Û ©«¼Öñ¦„ÖÆkc„µ1ÂÚamŒ°6FX#¬ÍúªyôÚ2Ïa¬­ ¸ááwñ9¿* Ô€Fh,bv8ˆm#Ò ê®2‡LÀ² T ‚¾³í:añ"Te¸Ÿ½Û^´Å'Þ¹Z–:ª—n 5/B °ñ}„Õýx¬¹äÏp¿i‹~J|ùe°O.YñéŠñ`mÒÜ6€Ðb´AzÀÔIEND®B`‚ipe-7.2.13/src/ipe/icons/paste.png0000644000175000017500000000202213561570220016531 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<¡PLTE\\\€€`@ZWO^^]ZWPnEmEkCcT:cU;jClDkBoEnDmDlDnDlCkBlDlClClCkCiLddYddYddYddYddYddYddYddYddYddYddYddYddYddYddYddY\\\ƒ„zzs——Š{{uÀƒ$©~:tpdbbaˆºº°ºº±»»±»»²¼¼²Šccb¸~#ň&uqdìíìÝÝÝkkj^^^ÛÛÛrocć&lCƇ'ijdÿÿÿððïïïîëëêhidŇ&ņ&hjd§§¦¦¦¦ííìîîííí릦¥¥¥¤¤¤£¤¤¢ééçîîìììëëëéêêèÛÛØÅ‡'££¡èèæççäÍÎÊĆ&ììêççåææãåå⸸µèèåææäÍÍÉÁÁ¾··´¶¶²êêéää⯯¬ääáââß­®ªââáÖÖÔååãÖ×ÓËËǵµ±¬¬¨ËËÉfhd±€1sobêëêm5pnbºƒ,¹~"´{"ÞJ¹-tRNS¿9ê<]ðüþþüð]ìëüüêéQçüýþìp +?Tj~‹p\G4"é²gÜbKGDL÷oó pHYs  ÒÝ~ü&IDATÓc`€F] `d@LÌÌ,¬ºzúúzº¬lÌÌLQvNN.C00âæäáå«å76153·°°´²¶±µ35± 3 :8:9»¸‚‹›“»‡'DØËÛÇ×Ï ü|}‘„aÀÏ' &ìã¡a¨Â¥áþHÂÕ‘QÑ1±¨Â@¥qñ ‰±Iád p(PiJljZºO@T80À'<,3!15+;'E¤?/¿ °¨E¸¨?»´ÌÇÇÇY¤¿¼¢ÒÇ·ªY8¿¦¼¶®¾Á§ª±©*,ØÒê¾ Q¸p[{ td@……E:=‚€  <ºDÁ±#&.!!)))@†´Œ,$Údåä•”UTÕÔ54µ´uEla³b”7%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/keyboard_32x32.png0000644000175000017500000000144213561570220020063 0ustar otfriedotfried‰PNG  IHDR D¤ŠÆgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<ÕPLTEÿÿÿUUUUUUUUUSSSSSSLLL???UUUUUUSSSSSSMMMRRRSSSRRRSSSOOOSSS999BBBOOOQQQOOO;;;SSS(((HHHUUUÿÿÿóóó–––ðïïóòòòññ«ª¨¯¯¯›››››šåâßàÞØœœœ———ïíí¬««îëëíëêîììñððTmÞ2tRNSªUŽ­Iq89ã·⮫¶åQ"kµÍ´P: ƒ#0.5­ô:IbKGDˆH pHYs  ÒÝ~üýIDAT8˵“‰n‚@EG´X´ˆ­{kÝ BE\žJ+Ø *üÿ' âò224ñ$7¹a3¼„܃—N2ðÀ'­g…««iŽãrù°=‰Ph¡ø /¥ •+Uꈢµz£þúÖ œ÷–Ô¦¡µnOVåCêWz²J¯k"|Ê-h¼ªëêõC€†¡±†â!ƒ0c3‡Qa¶`bÂø |}ÇsLaiÙÖ* ªH°~¬ßcPEÂzåØNTñîÆ=U¼Ãé&ÛAÕüÇ!6&Vp·î.ˆ·ó%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_graph.png0000644000175000017500000000051213561570220017524 0ustar otfriedotfried‰PNG  IHDRÄ´l;bKGDÿÿÿ ½§“ÿIDAT8íÓ«NA€áoK A!¡HÂK PX$I%I-Ë#¬@@VâHð^ ÉÒ”*½ v6)e·³ˆþÉd63çüs沬$¡?Än$vŒLêˆÛ¡ßÀf$öwx©#nÂ=¶ë·þzõ‚vd~ể.FÈp»,1Y6‰Ç—Á`ÆÒ'²½ßT >+Ž,aˆ4šUˆÏåOn‘ŽÒ]Mvä—YÆ&…øý’ \ü”·^Ñ«Oç+„¶È[~¦Ã¹¡’O’8¡vb‡¡UI)²ÛD­…  â…Öm(*H…¨ H’@£((‘@Dj%´$¤’ª(4jkå%µnÅHM»Q0r®½»öììήçòc×ï}ÌÆ%GºÚÝ;÷žùî9gÎ=wþÏD,ìØ¿¿7^püË 6-_áJï®ÞlUà¿:ðË®?ÙÚºv¹9°m[ _EÀÞ§wí~fðž={Ö¯i]}ññÇvDìRi¹YP…B±HßÁßd³b¢­wWoÖ3}Qx§Z×­kWòÅ"§ß¾Êà•Q׊?·í£¬ˆê ÇÜÈÒ?0äZo禵tÞÓŽ ‹ÉÜ]À,ð\øÇ‡N\p¥tgO—+X€»Z"ä¬"ϽtÑÕø æ§óžöùVw½Ü°_ûü½MÍùöWïcÇÃ[nùž· ¼³§³iغ*°h0Éi<´µQ{+í³]ðyÕº÷™;¾:°å‹¢6²GUðz{ûNssÌDÑt»>šeß¡3„uJ{Uãh*$TB,  ¢* GO^b,k5£‚©I޽<ˆð‰G5T¥‘OW›îñ¨$ D4HÂÐHDu~§†1s¶«0ÈNXœ½0LHó74†FÜЉ:ªª¸ãpã†î#¨ùˆ‰ˆFÔЈGtb†FP÷342ÎÝëWâñÔŽI»äðÞõqÂ! »$AQÊ ”ÃB€™³Éå‹Ôcš¼0Àvõtqÿ–uìÿýy¼AÂЉEÄ"±¨N, ¬ûÈ劑ÚÀ¦™'à8PBy7VÅ‚üà›Û9vj£'/ÕÔSu㘆~ú‰øz%uýè©í¼pê~•¸¡‹èÄ XD# ¨' CGA Q†‚²a%ÑH€ž/l"fh|ïÑNpää%—!Q‘ï<òéX€5+Ã<ö¥Mœ¿xæ#­ÀF¨>ì´Ä ­ìÝr (ÝïåÁ­á@Åû‚vR,M¹·ðÃݧ%ZÔßñ™Î ÿk # щ„ü®`g¡u„¢  ßçaÃÚzÀ;ßÃB°{Ç6’i«¼°FÀÕ`§%ôs÷úUä‹%Âzs°Ó P„ mu§zfB°º GÕ‡®QVôyÕ†»T#1\xÆu »Oãÿ[qŸ‡Å‚\…e°›¸m¼Uú–T/‡Üñ1¼Å³xH9¥Ü "–Z^NK±4E.o/ Æ´lJ%§éy‹€0™+Ô,­|‘Ëï§HŽç\—• Û„Y 9nrùZÛ.Õ—³g˜êZøØËƒœ<{yQf²ÀkCŒ&³¤Ò9’éY³Ð”…2“Ré©´ÅÈÍ ¯½9Tµ¤ƒGÄ mVQåS:E"ÁÚÛmf2ÏXÆb,]^dªò9–6Ie-~öìëüø©yá•wøÝñ·fXd‰ù"%<Ó×OK"Œªâ­Ì(A:RJÇAUUÚZŒº¡à÷ª¤³y’i³âЇ2ÉÊü™ÑÿLÔÕ³¨ø¡â–¹Ð£É >Ž”HެŒ=àccû ü¾ºkG øøXû †þ=N*mU¬l‘ÊæfàíâüxIi-o—ÊÖH›¤29’i»Xâ¡û:Õ³µ$ôÓ½µ«PœÑS~ÃÖ’¦òpÁ.ÍÜ@JøÆ—?I<¬5•ÒZbAv|q󬮌Uót±d`(oùB‘>¹U±`³Óhm1øþÛÈšyJMÀVvS­¥'ò¼:0tKo}¦Û+ç®`꿇®öªþ“RGüáHøÖW>ÕôÜ_<–C}ÛÕØ…Æ[RyyàÈ9žx«©9ûž;á—ÜÁV“ª€ßñžÌuqÔ¿‘š$nèì~üWº·l\€”³†ž¦R®¾ûžÕÞÖ.UU¥ks]›?ø?’Ö~ÈÏw¹¿©9SSS˜¦é{ã‹s=~ÿÃ>rþÈŸß¶2±RH)—ë´TÞ–„ŽãÈákCŽiNž8~ü¸ Ì{Ï"ÝÝÝõ°¾Æ.Ø)gÊ yÛŽRªª–¤”ÂãõØ>Ÿ/?‘ž¸Þßߘr -è‚@ ò]¥ü`Þγßà%À,À¬ô7tùô›¢Ûå°Õ.þ ß|ô϶§%tEXtdate:create2016-01-20T14:40:38+01:00ãåÃS%tEXtdate:modify2016-01-20T14:40:38+01:00’¸{ïIEND®B`‚ipe-7.2.13/src/ipe/icons/zoom_in_32x32.png0000644000175000017500000000155413561570220017741 0ustar otfriedotfried‰PNG  IHDR D¤ŠÆgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<APLTE3fª;j§+jª8h§:h¦-i¥6f¥5f¥7g¥6g¥-Z– @j3U5X4e¤ÇÙì8h¦Ÿ¾ÞÅØìŸ½Þž½ÞÃ×êÆÙìž¼ÞÂÕêÅ×ëž¼ßÀÔêÃÖ뜼߾Òé»Ðè¹Ïè¸ÎçµÍæ´Ìæ³Ë圼ݜ»ÝšºÝ—¸Ý–·Ü“¶Ü‘´ÛŽ²Ú‹¯Úˆ®Ú„«Ù‚©Ø€¨Ø|¥×œ»ß­Çãs ÏsŸÏrŸÏqžÐpÐoÐoœÐnœÐm›Ñl›ÑkšÑk™Ñj™Ñi˜Ñh˜Ñ‰®Ø¬Çã©Åâ§Ãá¤Âá¢ÀàŸ¾ß•·Ü’µÛ´ÚŽ±ÙŒ±Ùˆ®Øœ¼ÞlšÑ—¸Ü²Ú”¶Ûi™Ñ‘´Ú‰¯Ù³ÚŒ°Ú‰¯Øj¨–tRNSø üùú÷ø    Àâ®x pHYs  ÒÝ~üýIDAT8Ëc`y€Q ð(`’y¼ (W ˆ_’² nÌ,¬ªÊjêòl€"ö;‡¼†š¦–<' úVV ´U4utõô ŒÑ¨›(+›š™[XZYÛØÚÙ;8:¡)pvqqus÷ðôòöñõó FWàéíc/‹éH Hðñ‚±±…—Y¢_4¾ÈâJò HÆ­€›‡+% 5N–«,/¿€ WZjPº¬°ˆ(†"Q1q ®ŒÌ¬xYIq)^tD¤Ä¥!ΗÅp€¨ˆ°” ˆõ‹bw70 6;ð)°0£0W%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/zoom_in.png0000644000175000017500000000077113561570220017100 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<xPLTE4e¤4e¤µÌå´Ìå³Ìå³ËåÀÓè»Ñç¼Ñç¾Óé²Êå»Ðç·Îæ¶ÍæµÌæ¶Ìæ•·Û”¶Û’´Ú³Ú±ÙŠ¯Ù†­ÙƒªØ¨×}¦×Ÿ¾à¤ÁâqžÒ¥ÁâµÌçoÒµËçnœÒÓàïªÄã0÷àtRNSÌ £¹; pHYs  ÒÝ~ükIDATÓc` `deeÄ"ÌÊÆÎJa4a m@ÀÎ ¦ö²rqóððròñ  #´°²‹ˆŠ‰KHJIËÈʱ¢"¯€fD‹¢V—()cVQÅfb`US 3TÌ,LL,”Ç2ÞÆYÛß%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/stop@2x.png0000644000175000017500000000575313561570220016772 0ustar otfriedotfried‰PNG  IHDR,,„ZgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð àIDATXÃÕ™klÕÇ3;»Þµw½¶×vì¸1q‡$@HbCS ˆx¦‘ª~h!ªÚ R /5•Òª¥mP¥R¨Â£€  P @Ôv‚µÔˆT‚ˆããWœµ½Ù×ì®çqûagÖûtœ¶_z¥£™¹{wÎoþ÷Ü{Ï‘øÊoà‡• ¿ðú|zÉFBÌž˜&ª3u]žéibË`\ˆoéBa†_.koÿþõwÝU.’ÉBÎl`!À4Aˆ4¬e—‹õ÷§ú»ºzcBܲ ôùú¿ àÝð«ëÖí¸vëÖòÉÇ™ …J+k3 Yáp¹¨_·Ž?ü0u¸«ëPLˆÛæ í¸eZyõÕßÏÀ†Ã IiƒÂs똣ˆU/ u|œ–ŽÅåv7Ÿ=uêò«à/½Yô_? ¿¹dýúû6lÙâ™<|-A’¤Œ•.mÕ Ã 11Á’ŽEq¹ZÎ~þùeWëçƒ>/ðnøýå6|wýí·{‚ýýhÙÊZ&YPRh.caô ]'qö,K®¸BQ¥ubhè’k൹ çÞ ¿_½aö«o»- ‰Àæ+[, JV½ ÝÒÞ®8dyipxxy¼öó þ-<²æÚk·}å–[<“}}hÑhiØó…À\*†¦‘ imoW„Ë^mî†7ç ü0<ºúºëîþÊÍ7{‚ýýè%`%Yž[Éóü&˜í{CÓHLMÑÖÞ®˜B¬\5:ÚÔ ox7<Ö¾qã·×mÞì öõ¡ÇbEgO$Bý‰$jj0%:ªlåÔ5gÏ«¬ÌÀÚà†®§¡×®uÎèúe«ÆÇzàí’À»á±ŽM›¾uå7z‚}}h±Xºó`Ý‘$n¾™šþ~bÂV;GÂܱ㛞&c¬^ï³ÏˆZÐùJ«SS\ÜÑ¡Ì$“«ÖLLøº¡§øaøcÇ 7|ëŠM›Š3éõ—rþ"/QɶdEMMÔmߎkh(ǹ,ˤn½•Äý÷ÓãÇ ( ¡§ŸFÔÔ´­zê)ÿ;Cee˜Ì&IBˆ\xÓœxÐjy9µÛ·ãúâ‹¥%I"¹u+©ï}¿ŸsO? õõ9 ’$QùÌ3(½½ 9iXÛµmyàÙcBžåÌÍYó¯³ó[ÕífÜë¥æ¾ûp8Q¨ôwpnï^¨­ÍyY–ñ?ù$Ò»ïrÚ41lØ,Ùêæ¤¦¥B"_Ù¢à¦IÂåbÜí¦jçN\VLÏi’„÷‰'0ûúJ¥2aPTÍ캒Às„A޶™&ª,3*ITîÚ…³È@̆õ=ñâƒRÕXl0ÃÀœ™ÁL$Ðãqôh-ÁŒF1R© ¦R °(:VÓõE–Ú1M*öïGݵ+S/IBˆôŒQvô(Ÿ‡Ã˜¦‰©ëè‘F4Š¡ªÉd*å›q:™ …2PÀvÌwïTåñà[¸õrzf³3ÑÔ„zÏ=,Ù»—<ˆ …Åêò,©°ÝLÊÿ= ¨Êë%ÐÜŒú³ŸßœL–Sã«_E’e.u:ùç+¯RÕóÃéu%ÆÚáæ;Ë «›+++©]¼õ'?Aªª*Ø2I©¢¬,G!ýšk„`UYÇ:;™I&‹».ª°˜+†³J¥ßO][êƒBuuT¶26åÍ7q>Œ¶cf}}f€™¦‰¶~=Š,³ÚåâÃgŸEK$æ¼…CÉ¡-¢p~©ª¯§vÅ â÷Þ‹TY™ {†P^y…ø;ï0òÞ{\ìt"mߎQW—VÝR_»ê*n7ݳ‡”•K”T¶dHä­r™x´Â¢ª±‘ÚU«ˆoÛ>ßl÷[ÐŽˆ<Èñ}û0 ƒãû÷³Òã»ïư»½¾f 8´—•qô‘GHE£Eã¸äÂ!„Àáv§oZlî5MË–‘ܸ³¢"sƒ lO©¾>Žwvbóé¾}È/¼€|î\Á€œY¹eÑ"´·—tù³„àk EB¡{Z–.õV57K‰±±ÂÁD'&¨•$D]ÂÊk%IBùÛßHtuññã#t=Çqrzšðà ** µÓíN  ë”¿óg{{9ùÆEa§“ LNjq]ÿÓA:Bòz]ñÄñãw¶´µyk–,‘ÔÑÑL¦dßHF }ò un7Ô×#jjp:D²·—OöìAXÊæ;Nž;GøäIÄâÅ˜Š‚»«‹`w7Ÿ>ÿ|a¸ÊÊXºlÇÆÆ#ÑèÁxü¯`f¶H=Ùd{O|öÙ‹}… åè‰èÓÓhÁ Úè(3¤&' }ü1 8B!RGŽpü(P6%C!¢ƒƒ4TW#Œ0ÕÝͧÏ=W¶Ìãai[ÿQC¡ÎÂ7:¬·œ³üCPç„núò—›^¯c´··¨reuu4nÞÌé}û05­t æ]W-[Fõ%—0xà@QX·ÇÃ’¥Kéûâ u$~ôGðãl¾¢+ðCPç‚#7\yåEµŽ‘÷ÞË ¤|ùNüó¹öTTÐÒÚÊû§N©gb±Ý?€‚@%S†_CµŽlêèh­ózÃï¿_ ôÿÖ®³a{OŸŽŸ‰Fúcx¤ל9Î.¨ò‘Mk×.­õz#}}YÐÿ)\þu…×KsK ‡c“ªºýGð\)¦9_öBr¼¿£¡ººº±µUŠŒŽbf%Hÿ-¬¯²’E--ô ª#ªº}'Ÿ¿©µUŠŒ¥ß\ \¬ßOÓEÑ=0?šHìø]úµ”ÃjRôÛG)` ðØ6ŽÓÐU n¬÷ù*›Z[¥ðøxúBÕðWW³pÑ"ÞP%“÷ÿú²ü À´¬¬p¹eû¸ê¿OÞté¥_ªóze5šÝâdå!"?/1Í4U/I>¿Ÿ·â¯%“÷÷À1Ò›5ï83_`gpÆ.‚úmðÔª¦¦:‡Ãa/áRÎKÚN ížH'Q! ‡g^O¥ì†Zpù¦–Rr®"[Ðî,+[ uí°Ê§Š ŠŠÙ6ëæBSCž5]m NÏ̲¢ÊÎ8»Ë¶ÎÖQÉ2Ù2ɲìX4HÚÒÍ‚²Í†>ïGÆ þ°˜õ?Å‚v’¼Žë±îùFv× (®\³o,ŽOÐH=Ã7Ü;^öYÌäþï‰@"$‰Àß% ¸Ø'˜[àŒÀ nÏÅN}•Ï$ ¦ˆlÞAC^A+› ‚û"‡róÓ\ê# Þ€¼{@ø³†Ð¾N7t»àûI=`:Í4W9Çf±Ûàû0HÉY.3 >ê ÈpW¦ZÐ.¿‚ ~í7L&Õ‹ª;ìõä]€å¯½\þš7 Ã0ÔðNnŸwbË©[IEND®B`‚ipe-7.2.13/src/ipe/icons/zoom_out_32x32.png0000644000175000017500000000111613561570220020134 0ustar otfriedotfried‰PNG  IHDR D¤ŠÆgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<ÉPLTE+Uª-i¥5f¥7g¥4e¤Å×ëÄ×ëÃÖêÁÕêÀÔê¾Óé¼Òè»Ðè¹Ïç¸ÎçµÍæ´Ìæ³ËåÂÕꜼݞ½Þœ»ÝšºÝ—¸Ý–·Ü“¶Ü‘´ÛŽ²Ú‹¯Úˆ®Ú„«Ù‚©Ø€¨Ø|¥×œ»ß­Çãs ÏsŸÏrŸÏqžÐpÐoÐoœÐnœÐm›Ñl›ÑkšÑk™Ñj™Ñi˜Ñh˜Ñ‰®Ø¬Çã©Åâ§Ãá¤Âá¢ÀàŸ¾ß½Þ˜¸Ý•·Ü’µÛ´ÚŽ±ÙŒ±Ùˆ®ØÉ’ztRNSü÷a4Y$ pHYs  ÒÝ~üoIDAT8Ëc`C021¡ðYÑ3 +ª60`çàäâæáåãBS ,"**&.!)%-#+'¯ ¨¤Œ¦@EUUM]CSK[GWOßÀÐÈØ]Š©™¹…¥•µ¸­½ƒ£“+~GÁ@ä(@šk €?ñÒ×%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/zoom_out@2x.png0000644000175000017500000000166213561570220017653 0ustar otfriedotfried‰PNG  IHDR,,)Zª3gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<¹PLTE9h¦:j§9j§:k©9j¨;j¨:l©;j¨;k©:k¨5g¤9h¦3e¥5g¦8f§Ÿ»ÚºÏæ¸Îå·Íå¶ÌåµËä³Êä²Êä°Éã¯Èã®Çâ¬Æâ«ÅâªÅá©Ãà§Âà¥Àà¤Àà˜·Ù«Äß©Äᢿߡ¾ß ¾ßŸ¾ßŸ½ßž½ßž¼ß¼ßœ¼àœ»à›ºàšºà™ºà™¹àšºá ¾Þ¬Åà¦Ã៾ޟ½Þœ¼ß›»ß›ºßšºß™ºß˜¸ß•·Þ’µÝ³ÞŽ²ÝŽ±Ý²Þ–·Û˜¶×Œ±Ø†­Ö‰¯×‹°×‹¯×ˆ®×†­×„«ÖƒªÖ€¨Õ~§Õ{¥Ôz¤Õv¡Ôu ÔsŸÓpÒmœÒk™Ñj™Ñi™Ñi˜Òh˜Òh—Òg—Òi˜Ó{£Ò“´ÖŠ¯×ƒªÕ‚ªÔ©Õ€¨Ô¨Ô§Ô}¦Ô|¦Ôz¤Ôy¤Ôx£Ôw¢Ôu¡Ôt ÔsŸÔrŸÔqžÔpÔoÔn›Ôm›ÔnœÔq—Å„¦Ï‚¦Ï‚¤Î¤Î£Í~¢Í|¡Í{ ËzŸÌyŸËwžÊvËuœÉt›ÊsšÉq™Èp˜Èn—Çl–Çk•Æj”Çh’Åi“ÆbŽÀG26tRNS‡Ý«±Û²´¶·¸\wyn6vù³ pHYs%%IR$ðØIDAT8Ëc`£`Ð02áÌhŠY¡@HXDTL\BRRJZFVN^^AQ‰M1›²Š*¨©©«khjikëèêéëë› +f753 -2KK++kk[;{G'gWtÅnîž^Þ>¾~þAÁ!¡aá‘QÑ1±qñ ‰èŠ9“’SRRÓÒ32³²ƒrróòC ‹ŠKJËÊ+*1sUUW×ÔÖÕ7465·´¶µwtvu÷ôôöõO˜8qºbnÀ |`ÿ@Gì( dþ2ØÈ 3Ê%tEXtdate:create2016-01-20T14:40:39+01:00E’Èç%tEXtdate:modify2016-01-20T14:40:39+01:004Ïp[IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_parallelogram@2x.png0000644000175000017500000000150013561570220021615 0ustar otfriedotfried‰PNG  IHDR,,„ZbKGDÿÿÿ ½§“õIDATX…í×Kh\UÀñß$£-‚1CkF´¢Õ–B»KºWV)­Ô.ŠOD(m%,º”,\éR\X©‹F´JڅР…vá«õQÒ‚¶éƒ¡±¦¹.ν“›IÈÜ;™! ÷Μ{ÿû1çœïRPPPPPP°0Ýÿ§ÅÖà'lÂݘÄÅÅJuŠeøQCùû°½Kf7#‚àoxŸâ’Ùòÿàk¼ƒ èZS<éXh ÕÞ-ˆ½…£ñóô ü‰ýx ÷&ƒ"—Ɇ’´¯hUvþŠÞnÒwžÃG8ß  'ñÞ£<5)+[‘-ã›xÁãòoÚGÌDÿïD¾'-Ö×E7†R­.ZøÝx‘‹¸§• RÜ…-Ø×ËùºØ¶mQ;æ—s,ð$ö ÿÝ,þøºŠ80AOü»)Y…«øXØåïãp+†™8uŠ¡¡PkiŠ.A0·¸½Mju"zÚ¹éöƲXÝnY8GoVárü†%ápOÚnƒÓôí祟ñæœë„ðZö¬C×Ùú"ãót›¨×"º3¼áÅÂ3g3XBá ~ >ÈÇeáZ=ŒC¸Ð¢ìá<‡×ñsÖ%Â_S u\Ãø/© +æ,¾À¨FΊRÄv<¯³j”Gx¹ÆÊ1~•u£5LœuÓ=$¤†£Â×E:ûª Ñ߃ãy-4ç%óº&.ᓸ­l&ÑN’pØ] ieÂèrŒMXß0÷ÙïYö÷-°þÎæ•nk± _ ÑŽŽ%Ñ,•fNžáát”ßX*ÙF–ã©3ü^NM å8Oz™‡IY¾¨ïÇÌÉS«¥ûå>";%œ0ËJe¾ç“y'ìôWl».™:Žðqá²éjX+¹‘~ìðúÿuþn@™ò˜óIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_rectangles1.png0000644000175000017500000000053013561570220020633 0ustar otfriedotfried‰PNG  IHDRÕkgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ< PLTEßBÿÿÿR«ñÌtRNS@æØfbKGDf |d pHYs  ÒÝ~ü-IDAT×c`€Q0%¥êÿÿÿd#ZR¬ Ì@ë¾M[Í¡€‚(c) µ‡Æ¯%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_rectangles3@2x.png0000644000175000017500000000151013561570220021206 0ustar otfriedotfried‰PNG  IHDR,,„ZbKGDÿÿÿ ½§“ýIDATX…íØOhUÀñϦY­Ab¥ÄK¥TmQ+Ý›ø— *^D$zè©Ðc‚ô"^”Š¢øç -Ô`@<±R”ž´Bñ¿­m!M…’†6Mò<¼·›ÉŸÎÎf³IýÂcgÞþæ½ï̼÷æ7C›6mÚ´YK64» ›p¡E.+Î'ø¯aÇÚêä³—DálÅ[¨ c­ä–b(xOâ]Œ™/ïà”×FsŽ÷E©ƒ™ºìÆ!üm¾ü¿8‚q󪚢ÓÜÕ¼''®ƒâÏÊObX”ïn¥h•‡SÇ6pLúq³æä§SÝ~Ü^ œL䔞F„§ÎÞhä  w&Á˜ÉÈϤºþ&!§ôí¬ÿ¤Z¦p–ÛÄ¡1Œ©ªüDU¬»;„J%–-[–%¼+5zÖÊ/[·âe ׄ+•P£¿IázϤß!q,®$ãx{ºâÄ,DgÿŸN¿Ç–kU„R¼‹ŒŽ20+o¸{ņÆÕ?±¦H+A¡I×™9èuÜWÝÿ™»Î`W·óÞ,ñy+Å"ðe³ÜÛ¾{úx¥—°‹ï½ ÊÆjìÒ·ºœR˜žn•gRÌQ^M»—øáz±‹W‰r™©©XŽm‘â"ºðhÚþ4/°ðÚúAL!77!•Çc¢ô÷ø#/pñ¡¡¸}òd­ú^ÀóøV|Rï+ã[[ï‹/Ÿõ&ÝNáªù™Øi1CÛÖ„lS{Å“œ‚«Ä-b.p äsãÝ(5 üx:þ—"Áµ†OàŽœØ¯Kü”Ù¿IL=ŸÃSæçº‰óa|%¦•Õ~ö‰ã¼Í³£Ü7#/Åõþ£çŠÈ7ÃIþØYöÊáCñ5ë†ÀX;ù@«e²Áõ_.^âÊzÎRƒâcÿ7„±ªØÖ­!ŒŒÄÒ×·n„²ý2—!ìÜ9—ûni¶§RîÛev–É”_»¶Ê Ðì¤[W_kаÚC>“ÿ}b|µDÚ´ióä??8žKÚíIEND®B`‚ipe-7.2.13/src/ipe/icons/redo_32x32.png0000644000175000017500000000323513561570220017216 0ustar otfriedotfried‰PNG  IHDR szzôgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs  ÒÝ~ümIDATXÃÅ–[lUÇÿß™Ùݰ7[ ”bAŠE¨7î‘.C“Õ¢QôE‘'_äÑh5>iâ’0!* aM•…Š”û‚”µ@i»ô¾K·{™Ûù|`w³]v …ÎäË9gæÌ÷ÿÿœ™9ÄÌx˜EÜoOûÊãÓî9Ï}Ø"üæñiî‡@óf,].÷ø´Š‡€sV:7¬i ³Ÿ6óRP_Ó¨¬zæ¥É$D«Ç§-x`‚€ŠA³S*kź%¯–(B=äñiÍ€‚a£L*…gù›ÅšÓõ£g»¶ùŽ÷ç;àñiEšHà5"zŽ™+«77Œ~6›°Ù@±R²TüÒòCl$9üõÞ·õ­÷ àñi+H`÷”òZ­¾ö© å«h‚VŠ"ç$RJœ‡Å&$›°Ø„KL€Š"øgOìf4¼%6ø½º9nOs’Àç%îÉ›¼â®-›‡„Î1˜2 S&`p6°Ù‚Í’v¡d*¹På¬Ç¹‹gâ½ý7N³Ä‹~¯½kO›L.~|mÍ’9ë4:ò&$[°ØÈÔiëÓ×â­HØ€&&`ªk>þ ^Ð;»;®±ÄB¿WNk¨cÍ^(øvÑœ5-›Ý¬D­~ÜZlÀ­ÕŸ®)ëLÔêψ@±ZÓ´080`Ø“->&€Ç§­ª)¯_³pÖZ%bv˜Tœ9é¥[@ŸÌä¨pÖA³KqôÄ‘¸n&?ðoÔ¿ÌÕQ ˆ;I`Çê§×»bö ,Ö! ‚Á &¸”‰PÈ‘ý$Ñ<‡a³†Œª´Ù ½GO‰›¦¹ÅïÕwäÓ*äÀ†ºê¹eÅÅŤ‚LR«à`7þë=Ë]—Ã}2,z«é}Á,Ño´ª] °bÇOý·mëu¿W÷r:?anÝä׈5É“œU µãÀÉ݉h"¼‹‡´ Rþf–èÑÛ´obŠëI$†m´ž9“R6û½úá±ÖY^¡ÐeÅÕdÈl¶P☊öPÀÞòû–Xï÷ê-é±/owso2ˆAý*¦¹‘§'£,yµß«·â%¿Œ:‡Ã]F¡ 'F¿¶î2˜±ÈïÕ»³‡J–ˆÙƒ˜ænDÏ}¾íl˜%?ï÷ê—î$^€™+,J@² Šq¶½%Á°?ËO‹“è¼Þe¯^îa‰e~¯~ýnÄ?#A„ã}¸õjI\ëicfì(”äRð¢¼zù K<;ñ‚ZRîŠt˜‚ÉL#n™1!"AD ©é€®Pg |U.ýy“1”º®¤ÆÒ=¸MÞê¼pÊ– G©æG/I'€ÜФÅû?Y/Ùf%s®98ˆÈ‘‚Í t‰ïÞ³GÌÁø§7.ÆMGåôʲ©3ÄŠ\qÎÚۗvñì¶š®SîÐmt«(ÊÞmÆÁP{pëp¬7RZ^-J§kk­AQNrçHÔ4LîìSÂéP²ƒˆõ7LPRP™ö¦½Í³êæ¿“L ›m¾ÙÿEòÄP/l”ã w;·OÌŒ”%£„³Ûë>)«YÒÔøFÌr^h¹²ïàGÑ`,šqPäˆÛãhÛ¹ädúå3çÊw§Ö–ÌPêú®ŒÜ8¾3ÜѰ̔Ùð]Ì\°™Ùµ!ÉóÒ‘qÈQD¢zžê,Ÿ©º”H—Ô;ŽéI3N‰çÉ…²˜YŽZÙ‹±€xvžuîkÅy"Âff{”ÞX[²L6P>qJ%Ï‘çBãÚ–ç€eºÙ<΄ÿäÙäå6bƒ%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯tEXtSoftwarewww.inkscape.org›î<IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_stretch.png0000644000175000017500000000216513561570220020105 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<ÝPLTEÿÿÿ J‡L“¶Êå®Äâ±Æã³È䃤ÐUz­œÁZ~¯ÙãñKŠ©Óÿÿÿc†¶Œ«Ôz–¿ J‡‹¡ÀKŽmŒ·8cJv®Kv¯Mx¯Oy°Q{±¥»ÖT}²V³X€µZ‚µ\ƒ¶:ežNy°Pz±S|²:dV´X´^…¶¬ÂßJu®:eŸh¡U~³W€³=fž[ƒµ]„¶^…·`†·bˆ¹£»ÚP{±R|±?h¡Aj¢Yµª¾Ø]ƒ·Em£bˆ¸cˆ¹V~³Cl£?hŸGn¤dŠºd‰º›´ÕÔßî9c§¼×;e¨½Ø>fžr¸t¸Ho¥fŒºeŠºT~³Fn¤Hp¥gŒ»h¼hŒº[‚µ\„¶]…¶En£Jq¦i¼j޽i޼“®ÑZ‚¶Go¥Jp¥Jq¥Kr¦k¼m½n’¿Y´[‚¶`…¸b‡¹j¼l‘½n’¾q’¿ÿœ¨%tRNS{{ (".0126:=><5 FŸGbKGDÿ-Þ pHYs  ÒÝ~üUIDATÓc`ÀT¡]XM]CSM SXK[GWOŸ‘ Â:†F0ÕLac]#CUS00ƒP¦@a5=5Cs50°€P¦ —諪šZZYÛØÚÙ;8:9»…€‘ÁTÍÒÐÕÍÝÎÃÓËÛÙÅÇ×b©šŸ¿a€]`PpˆshX¸/\u„[¤aTtLl\|BbR2Lµ¯[JjšazFfVvxNn2LµoJªC^ºa~AvanQq D5£iiYyEeUµaamq]=D˜Á4¹Á1ÄÙ%¬Ñа©¹¥"ÌÌbZâåÝÖÞÑihhØÕÝÓÛffec7-ÉèMhœP;qÒä)S§„Y88¹LK¦Ïh÷™9«¾yö”9sç…™YÙ¹yL“!  ªyMÑÈl>~^AA!aQ1q I)iKXdd9¤åäùäå8•””¥UXä%_=lj%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_ink.png0000644000175000017500000000231213561570220017204 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTEÿÿÿg9h9j:g9h9vAk;g9g9˜[…J g9g9g9œe,k= g9g9g9•c-g9g9g9ˆ\-qGg9g9g9{R&i: g9g9vM|P!i:g9sGj; g9g9nB†Tk;ƒymƒxhk;g9€€€ŠŒˆ®¯¬p@ g9ŠŠ†’”„Z+m<‹Ž‰Ÿ¡†€sg9‰‰ƒ‹ˆ¦§¥ŒŽ‰ˆ‡€‰ˆÁÂÀžŸ‹ŒˆŠŠƒ>>=™š˜‹ˆŠŠƒnpk‡‡‡ÔŽEä—E™g1ç‘7¶x6Ôˆ9»lŒe:Á€;Éq•d0¯v<Û|˜Y‡b9›m<è…¤[ xV1‰xbË{'¶d}R#—f2²³±ŠŠƒ„[.–j;ôôôççç­­¬‰‰‚ÈÈÇùùùÆÆÆ£££öööàà௯¯øøø»»»YYX¢¢¢uuu„„„??? ’’’HHH$$$ +++;;;000 U ŽòwtRNSˆu ÈûÎÖøöuâûöãýÈ Óûô^¿øò ¥õ÷~‰ôõlôø‹vþê çþõALðù™Æþ÷ )õþí(œûýì% Ÿýýë#Ëî"ÁŠ•i&$  fæOG?7/'nóòðغ,%" ÌDUbKGDˆH pHYs  ÒÝ~ü÷IDATÓc`@ŒLÌ ˜€…•S”ƒ“‹›C”—¿\@]THX¤¢R]TL\¢ªZR MTZF¶¦¶NNMXA±¾¡QIMTEµ©¹¥UMUTC³­½£SKUTG·«»§·OOEÔÀ°ßhÂÄIÆ&¨ŠMÍ&O™:ÍÜÍ>Ëé3fβ²¶Aµµ›=g®½ƒ#šb'çyó]\ÝPÝ=<,ôòöAõõ[´xÉRÿTÑÀ eËg­XŒfnȪÕkÖ®[]µjÕ†›ââ“’SR£ÒÒA¢™™YÙ9¹yù…EÅ%¥e`A·¾BO·,‚%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯tEXtSoftwarewww.inkscape.org›î<IEND®B`‚ipe-7.2.13/src/ipe/icons/ipe128.png0000644000175000017500000004531413561570220016440 0ustar otfriedotfried‰PNG  IHDR€€Ã>aËÑiCCPICC Profile(‘”ÏKaÇ¿³(A`f{ˆ¡CH¨LeD宿شmY”Äìì»»“³³ÓÌìš"^:fÑ=*úé*˜“––Í9R»,Ÿ•"t%1)f¨m-’¢ë’ë²%‹ÙÌ*±tìÌ©vO¥žv¥æS¹¼Aç¯ö°õ°\þù¬\ÞzN=¬/õßÀ¼ýEN1I pHYs  šœ IDATxœì½wœTÕùøÿ¾wzÙÙÆ6`éM@AAŠ4QŒJŒ‰FŒ)£‰£Q±b4ňƞ»&ö(*E© Š €Ò¤,°´eÙ¾;½Ý{~ܙٙºË&ù¼^ßßózÍkwî9÷̹÷yÎsžvžGâÿ‡l åÐGüÇgñ‚\îÿ9òÉF#€@O °EÚC€hŽUÀV`à{õÕò€³ÎRß¾øbvîÜ©/++3™L&s^^žý¥õž!m!¥lÞTGP,„(‘$©§$I¿ûï>2èÿÛ?øî»OæþûÚÊ5&à à|`&â; z½^9餓œ§˜Š¤Ro›×ë5˜L&FŒHnâ ËvùB IRôÿ{%Iòuõ±þŸ©÷­Ñ“š{IBéÚ·ëì÷Eú!dUUMªª:„¥Bˆ~ZÖðý…‹výdáÂ…×7î“ÉäA#†.$IJº6zôhñ׿þU£Gî¶Ÿê~›Í&z÷î-&L˜ ,X fÍš%d.eÿøïÓ/¼B8p@øCªhö„•£-¡Ð}oï0þ—Ðt‘Øíö¢^’¤ÒŽ«Ðjð‡’V•]Ý’$a1HxC‚þ¾è_³ÅF~Q† êÇ„3&1ãœó9f<ÞàÔ™{Øìع)é÷⿯Yôã6o`æµ1päxÙb„ËP1XßéIvºªª’$µ¥Ì _8óK¶%¼AAž)}»;˜‰dœ5m;¾V=÷6.zEQâÕ¬ŒóJ1¤[óÈ+*£ ¬%CN§ò”³é1ðT:øÔ#ñÕF/£„ÅÐ3tuÇîÀÓR—qìæ#»Xñйô…¸àœ |´K³ìt‰šššÔââbwª6sjVƒFé Ï$ãÊ€`‡I·Ç{ƒ_HûÔÔÖóà}w°þ߯ÆÚOdŸ·Ú””÷¢wßœ2nÓ¦ŸÅé§ŸF½[aMUßN³¡““9™÷´Ÿ³cÛV¶-y†`0˜‘û´¶¶rÙe—ñÌ3ÏÈ—]vÙX`S—'ÜI諪ª¶F…¸x0ê$„€°*Чx1V£” äyƒo¨‰->•#­ ««±k¾P{O@PïR¹õC'¾À¬‹ABõ6³ò…»ÙôÉë]y¬RRчüòþüø{“™1ccÆŒIè“o–xg«?%ò£Ï8í'·“ïÙÍêŸÄÝtDøÍo~#=zô*àÙz€N@—·Y–ÛT!ð‡‘¨×ÁºAT†¼`"kÚTµøP…_, ÑOX…¯J“WÅb(´ÊôŠk·$ùÔÍ=gÛq˜4"t»ÝÜyç£|»êí¬+>"Š‹‹8p ƒfüøñôqtøyª=åù™¢=“Åšz—Ø9ã¶ßÓpüÛ·oO;¯è|‚Á =ôÐXàÇÀ[YpÐ-Ð%øõ;Mý ,úŠþ°†€f¯Êן¦ÜåbÐÃ&ÓàVéS¨KÙ^–§£(o§v{öì!¤ìϼ^¯ü8|–qÝ]"€™Ã•Ó+ówXtãSQÿŸVº˜=ÌŒëØ6lØ€Ûí¦W¯^Œ1‚!Ʊ·>Œ)‘`3I¸3 y€Ã¤ÙЬ2ï½÷O<ñn·;-›^+--eøðáôìjé(îþé”$[=@E·²»LƒGIK Uyóã%ܲ EQ2>O‡9W ‡2Þx‚Ð%¸xDiPUÕF9Í‹1$¶lÙÂóý=‹/4;fÌ&L˜€càô=5íøy&9£gÖÁ;wòÈ#pìØ±´†¡²²2FŨQ£3f cÇŽ¥¸÷`ž\çaÄGÊ{dIÛzš=*¥y©\j×ÑàJ&ÔêêjÞ|óM^xù5öïÝ•òÞTÒ1ÀýÀ/2u:Qèª dYNëµ2$žòñòšššX¹r%+W®¤Ï€! ;òëæ2uj2!˜õV!¤ ºÔHu˜eZ½|ôÜslذ¡}b‘—ZX\Jßac8úiŒ=šÑ£G3xðàX¿"hó T!ÓN±U¦É›žJl2û›Â ×>ùäâI–-]’Ô¿°¸ŸÏƒßëÉE3Ñ?@Û^ÊÖ¹«ÐePÅ#ËrÊUg’û"”OéÑÿØËá{©ß½žK/½”o¼»½]Ø’$ {ÄThMG«W,åÍ7ßLú_ÿú׌Õ^´ø‡šÃlQ¨w«¸E€Q/Qh‘iõ öÐ1u ‰ñ}LdâÜ“Ì\0Â̬!&Šm2°à×mœÚÛÀɆ•êØCOŸB•…:>ú¶‰ÝKŸà©Ç‰ ¡©ö÷+¯¼’‹/¾ƒÁÀøñãùøãihhÈøŽ#õ@>ÚVñ†®@—8À‚ àO×n6Àð góì ¯°téRÖ~º†Û¿Íh_¹r%³|5çßö2˜ Qmó“gÒV]ü ô6cÏÆ R‹!7L±qÖYæ-rò»ö´R|‹OÅf”Ô#õk(¶I4zÒïÕ¡PˆªϱöGñû|MÎ?ùÉO0™4ÛwÏž=yê©§8÷ÜsÓª†ˆrAÀü<…]"€Ÿ¨2Ž:­¢Ìaѵï‰qû£' ±W«ñtS‡qö)s9íÈ.¶¬|“mŸ/K;nõ·ŸÑ¸ô>^yùeÞßî§Ä&3}p²Ã`Ñ¢ílÿr9^š–$ ‡YÛã‹m©  Ð"s<……6™&OúöW_}•Ïßy<+òËú fРA Üoúôé<øàƒüîw9{ô0èK7«…]"€mÍ5Ê(©§§Ä&c1F <‘Õi5Hì8b£Â/N·¢É1½Ó8úˬ]»–;#GÚešx$.[ü!}ð>öaßÕÂ_àv»Y·n·&‚d’¦ ,2­>•b›œ²½È*³«.y ‰‚Í(£ M.èh³Ø»w/o¼ñ^WkìZº¹ô= «5Y˜¹öÚkùüóÏùàƒÒÎv.0ø>ðD¦Î…Ôo& |vÿôðUl{¦ 22¡¯‘Q= .ÑÓ+_G¡U&ß,ãOáìÝ»7sçÎeéÒ¥ô:hG~tu´µµ±pá˜ÐöîÝ˧Ÿ~šÓ< #Šmšš— zØdSpÊÊJf̘ÞÐÝÖQ#Š~/x:F“9i «ÕÊc=FAIEÊû£ÃD83ãd»]"€P(Hgx1ëÓ{%Ibäȑ̽ûš %DÿVUU±÷›/RZ÷îÝË–-[ršc¾E¢Õ—žCZdZ²@±M¦9E‹ÅÂÍ7ß̧_¦¸ç€U7 Ñk}§5øªUà ¨XŠ+¹êîgú§€hà `lÆ wº.„ˆJ/ áZ‰ ÈâîUÙ—}–Ë.˜–ÔæõzÙüÅJ†\xzÂu·ÛÍ·ß~›ó Ì2­þô޲õT,> é8€l03碱-8ˆÝoÏgýÚÕI}ÌV;Â`çù ^í·"òRH%¶mšžÉÄKï`ý›N7ÕèäzãÍiª“Ðe0~!„Ü‘˜ š“(XÃN9ƒ3f°zµöâ¢+ °÷v*:lµµµ|óÍ7@nÑ=‰ƒ-éû!È·ÈT7‡É3É1;AIÞà@“‚'fw}8vͬÅ6‹úà"µI¹¤¬‚¥f*‹õLhŒÉKæ8J­S!äû ÆãøôÓO3=[1pJƇî$t™ü~ØlNÞ×,¶€(X ¾Lš4)FQP…æ¦z< ¾¾žï¾ûÈ,üí®aÜàh«ÂþÆ0ÿÜäMB¬7(ð‡A'Á«›|ZÚ½•ñBmßB{ÂLdŒ©¡y&£ž˜zyÝÓß 4WS^^ÎW\Áûï¿ÏîÝ»(ïQÀÐr.UÐ+?OAƯÏçñ'Ÿfʤ3b!li 7š] -ã κLf³Y‰ÞÚ RJ!0lF-.0>J7|!ðíôÇ,t>¯áèÑ£Yçv¨Y¡Ä©bÐIÁ€b}»–ÒÁ¦ðæ7>*2S¦ŽO;îTø®.̈rCÊvÝ^<ÀÄ3&på•WrÝu×qÍ5×°dɬV+åyzªêÒoE:Y¢Ô.ã¨ÄóÏ?Ï%—\’ª[T(A;®öMÖ‘t™¼^¯bµZU!„¬ b«*Š,E…ÏöðÇÙÎc¦Ø  Ñ£Ro¾ýIÒØ’,cv” ×i‘E¥v«QbŸ¨Ïinç 33kŒ…°*ø¢:Èý i=……)¥…b›&(fryáq»9r$¥¥¥8ÞyçÞ{ï=FEŸ~¥¼»Ï›qÎun8÷Üs¹þúëyê©§:v‰þxPÉÿšîú88Ìb ùý!¬A…˜ ÊBõ2T7)Xä˜íÜbÔX¿Õ ±óx˜ÏÖ¬ ®*9üÍj±pÁôqH™3ú)wèðx<,öjkt¯^ÖöZw@gN¼"«LMmzÅ Ó8E*§Q|mš?bàÀ8š,`±X¸ì²Ëb„'KN¿ŠÃœZñªÈÓŒRãûÚ¹í¶ÛÔµk×ÊÛ¶mƒö•P–r.@— `öSÕ©} Mv“lµµ‡ ‡Ã!0 Ü÷±‹ï 7QjO½ïm¯:ij÷] ¤Z­VfÏžÍ~-(£ðù|1Ûyg‚< -->A^jq…"kj5/zDì…Ödäµ¶¶p5PRR’ÐÏuÊòdê\ _ÇúƒA*++å¿ÿýïL:•P($‘H64›@·@—íß.yBúxÑÊÕ¿ü9Æ Ãl6c00 »|(sΙÁ¼yóø÷¿ÿMKKK q;vìàšÍ ­éxòeYfèСL˜0»©=x4 &8–r…|‹L[cP.PœÁ$ìr¹ú4«¤ÍfK;FYžÌqWú¨  ‡Lm[{û˜1cxøá‡£þ–(€fÎË8áN@W9ÀyóçÏLÑ/þb”âÃá0ΦZ6®¯eãúµ<þøãH’ÄìÙ³9ùä“yòÉ'ñù4GNÇhÙüü|î¾ûnòŒR,<<Çîé d³ä[4"Ëú•Éà÷ûQB fBN/(Ydµ(ôi k²PPà‰ÓHLPÑåôkvoH°ë°Ÿ&wI’YS¤¾HS9=AMØ"Ù¤Cóp¶*X2¶8­$Ï$Sž'q IaL/ƒzè±%,»üùšºK/]ÓqÏï2çî%€AÀ¯ÐXÚ‘î¬iÏŽ¶éõz&L˜ÀsÏ=k³›Ú%ôTgr‹Ì¾Æv!/êÜñžÈêÓËŸí`1J1;'ØÞÏоo9Âf”p˜eŒ:Mðu;AÈ:„F'«œÜSÕ EYãÜèQyj‡;f¦çÞûØô½ t¨ªªVWWË>ø`4g@¼9´ÐYè Œ‹üßmée$Ibøðá,^¼8vBÀn”8gÉË•ÖWiÜâÃÔ¹š<*U N<ãOA£öWp¤Ua@=™žùížM›Q"¤ ž]ïåç%[ûŽ+fM‰f‚œV™úlg›Œ3bA4éS?GÏ|Ç"r€Ëå’Ÿzê)vìØa#ùÝ–E¤+[@t"Õ“.ƒ$Iô:’Ýõ*¢%Û¶jQ@ûÂÃÑÃö4d±/GÀ ƒ^ù26£DPѳt—Ÿ¦Ø°å”6ÿwúÑKð½á©U…(×H¤ZPP@AAuÍé-x²$Qb“©w«T¤ÖŒ*š{ZQ–-[Æc=mŠÿQÑTØèì^R‹– @ê KNªªòÁ;¯ó›_ÿŠmG}Ô»UZܽN†Éýœ3ÌD¿ÂÜèõ´>FÎhbl¥‘Szð%v]Z‡O‘E¦%ƒ¦ O¡-X­ÖX[ͱڌÛ]yž.£&ÐÓ¡ã˜S ‘»þúë”\Ï4§¤“ÐY؃¢ì;tчܲê]Ž­|œKN±pþp3SšPœÜÓ@ß"}‚%W°$dôMY%š½™Ÿ%“&ЫW/ŽTWÑÔÔ”vŒÒ<™ú H‰–Æ:nýÝm455¥3xµ¡-Än®H“o¡Å¦í—e]Nb¹Íf£wïÞŒ;– .¸€òòò„öxUpáÂ…|ýõ×@ö<¹BA–Àµ 4ˆ²²2êlãàÑãiLjƒÒA(¢úÓ—YµrE*äG¿4‡3N¶Ð üÝh4®4iÒ£À9ÍÍÍø|¾˜š¦Ó鲑°lfÄ€rFÍäÉ“™5kƒ×^{x€ªªª¤Á½^/ ,`É’%õ’DVÇR6(0K´úå©=¶Z5{:çdæ#GŽdàÀ¬_¿žU‡wÊÈ”ýÊót¬Ú›>tÅŠ,ù隣«ö§¤“ÐeSðüùów/X°à_À9GŽ¡¦¦·ÛªªX,ÜR>[ÝeÜ1;ÙlýÓŸþ”ÊÊJ~øãËi®¯I°*ŠÂÆÙ±c#GŽì.ÍhÒKõ™}ÅV™M©…СC‡2|øpÖ¯_ÏÆ¯7s霳bÀñg’¨s«nQÚc"÷UUq߯~ë›a{­F[„Ý]&€ !„´ø¸ÊÊÊ„ö#­ ßnJï›6m?½ñ>ž¸çš¤‡õûý|øá‡Œ9»QÆ“å h6(Ì"äAû6—ÆVÝ¢¶h|Aôÿ¼¾§b4ÛøèƒEô;GÏÁ HÖŽ‘ƒ¢ÂË_{)0·«š„=¼þÄ=4ÏzøçÝ '@’$ !DZJ4ëÁ—Ek;ÿ⟱èÕ'9´w;û³›4‡Ð‰¿ ,ÇœíÐqõiîkÁÚAljHކT|!¸g™›IÆ¢'fä±$†>“~ÃNaï·_ ÕocÖ´ † «A3d=¹ÎÃŒÁÆ„ø‚Gù_¬X”1Ä=rý(Ýœ?èDSÅú3…d‹ 2JŒœ0+FQ‡Ã;v h?"Öˆ‚"lô¨¸ü*›„ðF2ŠX;Xê=*¥v™"«ÜÞçâ^ð‰›ûgÛ±Sq‰!l_>½ß~Á§¾ÆÏ0ƒÞe½“z•;dŽ;UFDäàÕ«WsÏ=÷d|ž8¢ø8ЉW‘N”|é„&K`AÕ¥6¾4ºB¼±ÅÇÁf…ƒÍ ¾f»êróD AQº‚{Ì›jÃj”Rv¬Ú Å§rΰ4~c ‡M¢É#°¥Iäö‹Ÿ]Æ;‹–°råJV¬XÁÏ~ö3tºD£O™]æh›Æjjj˜7o¾ÈÁ’LjuQQQÀår­êŠ?$œ0ð…n¿¢úIöu`›ª€×·øbQA l5¨¥’Ù±9™£É²LAQ1½òe|!ª€aå&¶éٓ䢆 (´ùUm÷c7¥×z‹¬ÉG½;BTH—bì¨á šp> ÕÛøË_þÂøñã>|xBŸò<›†B0þ|¶oßžS€ËÀƒ—]vÙç7ß|sÆ~…"€ß¼Û2Áb±$9¥FþuPl•(²é’Ú¬‰%«×óô®/“Æ5™LLŸ0š3šÐÉAª›ÃTè1uÁšôí iû|º¤N¹ƒ2Ù¢0ý¢_"Õ|É矮âÑGå±ÇK8ú^±<õÔS¼öÚk‘ms8œþù¡yóæåÿŸ"€Ç.°®1H’DCC^¯&õ›L& ØvLfL/CÊ GŽá;o! $…˜L¦˜KØnì¼Øq[’%‰<“D›_P”&¬+'cU¦¦-sŸ~½JùñU¿¥ºj7/¼ðÇgÞ¼y1'WEæÐμøÈYŸ#JÇçšk®1'ÑnŠï8È›:uê´éÓ§sèÐ!œNg줫Á`Àf³qØ—‡çóþL3œ1cÆÄÎÿóÍ7Ü}÷Ýlúz#h ”$‰Áƒ3}út€´GÄ: Qk`Qа®èïÂ`X`Lã­ëa“Ùz,ó6Qj—Ñ™Á-·ÜÂí·ßÎý÷ßOyy9—]v …­宜ÃÛòóó¹üòË)++ËSUu ðf–Gít•¦7mÚ´éô7fìøÍrïôìIee%ǧoß¾,Z´(fîíƒ[n¹%¶Š£Z@gàþûïgíÚµLœ8‘©S§b±X"~)ÎáSîH½Ççr–°Ä.³».̵×^ËÁƒyâ‰'¸õÖ[1 \|ñÅÜqÇÞ•úÙSAé ±ë}±øÝ‡NÉTξøíà ޹¤Ïÿ´¨Ä `7 gJŠÿ±X,)¯G?sçÎMHï(â–ZÅÁƒÅ…^˜ñÞøyF1hÐ 1sæLqë­·Š;žxW,Ùš²„@ žXë;kÓ'©†Uqã{­B‰Ì/¬¨ÂéSDm[Xìo ‰mÇ‚bÑvŸ¸g™S|´Ã'ž_sTL:ïrˆü’^bÌìŸ ½1óóÇ z”‰·¯µm!ÅåWD0^.„HŸ;¯ ÐYP \ |hõ’:v¼eñѸ¾TÂϸqãX¸paÂn5HÂÚaÊlÝB$I" ²oß>öíÛǺuë(*}—E/UðɔӘ1c3gÎŒ gaU‹?°`w}˜°J,"ȳ牜w¸w™ _Hk\¬‘À«Q¢—hñªÈ ì݃{ø3/[x÷Ÿ/ðÍǯd}†è{ÑŒ\xùo¸ä¼i²!(A;ò?sõ£ýˆr§B:";þ»$IL™2…gŸ}–ž={&ô“$íåzrÜRc0äøÑƒ?zªí›xõÍ÷°”R:`½FM§çÉÓ),ÈG`Ô)Ô¹Ul†v¤ötÈ1${ƒ‚™ƒŒ¬0¤Íºãƒ6¦Å’`öbèïïbçŸpøpf¼ÅËA§ŸËäݘÐ.ËrЇÿ!€h¦ƒn­8f46lÁp{0¥'(Ð˰éHú Á¹‚ÑZ”Öú£ÔØÆñ­Ÿp´¬ŒÑ£G3hÜ,ІOç7{¦½ÿëáØÉÞtPj×QçVè_¤½Þ§Ÿ~𯯯ŒóŠçˆ£Fâ¡GçÓº$ô” ´ú<‡GÍ :K hA!§Ñ!aBÖ~þ%cν’3¯þk,‹ht8Úª>1ŸPH’D8¦¶¶–ÚÚZvìØcÉR ¶bÖq srÿ­ IDATæÌáœsΡ¨¨(á¾lic@ÓÜ*ý‹àí·ßæÕW_©ÈÙÒØöéÓ‡þóŸ Ö‡·ö9cGÒ"}ôBˆaÝ÷:2p킊JŽM.»Ý.zxa’ðõÜ—ñÑ—{³ ?¹TIÕG¯×‹ââb1hÐ qÑE‰W_}U466 !´j$/môd&?Üá‹wúÄþýû³V+‰¿VVV&¾þúëØ8w/mõ®pô«¢ªªPåu!DW³»u ØÛЂ;…^½z‰™3gfìÓ»wo±k×®„úƯxó³=9€ÉdsæÌÅÅÅi5”Î|ôz½ÈÏÏ}ûö\pøË“/ˆïWg$€(‘üð‡?²,çDŒ½zõ›7oNç™ÏÝâÛ¥sEY-„è¶£a]=pŠÁ`x¸gÏž-¤[Ñy1pÔDqÛm·‰U«V‰ºº:ár¹Ä¿þõ/a4S®½^/~üã'<ôâ>ñâŠÝ9s€•+WŠ·ÞzKuФšOüG§Ó ›Í&l¥böìÙâùçŸ Ip 1$fýâ.‘———Óo9RTUU%³h»O,ýÎבv !¢ZØÿþüç?ç×ÔÔ<]WW'vìØ!Ö­['Ö®]+¶lÙ"jjjĦªñÇ¥µÂï÷'èöŠ¢ˆ•+W ƒÁv5Ä¿5U~ñäâÜ `ÕªUB!¾øâ 1dÈ.¯þè'1Ȳ,,‹(**³fÍÏ>û¬¨¯¯×·øc‘_Þ?íýñß/¹ä’Øö©¢Ù£ˆ£­a±§>$ÞÜâ ׸ÄòÝ~±h»Oük“Güý —û¾e­wvOÈpûí·ûˆ„(—––&%JRZÄAoRx”,ËÌœ9“Gy„olWu¢ÂÓédñâÅÌ›7Ь™JÌt„è<&NœÈçŸÎõ×_Ï;3”³¸³ãÅß«ª*>ŸŸÏǪU«øì³Ï¸õÖ[™4i{öî¥íxuÊû£ßež3¯z˜“.ø) 7ðÛ’„_½,QӦпH‡Í(QdÑa3laU1ÞŸóìÿƒ°fͽb~ºŽ .Eܳ4e‰Ô'èÓo@Òê2 bîܹ±~»êBâÞ·vvj èo½õ–(*©Èº²Oø“اMž)>X»SünQ‹Øu<$Z¼Š„“ßa0¬Š›Þo/±WžïñîÂá 2œ6mš¼iÓÅeI%Ë2³Ï» éz(J0šä™r7%¥Ú|*“gÿ§>ÚÆÙ?ýf‹fÊè ÈR¨xQ2dï½÷ë×|Ìœ)é(Ð#Iš£Ê˜"-¾A§å4np«Ç*B¤\éœh@ˆÒÆ9[rHWRœZ  Ûà £¸`ŽááÿÚìeu@; ¨ªíæZ §\|7s~z=+ßx‚ï>×í̇—2õB0jÔ(n½õV.½ôR q‰%ËótÔ¹†–¦GC…C昳ÝA!‚^@ZY™‚î H¨“%t .VÍ®®Æìë·ìHºO’$ZU;¿_vEÂ)ßLpöPçL³c1J˜ã\»ÇÚ^üÊËu³úpݬ…þö^ýu^yåÖ¯_EQR¦¶Ïøâd‹¨ßßfw0|ÂÙ<|÷õLš4)åû)Ï“9ÖFQô ¿?^™UåHS€Ñ2qõz¡••ùßÀ‚ ¤óy‡Ñ¤×%¹Ž:S®pás¸DÏÇÛjùô““Æ5L3œ«&Xcçè¯}†”êٛüJ캔é\:º„M&W\qW\q ,^¼˜O–¯äã5ë :µ¼?ªªÆOª½®)ƒræ™g2{ölúšÂ»“''VS…pX;ê®ÙÍ’å_³ù_{©Ú·£55455ár¹4‡^%¯KqoVMÉøñ˜8ñ **Êû†C¡!tC¢¨"€ÚžèÞßêëYf‹Nh•ÃŒùF‰ž6v³žcN‰¹§Z¨,Ð%dƒA.¼ð&¡vVe¥6«• ÏAÏ8¿¼Í(“¥îRV°%5õí’’’1ÜòA¿ P]õÕÕÕ;vŒææf¼^/Š¢ ë |}ÜÀe“+éÕ«ƒ椓NÂhluT# ­UU%àv:Yµr9~øËW®¤©¹%û¤ëëaÿvµŠ'y$™q§OO;}±¯Ã×TäÆSÀ‰€é׌+¼á†|••ì®®.—KB«^VVÆÀqûãØaÍCÕYõz\.7ÝtË–-KYέ´´”9sæ$ü˜Í(î¡-T–¦háaªÉÎäÉ“™·}ääʳíä¥ 4µ›dT%Lmc+{¶~ÍK/½Ä›o½M0Üu*ÖޕʦëÙ´qýtSÐ;Co{ íQ4Ó|§ «Ð­€ÁuO>ùdèüÒu~µ°ˆYgÍä‡?ü!Æ ãæ›ofÍš5@²$nµZ¹êª«Ðë§f1IœÀ»‹A¾EKùV–á A¡U¦Õ›þ?D JyÔ” ( .§“†o>༞Œ¥·B63]{²=BéAØù Â÷s,%wQÐg µ›3'$ì8ø”v½6­C(›žª}Ò¤I"•]á¯îSfÍé² /åÒ¶ ¡ùÖTù3öyþKØt8y§Ó)–-þ@L:}œr°&êôa0…ÑhŒù :ñQcï_Ò ŽG(šÞ—:ˊЪXML2¬üŽTOÙ#AK´øÌ3Ϥ”˜­F‰pQAÙ  —ñ9?-…سk' ÿò¯þëÍ$^,"Q>6G!«£5G^HÖ"t%ŒÏÕBÐÕ€ÏÝBØçÁïiÃïódšF{¶¡H„Ü¿Åu¬7=ÜMãä£×) ³0 87År‚x‚è¸ï—õêË“O>ɨQ£RÞk3j¥bOòÍõîÌX%·ŠXjOœVã jõkÚZ|*5m*Í-­l^õË_ù3Í Éš™Å^@QiO†:‰ñSÎâÔÓÆÓ¯wV£ÄÑV•ªÆ0Wžn%Àðû¼lÞ´‰Õ«VñÉòåìØµ‡¶VM`L³=Dòªt_‚[g¤GÿÛi¬Îª4u–,´g©ì¶ˆ Y–yú4Î=÷Ü´}´¢Ò]çž Š'()p¸Eá«ÃÁ”Èõ­>W@pÃ{¡„˜¿h毋ŒÃ,ÑàÒð!V¿þ0ïüó%”Ó3[l÷=‰y¿ºœ+~ñ Š‹ò“æ•gRØx8˜ýÄl±2iÊ™Lšr&wÞ}7O>ý,?þ µÕ»’¸fDˆ@@Ày!’a9c¯®fó?2ž%ë,´ -©ýX÷ªª¬[ö6Ï??™«®º*e»IÊ9"èƒ>¾‘Ý È5é5É\/C«Oeçñp ©%v9†\›Iã4ÏoðòçóÓd”Ü w?·Š'ÿ‰«?Õ^F|dOßþühîåøF^Å­?é“vœ²<™F·šöÔ’NoàÆ¯c§þ4޾'Ÿ¬Z‰4Ð[6cÎû<ò¡óP¼‡FñéKO˜‚~×ßp#5¡"FN:O Ѩtô°—?7pr…™£Ì «7jhõ©üeµ›+NOS‘-+˜/”>{¨ª(|½úC>|üNŽÒêÄ"IŒŸ0‰ûÿ çœ5•ß}èÄH­-€fïwX4"]‰ZY’4l?ûó¨·]ËŠ5kS!_[²±kñm´Øžb¨n>Àóh©Ê:%µ–÷CÆfìÓ³ï ñÖçÅúê€ØZU !q¬-,Ö}»O =ã¼ÖU‹ízØÒÁ=‰áX1‡Bâ­¾"õë“B—Åys.»÷îõh•Kìo eü­§?w‹m5éÏ#!Ä+_yÄâë/׉ÃwÔ,"š€ÞƒµôWpñBÌf3”––"9z²+Øùç¶ç š|úô©ìÍ}÷݇ߟX€4óþûïs×]wQZZ»nޤ{˼Á,R¾EK Ê_…"kâ10UQXôÎÌ¿ónŽ«MÚƒ§NŸÅ_þ#ýúöJ§Ô.Ó%Џ,OÇ¡–ÌÖÜ ‡Ìî}ZŸ9^ĺµkyù_o!@ ô¶°=NÓúΧT?B !–¥£Ü#-añàrgʶßþö·) C‡C<÷Üs }<(†Lȼüî'WÓ?¾t‹-G2³ÜwøÄ’íñx+–~(†ôï›’k =éd±fí—)ÇÙx( ^Ü9Šxo}H<²Æ•±O£[ó·×,_ú‘:~ìQTTÔˆlþKïÓº‚¿uÓÔÔ¤§5?fªtÏ=÷ðÎ;ïĪˆŠÈŠòûý¬_¿>I#Ðç¾’•dI!š9ø`³¶â¶nþŠ;æßÉÞêCI,£5ŸnšÇ´)RŽSb—©ÏÂÊ#ÕBT‘¨’Æ«¦žH–ò6zñmÊXéä˦Gíñ§«íÙu»vSWdñ&€ââbUá…ÔÉœ-­T*(((àœsÎáùçŸO¸ …8p 9Nºä![ü`¶Ä‘ %¶ØrDåø±£Üs÷]lÞº#EQH™S/âÒK~”p¯‰ÙÆë]šÝ¡#R;"ø†÷œíö†8»CôZ±M¦Ô.3 X‡ÝX‚uÚ4,𥰋ýoR—Œ$'LGŽQ*++ÓÚ+Íz‰@X¤MÂØ¯_¿¤kB<žä!õ9ʶÞ,Úo¾E¢¦-óû*´È4´zxtá_XüÉÊØ¼â¡¸×úœþÞúN‡'àNP[- {‘a¾© Qh‘cv‡~ñˆ6H¼üµ‹F™ÓV2­ÚyEJÈ0¦ªê°d(¥‹écO˜ü~¿ªªª;>Í{<èd AL)~mïÞdk¥$Iäå% ³ú“S§Ú|¡èJSió Ž´*|¶?vUºýaªÖ/eÙSëæ™¤Ì¤™çS9r2ãûbÈ"5>Õ_V»™5ÄÄ€âô¯»§CK3¨GÚ.T8tÔ:ŸM’¤F£±7]ÌrÂàt:UÀ›n…C{!ÉŽAMMM,]º4©¿ÑhdРAɓ͑hVxäÓDK AG AFVˆ¢Ö©b3j‰!zh+ÑfÒØnÛñjfÜø ÁP8¥«ÿ€Á\}Ù¾‘õ”çéÒ…M¨w« (N?çrGæLâ ÕØz,½EËöV¦¾#;œ0¸\.!ËrFt´–p~\jƒ@Xpí óRžšÕLH½NçÙõžkº2&ZŽ£Nâû#Í1„ÛŒR‚üT·}ääÒ1©s-ø}>žüûcÔÖ䎬$&NšÂŒégrx“ŸFš‘Jì푽é ,Ofo–z=r*€ªªý6mÚd7n\§sÈ(ØÏ:ë¬3ç\tñ”¢âRZÛœ„ÞlÅšWD~Y%ކàÌÉK_i5s¢+rí‹óÙþñÛ©upñ.¢¤À¨í‘&‰¦Zß½¥Ë)K¢"DƽԨӸ€'¨&%}BðÝÖÍ<òäßSÚ„8ò‹™8q"£ŽÖÜN oËP›¢UÅ2ã0ËHhiïòµ”¶ÑÉ;v¬•.”“í*¡þ¾¢¨e~°¨‡$ªª=¤,ëÐŒ˜Í¬6;ªÁƈ#ùþßcʈ“xü‘?±wõÇ(á`’AÅh4ò«+~ÊY#e‡Zd 9nþPz¡3 ùf­˜TǤ>Ÿ—?þá~)¢s=iÄp&Mžä–7¨‡]sød‚b«ŒÓ§¦¬JÑL£ùq9eYæóù ø/À`àa`6`L´æ©ŠB8ÄïuÓÚ¬eÃj8´‹mVaµZ9zô(J$ÂStðl 4ˆÛo¿=õdsT :í ‰Ý”¾TŒgݪª²å‹µ¼·deÊ{„ É 6‚Ñ#†‘ŠbYX·&dÞßu²DHI™LÛIE¤ªHô,Aä½´X,¥hžÚNAg  ¸ø~ܵŒná(rE‰¥F‹oƒö=Öd±ñ /¤Ôt9‚¢éaíªë¥*' yxáŸÑœz©Ý­yyœ2fLì{. #lFY’2zÊ"š@&èéhO5 ¶—N…‚E¡³0ˆ†ëFŸqY¦z‰©ÚÌ ?»çy&LHmQƒÜ-V£„Ó/¨HïÎO2 !ؽm‹—¯Í8ïÞ••œ|òɱïÑàÐl[N4kHFˆÕÒô|oPਠƢš6•Ýu!ÞØ¢¹¸ªð‘Z|êE?}åèç¯ý¼wúš5) ³à Òº-"H§Ó1÷çW3xÂùûåZ¤J#€,¦^‹Lus;ë‡Ã<÷ìßQɜƥ¢¢¹*GãÚNç`úô) }zåËkk/:ùRNWB' Juå-W—£Õ¾ í”jZBPT\€1Ó¹÷ÆË=z4W_}5Ë—/OÉj÷îÝËÝ÷=À ·ÝC˜;¨rà€Ÿš¶ÜŽwª„=*m~ÍÔ[lÕc7I ¬×j”øÝGNî9;€³‘û·d®Ä’€È GÁ³A.OÅfËãìï]€©ƒRPáÐQ•¨zª€,Ër%°!‡ŸˆAW—Y3ðð0zĈΘ1ã6—Ë¥B`·Û©¨¨ ï€A y*[Vï R>ÌÄ à†G¡Üw«þýBÒ õûýüý…W0Ÿqùyš9×n” )e…T0cˆ‰j“ÄGeN«[`Ö4¯W-' f?²• ‚»JËJ™{Ùܤ뙵ûHIÐét…zI’r>,z¢¦àðÕOû¢¨Èª»Þ"/Êj냂F v‘0ꃴzU¶×F “ÄzгžÏ–'—m u­`îùíïõö¦fò©|±òô•ÄUUeôèÑô©(ek}vdå[$Z½*«W­²«¬’$ÅJÀtŒ PE{¼B:m%¬h9„3i3jdA FÆOœÁ¨¡ý“úTä騋ȉœi˜,Ë&:qZø„AE©íÔ^W¾E—g‹cµQ“f“G察¹¹r|b(öè7^¢OŸ>I¾ŸÏÇÚµk™;·¬V+×]w#Ÿñý‹ /RUUŠŠŠ¸öÚk9eÌ(Þ\äLxA© 0b Xÿe…¸$™‘£Fó“¹—’Ÿï   ‡ÃÍfE’u<õ…ySóÐÉéËÜ´ÃG¿"#+4=?ÊýD$锪ªì¯÷³ñ€› GÙ˜ræô”㘠v“D“G¥ÄÞ¾?H’4MCËxž¬ÛAUÕÞBˆíéâÙ<UÜòAkʶË/¿<)¦O’$1cÆŒ”ý¿;O¬u§û©ÜþQ›pú2Gþ¾¿Í'–mkf]ö8CƒÑ"n»ë÷iǺg™SÔ¥#‡%ßùÄÛ}û´xqÇâô‰µ¢ðÌçnñíÑö¸ÆèZ¿ß?¤3¸;¡$QQðz½a!DZýÓ¤‡@85‹:49ç¡Zª¸T`3ʸs($™gÊÍppÏüJv#“Åj‹U OÅV‰fOæß+±eÎ7kTÙr+•;dj] !E;ÊVÓª¨{ëÃ,¯RNÎxcè–-Àf³…·È+H/C@Ñ JÆCmmr$“$IX,©¸¼+ˆ8̲f H>Žƒ³ÌÞHýâTÄ£‘‚‚¢´íÅ6™Æ,^AÍœ^*šÖSh‘ùúpk$M¾¦ µ[ÝA³W³ .ÛˆÄ"ÙM2¡°:öêgk–ýãš^9å è@ÓnÒ¦‹ƒö:‚ñI›¼^/K–,Iž”^OÿþÉÂä^CÈa–hËù+Qs¨:ëX’¬Ã`2¤mïè „ã¦â š<*u.•·¿õÅmóBhQKAÖì Ò;_‡Í¤iA%6™~ERL+rìðs׬˜ãLPUUì*?þGNOÕM „P$IJË ®’hda«ªÊc=Æ¡C‡’Ô/³ÙœÖ)dÐi™Çü!‘p¢¶#äEJÎf‚|³L}mMÆ>Q@›_°óx(Á9EdM›‚Ó¯jÑ¿‘ß"ϵç%dI«„Íþi7É1E4dîã]~ |dúT€AEÐâP©,Ë'>ÜLަ»…êêê”òòòŒÀ¬—ðE΃A-Z+™Ú‘ýrÞyç¥+ZH*8ÌrJ‡?Ô¾ò\~AkKæBñ÷}q €®*˜`T*Ë“`’ÔCǺýA®›¬ÙñÓU;ܪùòfˆX*ËÓñõ‘Ìø3ê$ ¬š‡1šC0²O—$Ɇvv3+t ”——«dqBD9À±cÇx÷Ýw¹å–[PU5É,É2³fÍ¢OŸôGªm&M´5{G¯'(8Цɫr¨EIX­z9º2µ•'¹ÑÈBafÁ¯§ØR¶»*K¾ d{\@&(±Ë4{Òç ˆBÏüÄ0qUUUI’dI’z¢šÎ ÝBƒV_™QçËñÆV¾Ûµ—]»wóáâ¥l_û>jŠdQ䛬Æü`Õá^Ôׇcûfe¡Ž¼8$/Ùåçä ú¦©â Ô´)ì­3$CV ©¸s:úÜì«Êœv§Øªå Ê”]¬Ä.ómMfC^ÖBÕãÙ{*¨pÈl>Ò,Gg(Š2H±Z’¤¬l¤[à¦7êŠìy¦!a!ã‰ìͲ¯‰-‹ÿζ5ïÒP“=–×jµrÓÍ7<ý§\;)5›B±UΪ 8r,¶ zb<…ýU{¨mtRÑ#u¨Q±M[¹Ù Ñ“ë”æÉÔe#€<µÎäTÍ:îdÀø“;@·‚D³õŠñ¶mwϲóÄEÎq`Úñ"k^_˜ùñcqq1·ß~;>p?°fÏvSv°Ej d«,îz6Ø·o+W¤…Ül%6]Ö$U Ív¢4OËxꘜÆ9eïxâÜÁÁA%†f»©ýHÔŠ+bB^^¶4m®¢¶ìáßÖˆ’ÍFQž§ã¸33§ÐËÚ9ÃŽ£b¼×ëMŸ'~Œ\:eI’D8öÇï§Ñ€ŽŽB^ôoÏž=™3g¿øÅ/?~|ì>k„2EôÚ9Z#æàü ^áS"ž¹¥‡WY·v .ù„‹.8'©µ‡UfW]vG\‰MÛßãcû;BYžÌçÕ©‰DAÀB«ÌÎÚN¿˜½AØU¯œü;Û\ºËˆN§óÇ‚.ºè"6mÚD Hx±ƒ búôéÌž=›óÏ??!Á2hɦ=Yìà¹ZóÌ2.¿ ¤ßGO7£ ÁSÐ9t×^y™)ÇSR\ÐVœCˆ8´‹?ê·¿¸#šÎq§Ââ~M \A—ËËÆ%/Óâô2âœ+päp¨Y¡²P3,Ù ›I–úèJ¯~v“á×d>.Ömø#çÔTY–åhr‡>ú§ÓIqÏ~Xzæ†MäŒ3ÎÀfK-èE‹Cd‚\ ßœÝ!Ô·²7=ûæ`uN‰5•åË–ðç_â®ÛoNh‰žò‡¢6 ™­†‡Zö7†Y]ˆµÉË`»Z šI¹Â¡}w?Àÿzœ/Þz0pÝœÑ {>_ ò›‰±÷Ýsó/3VüãšÌOÓm‡Cz½>¦Š‘jy.‰IDAT8nºé&fÏžÛí&`*acs gM·gÇjðfãFw–,  J6À¨—2q«ɹJˆ×ëâÑÇŸ ÁØ—“'ÎÖŒQD‡¸c‰3¦Âæ™å„P´ ‡Œ^Ös¸Eá’S,1ÛEªh§¿~æfTOƒKô,ùà=þúØã¬ùl-ª€^}g·Sá©í*áħ¢0ȸ'uèõú$•C§ÓÅbèµ)|VŸÝAeÍX ŒTÏd(q˜D4î@¢qið”‹YóÆ#„:‘‰´¹ö ï?³€ÁÌž~fÌ<üÜ/?mΘ àPK˜ª†0½3¨‹ ™„¿«ªæù‡žá­·ÿÍ¡#G‰SOϽ÷ÞËÌiS0[dœ?œèh&·µµ™Éb¡í6B„2úr¨¹€‘ð¶* †§xk¡'â ió«l>¢9p¤(›:a"«¯¸r0c'LaÃúu9=k”SÞ·¿ýá· (z”sÏž´[ú2å(µëhpg>M$…­Ë^`ñ;¯±ï»o†B ÉüèÇ—qÏ]ó5²ýpJyžŽZg{±êȘF£ÑŽ–Ý5-t§ Èè Œ$‰HycüÊô«´øŸî Ä„ŸŽæ`w@Váï_zq˜‘uÐØL} u|s4¤•žIÃfþô¹i>›¾\‡Böm ^³Ù¹c+×þúæß}W]ñ³¤,â©Àb0èµãkù–ä9}ðÞ»¼ðâ‹|±á+š›´0ÿ¼¼Bn›'¿úå/(+Mt$T8djZÃjÿ¢ÄÃs‹¥7p$Ó\ºB¡PÐh4†ƒa¡oGT»ä axq£7ɶí®SE…  %n5™ «Ö(ñ·õf3g¬¸uÌ©°áP0«ƒ¦À*£ ÏÜ‹/äµ·å$ ÄÁÁê}ÜqëÍlÜð%çüìVü¦Œ‘ò@»S(ߢÍM yû­7yý7øvë6jjŽÅÂÇ<…‡zˆ™ÓÏÄbi·ïDçPá©s 9îz³$ImápØ$„"iíRB·ÀmK¼§á K’¤ïèî:†•ê)´&"3ÞuºõXˆ/¹ä”Ì!ÝvSöÐ0‡I[eÙ À,sØoáž°ôã49="€––f^{ù>ýt-'^ÄŒ?\Gï^åÑ®ÑT.1èá {×±$R¬êhM õuuq‰)$N:ë þõØíõ§Œ²SQF«V§(J£ªª-Þ *o8ä7OíåÙÖ£Gð¾}ûÔ`0(FŒ΄|èFøõ8ë×ýÊõÍfƒœö˜òÕAN*Óg\‘Ö,›1ÈfÔâë² ‹‰mµ*GŸÄßžyš¹?ûŠš%#w¢í’$iéíª¾ãÈ‘ÃL]÷cÇÆ™gžÉI' •‹‹Šðûý?~,¼}붆¥ŸmÒسÝèwµàõz-aEI4ˆÈƆü•w÷;ã˯Ø÷Ÿ2‚€$I,X°@ÜÿýBA¤ö2DT¿…¤LjòߟÏ×_Q”=éÊÈ !ÄýŸ8ű¶Ì‘³5­añÀ'©3‹ÆÃâ>±xgæ[!´¼À-ÞÌÑÁ‡›CÊVh¿éq»ÄÃü}¬ÜK¶²7ñŸ}Ã’$µI’TÔÇÐ×¶¡Eì¤Gíoaì9”î•ÑRB·ý€Éd I’”1Ý’AŒ‚՘ݚŽÜ™r H`·y&§_P`IdÙñÿX$¹-rRØj³ï½òªkj:h}úÙÇGœI9‚íÜ"úNá@;VŸdÓ!LŽ[ð5|‘šsÿaè6$)ž).0›*„ƒ¤ýSAžI¦*h㈠UŽC®ÓªMõîÐÎ>…º=’$B¡P­¢UQ”Ö`0èv:¾æ6kñ‚ þ¿òÎß·i ŠãŸóbL¨Ü11S˜˜Ø?ÄÆÀD2ððc`ƒ  3B]ØZu@B*Tj“&m\Ù±cÇ÷’š %´–@â;Ýp:î=½{w÷¾ß«W«U9íÏsažYßåÚN£T þã´lèiúŒŒe$8'’¸Ïˆ»LG!,e†˜þÄ`C7Õ…AE2„÷ji^´‹¾À†Rꛈ|AK§ôMà}–emÛ¶w•R{­V+ò}¿7œ\µ6óöC[/×®Lz¥Ù¨Õj¬6‰€7 Ÿ’œÛ{wtQÒ NatÏV(3Árž`zL¼Õ‚ÎT…œe¢4‚@{ž—î+†Ž ·Ç,E/Tkݶ•Rk"RWJ­k­›†a4<‡³_Û½ n¯S©Tb 5 c\¼W&$>¯oœ?Ê¢ÊvÂpÑái¨¹Ù͸%pQËXãÿ’”qÐI†äAkÛ}Î̉—„€,úc}¿²PšÌ‹ˆÏóü®išKyž¶D¤)"mÛ¶wÂ0 ^¬$Võƒ{W»üÍŒõð0cÎáLœr9.‰°$pN4ùßÜíªM”µ‚2—™{GØXgpG_Â?hGCiðŸbtý Àc ¤6d¸ÄßùY£ÿÏ9ýWòGÂÓã˜IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_rectangles3_32x32.png0000644000175000017500000000122613561570220021501 0ustar otfriedotfried‰PNG  IHDR szzôbKGDÿÿÿ ½§“KIDATX…íÖKHQÇñÏ”…dPD;…À„H¬ŒÈŒPp!H›–mÚå& \äªÇ&¢UMTö E "ÜP+#‚ÚáªVö€ÓâL¥v¯^¹Dþà0Ãüÿs~ßùÏ™ÿµ¨ÿ]Kg‰ïÆ!¼Ã›…ÇùSWÒñ §P‹%Ã|Þ¦mèÂÇæ ΣÅ КÕOº¶ûq9… éñ¢d®&É ± hÁZ|Í_ŠmiN Öá3zpÝxâyY–û÷&|Ée¾D,ó¥ÙŸáW~-:ñB¬Ìwô~à] d+fšpG:ISž“• 'ñ|ô§áíÛ!ôõ…PR’ÀŒ›%)}e,ÂØX!„PZ: (Ç4á.> PÌ7P_OQããSâEØ„fxÌúëlØÎÀ’R¸††rÇ­9ʹB}ÛÈlåI rÒH˜þ ªªhn&“¡»»PoÄ>±Ç†§Ç§¶ÔÊJŽ£± PÕ2{FW¶àÔ ]kÄŸ–;˜èøiXWB{{ÕÕ 0Y+С³3¶Þ#GfÈÖŠ чq‘6ééab‚þþy¶˜E޹¬ù®ÜÃD–빋úWô©ö˜n÷_IEND®B`‚ipe-7.2.13/src/ipe/icons/copy.png0000644000175000017500000000202313561570220016370 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<qPLTE‹ŒŽ‰ˆŠ…ÿÿÿ‘ŠŒ†ððïþþþ‘’Žïïîééèèèçööö‘ÊÊÊÉÉÉ—™•ŒŽ‰ŒŽ‰ŒŽŠŠŒŽ‰Š‰‹†ÅÆÅ‰‹†ŠŒ‡ÊÊÉÅÅÃïïîîîîîîíææåÉÉÈÈÈÈÈÈÇÃÉ‹†ííììììììëäåäÇÇÇÇÇÆÆÆÅÁÁÁýýýëëëëëêêêêããâúúúêêééééââወ÷÷÷ééèèèèòòòóóóñññðððíí퉋†ˆŠ…ˆŠ…ˆŠ…‡‹…”ˆŒ†Š†Š„ˆŠ…†Š„ÿÿÿþþþððïïïîÇÇÆÆÆÅîîîîîíííìíííÅÅÅÅÅÄÈÈÇôôôììëëëëïïïòòòüüüÄÄÄÄÄÃÃÃÃÍÍÍÜÜÜùùùëëêêêêêêéììì÷÷÷ðððñññ½¾»ýýýˆŠ…úúú†Š„ÏÏϺ»¹éééóó󉇴µ´ööö†Š…‰‹†‡Š„9.«¹LtRNSW~~~~€ƒƒƒ‚€Úþýýýü´þƒýýƒƒƒ~ƒƒƒƒüƒüƒÌd’a®ýà ɊÑ>bKGD Lò pHYs  ÒÝ~ü8IDATÓ]iW‚@FÇ´U‹Š²R3Û4Û¥2Û4ÛŒtÀB¡Í$qŠÒVûõÍ §ûí½çžçà l-VlÀÀî°ÒÚÐmŽv“ŽÎºË‰qu÷X4EQ½}ý4M Òn=dÔÎa6eÂÒF=âa/LRn£vy-š«kÊçÅõ¥A:S×þ±À8®9yA×þ‰É©éFÎf¯HtB3áÙú6Ž ºÍÍ/,âú·8†‚HôRx9¬í äù\^’¥¬W#ÌZtÝËrxõöîþ¡Pc ¸ÁD7·p sù¢òT’IVcÀ¾½OÄw½,_Ê®,!='m°ïy!q©œÑG&_õ ½U*Uí°©Uå"ô!~V¾´#ÐÔ²ŒÊHT¿ªÚqÓ‚“ZM_ý==;Çç‡O^®«H‹%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_marks_32x32.png0000644000175000017500000000070213561570220020402 0ustar otfriedotfried‰PNG  IHDR szzôbKGDÿÿÿ ½§“wIDATX…íÕÏKUAÆñ‘ÝĆP@;Û‰"(­Ã‹+.TB 7ý!®\E%â…›v­.‰´hA‹ ‚RIElqÏ•#wf./n:_gÞyçyæÌÌy))ùßéJÄæ0‰­b;ÐßÇÆ/¬a·¨¹×8‹´ñ}ø„¯XÆޱ¹^Ô]€ET0ˆý¬o¯ð?BI×:h` orâ°ŽŒÄ’:ià7óßÀÑUx§¸›½wá%Nð1–ÔÉ3°ŒQ|F·Ñ·å©k8‰{‘ØñUh\ßØÉž%%…éÁÞa³âW·Õ@þTQñ^ìi­›‘ñUüE-'¾£QŒ*E ÌÄ›í~$g:31›("+ ÏyqªQÛŠ§~Å¿ ÄzðßpÚH1.¼úýlòxþ³7·ãÑeL<ßœøwLDÆNiÝó¾HÂT-hr C«©ã01¶¢µô†úJJJÎùŽl^ô8åîIEND®B`‚ipe-7.2.13/src/ipe/icons/cut_32x32@2x.png0000644000175000017500000001316413561570220017434 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð¤IDATxÚå›{t^Õuàçœ{¿·ôéaKòS~66°ÁÓÎÊ “LÓ)ÉÔ”òp›GÇqƒ.ÍìØ8f h˜) ¤Ã°š™¤kÚ$%6~IŒmÀ6–_Â’,KÖë{ÞÇÙóÇ'©’lcãíêYk/}ëÞs÷ÙûwöÙçq¯à_yQç«`Õ“ßZ¤­³|ù£¯\ ƒ×¯_oÚŸF¶>øà#;ÎWŸ>OçoU¢_¥^^õä·] ÷Ý ò¬(õÖš5ßšü‰0Ê]QWWŒ;.t´û\CCƒs1_»¶a„1fõÌ+g'eøÄ¬Zóøï[Ü2÷ºëçÍ7"2-–pÿôb°DWÇ¢Ñøu×Îáú9×»VäÞÕ«Ÿ{ɬ[×P¥•þþeÓ®°uu£(//gÖÌYZkýÄÊ•+G^ çW¯~ü:¹kÞ¼ù®1S§NeìØ±ViýÃuëÖÅ/)ßFÖÅb±òy7Ü }?Àó|f_} ±h4fYy¡ohhÐóB]]m8yÒd …žç³ð¦…Ž6¦¾æ»dÖ¬yâj„/Í¿q¾ë8ŠEß0ÆpÃõó\”º{ÕÚU×^H±dä^DfÞtãÇ÷ÂÐR,z$Iæ\7×Ѩû¿ýío¿$,Ü“NWø“&N¦Xô®‹S¦LedMMèÀs"rÞS,”ŸVjÍÌ+gꊊJŠÅ""‚ˆÏ™1}ÑHe». c̼ñãÆE¬µ„a8p= -¾°`þÇŠ\·úÉ•w^¡uWEû_±èa­ j3ÄZaüøñ.¢Î)žKÈ‹žh­Qjh'{žOuU5W\>£Íwži(?çW¯~|.JÝ}ã¼]­ žç D@©C4…b!D‘»$Â0\¿¿ñ›Íf‰DÜ!÷D„bÑgÊ8¦"^t=WçûßóuµuáÔ)ÓÈåòCˆÅ¢tuuÒÔÔ¤¬Ø×. €BÎÿ¾@Ó¶í[m$⢵0LDð<×u¹~Î ¨o¬\»òòs1¬/ñÍZpÓB§Xô† 7c Ñh„Í[¶Jëw‹¹àG—@CCƒgm°´ñ@£nim&‹ ©PdÆŒTVV‰#ê¹Ûƺu U µzÖÌYªªªŠB¡0t"£ñ@#Í-GÁ} ö’xèG¢´úåæÍ›|c4®ë1Î÷|?`á‚›]+á¢Õ«W~öãè÷wu4I\wí\r¹XÕàû~æ­·ß–h4Š1fÈíB¡H"gεs ¨?_»öñúRM¸÷Xk¯^´ð§P(àûþÐw]—X,Ê›6…@cezijçeÿùxøá‡;­Èûvï”îîN’ÉÒž¤¿·¬µd29®ºj6©T™œµ§ÓµråÊj£õšY3¯Ò••Ud2Ù“ê$“ >Ì‘¦Ã&°þ’%K–øŸ(€IõS^PZ¿¿i˦Àu#¸îе畦°›,rCþÇ5kVÞ|*=ŽËÑH4qýõדÍf±Ö ýX,†RŠ›6úZë?üÀc¿:_Û/€Ûo¿= B»¤©©É:tT*1ûïíÍP_?úñãCÑêùá'«¾³j¶¹÷¦ù \…&—Ë5RkÊÊ’ìxg¹\ÖjÂó>¹`V<¸b³ÖúÕ76oðA $Äþ†!¹\–… ~Ç(˜;÷ôßåˆú^mm]xÙe—ÓÝÝ3D·ˆJ%Éd³üú7o…ÖJÃý÷?zøŸ õ²L&¾³s©T­ÿIµˆÉdI¥’Ìšyµ1Ƭ^¹re5Àê'WÞiÅλyá"7›Í $¾~q]—D"ΦÍ-ȇ‰Xê© e3€9¥ò‹_ü¢çÖOÊ´¶¶,œ~Å Æ( CêXk™4i2»ßÝ¥C¤>}ëïnÒ?»rúÌÄŒé3Ô‰'NÒ[UUIKK3[·mU¡°øþe÷ï¹.XDœØ“"¶uËÖÍ6‘ˆ‰D†ÜÏçóˆXnœ7ßù*Úÿ®ÑN弿©îîž!ÃFDH&8ŽaÃ|­õOW<¸âï.¤½À²eËò6¥{÷íÑÍÍ-”—— g€®®n¦_1ƒ‘#FZ­œ/Ý4£µ!›Í©[J|e¼³óºº:ÁË.´óÀòå+^UJoÚ°ñu¿ü.AÍf¹å–O9¡ U"§³³ë$=étšb±Àö7·"vÕƒ>öÁ¿úÒq¢Ã¼¿ç}ÒétéÚ Þíé饶¦–˦]ÎÆ76 Éý‰/™LðÆæ7Ć¶Ý¨èš‹açEðÐCþ."Ïo޲тtzèÁµ–®®.,XH>Ÿgÿþ}C†IUU%­­-ìÝ»GÙÐ~õÈž‹Ÿ×ñ)½Ü[oo#•J´eÎd²¸ŽËÜ9sÙ·ï@”••êþjÃë¾6zÃòå+Îé¤ç°lYà ÃG»ã·¶»»‹ŠŠôû‚ÐÑq‚kfÏ!O°û½(¥¨¨¨`×®o?®}k¿v1¿¨&NœöJíݰñWa<'/%Äl>C¾eÉçóܼðfššŽàyE<Ïc˶-¾ˆ}ê‘Ùý/Àí·ß†ÖÿڡÇÌÁC‡¨ªªÀ†–B¡@ÑóèêêbÒÄ)Œ_Ï›oogó–M~/Öyüb;p%xºòËŸ¿~ðwoYpSsKó¤Ù³K/ŒÄ FŒvߤ‰Ùºm mmǰb—<´|Å[—ÀE€þ’úáËS3½=ìxg••8Ž!ù§c´žžÒéJf^9 ·µÙV½òÒÞKaÀE}Ÿðlýȯ:‡ë'ìØÉ6ÇåŠË§SSSK.—+½Þj:Lçö-lܼ‘¶ ÿHª·Ç‰lü~%uK:龨ö]÷w§+ÿ«‚ŠçH]¬¬læø©üßÏý[ÊÆŽcìØqtýÅ3dÞ~ïxÆ8TÆ’T¹1ÒÑ8;Ú?? ž¹/ÃÒ‹ à¢æ€Ûž6ÂÜkGOÒQm¨<ÑI—çq¼¥™Þß¼ ‡rmM=ÓÒ5ÔÄËHÇS$#1\”:žÏÌý\„×þGÛÅ´ñ‚g ZúvÈ¿PÎ\±Ü;­z´Š8.ÖZjZŽQÛÚ†ð{ß÷‹‚ê,朘rDˆ¸.¸.cÊ«iêí 3AñyAæ+€õς܅󵵿œ×xÊ|ø¥Ô Vd äC£l$îÆæN˜fô ÓâX,ÆûmMÒØÞÒŠ<¥•zlþ¨Éºèh­‰¸.Ç![̳½õ€8«#¾š­`¡‰¢µî@d»ˆ¼êÁßÞ]—ÀzHáÏ”RÉT<.åɤ‰».J)ŠA@O&CO.G*‘`Ú¸qŽuúy¶Ú#(î=ÚËKcÊÔ®êhrêuuL[w7®ëâ:QÇ὎f:{{eL¢ÒŽ9ÒD²…m'N„m'N P@äI§î€žëËÇðC˜g•ú±†ÚNMEŽ1'½ð‚€Í͈³¦L!¯BÞ<²ÏŠÈ³÷fø3ò|’[QüüêšñŒ+«ä艸ŽCÄu m(¾FL–#Ö‚(…L$‚q·¶²ÿÈ‘ÀZÛ."_X /€ÀÖ•ÅãR_[k\gX Qj@¡A+…ïøAðl†?Ë‹í==ÓŽ?.±X̤âq  ª¼œ²TJko_ðy(¾›ÎäÛ—Â?€ ÖÖUU©Š²¾3> ¹½];&aþUÆÜ_¼V-†o*á±ÖŽ1ÆŠ`´&‹…ÀôÓµ³rÖ‘ÏaØùÛc‡¥(–X4ŠáàÑ£¾…'ÃÒ;`Õð‡¾È?^|ïÀÙÓÔdQ ¯P`Tu5WNª€'~Ÿ>//B™VêÕòD‚étiã¢Mmm¶½»;Pð…ÅpÏíp|ðs~Z«¼¾q F]­Ô„joI'Ý‘¬l3e­€1ä ‚0t~:¸î—¡ãøS¿w¬£Ãß}èUÆPÌç™0jãjkÑJýh=T3€<¢”ª[ScúOjwuÑÕÛküûÅðãS=g (O”RØÒIж´ÐUFÄ:ZƒAôß:峋á'"ò™ã]]acK Z)¼b‘«.»LG'åÃ9'¯@½‚ecª«m yÏ£µ£C€o.†¿?ݳcܾÖ¿äIç™(èòà×ÝÙ¬Q}³Lß4è)XøQÝ / ÔÏß=xÐWŽCP(P?jñX,Xò±¬£”ºod:íZkÑÆÍçÉ‹Žˆ|}ø46 œÒJÝ52v žG$%›ÏZël=“÷l±Öšl¡PZT‹PNG´R´þ ³–ˆ|#›Ï;Ý}¯×m2uüxW)u÷÷Á=Õ3ú4FÌ‘šŠT ±Ç:zzD)õÖð›2âø¡ÈäÚª*ñh”ÖŽÑJ5Þ »úÚÔ”œ.ú˰_+µûÃcǬÖ Œ®®FDÆøðÅjûxO)µñpk«ÕZã{ãGBD*âpÍYažV*pŒ)­î”¢;› ùßêª>à rŒ@©ïÖTVÚÚtšñuup¬£#ÌŠ¼$û$5èwrøõ^‘›ÛÛÅöHÄ㌬¬¥žzê€(ék×ôùÑÿQÂkí]]Vkå¥#y_Á g @ÁäX$2(ƒ‡aèz¥tû ˆ–JˆÏSê:ÆÔN¯¯×Z)|57K(Òû ¼ $úMœ@H>kE:›š,Æàˆ0qôhåS1C©¿*/ÕÜ~¬O¢Yx/CG(ÍBJ)Ò©”(˜|Ö€¤ÖZ 0¦ªjàಊ}Î÷K ˆ¦ ¾žváß]=y²“t|²ùõx6Qªlí*ÙØ ¥E›ë8F•¢ë¬( ©.+Ckë8(¥¬.M'‘Áò¨}F©¿N(uçUS¦èš²2|¥ð¬e×þýAvçûÄ\—T$ÖâF£$+*xãí·mS[Û¾ÅÖ^3Ho?è“ý¨{BÏû2 ñ8Ž1ÄŒ¡<§"‘ Ù÷ù‹ß'Gg×þýaÖ÷üƒÈ—_‚½Ãì— Oú oÐoX`sàïÇÁœ[Zªcñ¸®®ªBâûD•"á8DŒA‹I$H¦Óì9p€=J—Èý4ëýS!Éð%øª§«Ói©¯«3©DÓ÷õ—EÏãxWGŽó=ß§GäùÕðÃ%Ç÷ôð^?]Ûr:©ó,­TêO"‘ˆº¬¾Þ_[K<-MyÆàº.=Ù,ïîßo=ªâº^´Ôóªàyâû~¥z}‘õ;á©§ y“ƒÀ©ÃþtEý=I¾5×ÂÒ˜R_‘òX$â%¥4³ù<ùB!¢µ>X{÷—>bÓvVú¬P/Ã<`‘‚Z@  açÏà—B[A†·§NÝÔÙAdè?†›\¸Ê”v¯Ó°á?ÁæÚ³|,çX†÷<œ9ü;/§ø=Òy—ÿŽã­R*®ëtEXtAuthorGarrett Le Sages@5XtEXtCopyrightCC0 Public Domain Dedication http://creativecommons.org/publicdomain/zero/1.0/Æã½ù%tEXtdate:create2016-01-21T14:13:02+01:00ý.%tEXtdate:modify2016-01-21T14:13:02+01:00ŒO¥’tEXtSoftwarewww.inkscape.org›î<tEXtTitleEdit Cut,7<IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_ink_32x32.png0000644000175000017500000000312213561570220020045 0ustar otfriedotfried‰PNG  IHDR D¤ŠÆgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<—PLTEc9m>j5 i<o=Àor>].o= ÓuƒH h8q9m;Èn¢Z i<U+k<¿ik;f3j<·ds@ €i:¯a„H g9h:£Z e8g:˜T e8i?g;N e8k;i;‚H j<UUh6|E l<b; j< vA o> m= g6s@ q?n>|iOp? p= o=€@€€€‹‰ƒ•Ž‚p>’ŒÊËÉ—”Œr?l9ŽŒ¯°®Š€k=‹‹…›œ˜—™•…z™™™€€€’“Ž•–“‰Ž‰‘ããã¡¢¡’“ŒŒ„III‘ŒÍÎÌ ¡ ‘ˆˆˆ555MMMnnnVVVŠ‹‰žŸ‘+++999DDDƒ€€€€))) ¸fÂkÇnÍq‘P Òt˜T ×wžW Ýz£Z j;á}©] o> å®`u@ â}³czC ¹fF °u5…I k<ëëëpN(èèè×××££¢ôôôÒÒÒ£££íííÚÚÚ¡¢¡âââééé^^^°°°\\\JJJ```MMMHHH;;;999000777555!!!µ¨»¤tRNSƒÔþª Íýê@ ÊüûžÅûÙÀùë¸øû¡¦ôÛ’ñé=yîôŠdëÌLèà<æìT/ä÷DàþÈ óýÛ¸þþä(qñü2,çåk×â6®ýþÛdôúÊ¿þòòò°Úú’ Á=¢ß;963.)$ ‚ÞbBA=8-("^kti\E&%# èîÝV pHYs  ÒÝ~üVIDAT8Ëc` 021ã•gaecÇ'ÏÁÉÅ̓Gž—_@¼°ÈQ^ÜòbâK%ñX %-³LVò ËW(â±@Iyå*UÜòjê«×hhâ–×Ò^»n½Ž.Ny=ý 7â”72Þ¼e«‰)Ny3ómÛwXXâ”·²^½s—­.y{ÇÝ{ö:1â4ÀÙeŸë~7wœòžòòÆ)ïã{øÈQ?ÿ\òAÇŽŸÁ‚¡a'Ã#"qJGEÇœŠ‹Ç%˜”œ’š†ÓúôŒÓgÎffec—ÍÉÍË?wþÂÅK…EÅ%¥eå¹9Ùʪò¼êšËW®^»^[WßÐØÔÜÒZÜVž[ ×ÞÞÑÙuãæ­Ûwº{zûú'4Nœ4¹¨³£=aÆ”©Ó¦Ï˜9kvËœ9sæÎ›_TÒÖ±`Jš3**s.ªÊ­Z´0gqusÀp«·_Œ§tEXtAuthorJakub Steineræû÷/tEXtCreation Time2005-11-23wf–Ä%tEXtdate:create2016-01-21T14:12:09+01:00×"ê%tEXtdate:modify2016-01-21T14:12:09+01:00aŠšVtEXtSoftwarewww.inkscape.org›î<tEXtSourcehttp://tango-project.orgïâ– tEXtTitleBrush Toolo-6vIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_translate.png0000644000175000017500000000126213561570220020423 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<¢PLTE J‡ '%# , +(I J‡rŸÏL|µSƒºYˆ¾b‘Ä0e 0tRNS  !-1% .:V[?0 +6^D9*(LM4. ™üYk pHYs  ÒÝ~üÏIDATÓuéC0F‚P¢Š.ºéªklïÿj½‰ÔtÐo&÷Ç™;_N¢(]Te,*SGi1–#h |€«à ËYÍú½°FÌ®Ÿ;ˆv9ÕÎñbJN˪n ž¦®Ê>Üþ×ÝšhZßÒ Þ¦nÙˆM@bŽ+_éN<¬#ΑïÐ`*ÿ$œE±iÖì„ÎË•øÁt½Ùî<Ž÷Ùa‚Ãñt¾\_”çQp ïìñÌêYí•üNœ8¹û¢ñÛlWeqµ/ûy±!aµý_%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/undo@2x.png0000644000175000017500000000433013561570220016740 0ustar otfriedotfried‰PNG  IHDR,,„ZgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ðÍIDATXÃåØ{lÇÀñïìÞíÝùÎ/À¤ØP‚yCA¢Ð€yÆ BA@iJ m ”´MQ?¢V¡H RªT‰”¦ì ¢’(mÒ6‚p0˜GCÄÆDZÁ/ æŒw¾Ç>¦œmÎgû|6XŠÚ‘F;Ú›ýìofvfþß“Ü"w  Uû¶»ÙØÉC¸ŠÐ]侯4¸ð #D˜"`ÊP@;Ó]éºSLu˜ââÄyÛ¦¸R²†$²w \TÀEÕN}ã=©™ë„‚Jï‹ Øàqü׌ RíÎ$a×A Ù|»3ð‰žw§OxmÚÒ}¬j ß$bHC<àIWXˆÍQKÁ°¬eß·Ói´ŸÄ •PC< >ûIz-ÿΜº6'sê‡îÿK¯A)-@ P¿àâF†àØÄomŸ>f­]÷}€4›ˆŒ*‘<´#"1ð©}Ü MZ¼3+%#WÑýG–ï6ºŽŠªØµ ÅùXŠJ=’bÓàPº›#Ó×¾Sp¿á8¾ŸÙš]ûpÚ¯ sx²…á/BÊHduÔRÖ Ø2@XV;Fûø›/ÐÜpÁ³ú3)„ü[Ð`{î&†\¼Ÿš+íàô¥¯§¨vFà? M`t`#YÊp×C˜zR¿ŽPÓP´ll®o"lc¹U{Ĭ){×oé¡‚cØ›‹q×ÀÅùüÜ6~÷Ôû_ñH«3XÒQ]R¸Ô‘DЖ^‹<´ü=o¤¦£%¯Bu. ¦ì¯Aoõ‰óAå¹›h¾#°”ˆÓÙ“’1ë§r^t[Ás˜z%  È0Ò"Ñ–RÇ •v I£^¥ìãßùÛ[f.ú•ñ<ý.üùï`,û>o¨7ʦÚ.eó°fN"ë=êjÉ+¹X¸=T]Zà»Y}Niom¨öqŠ;#O±%ÍÀÒ«‘VkO²êÆá¯¶6–´ïý;GãyÚ^®[‡9w=ë›ê>ýsÅ™Ý>ǰmØ\sz­+!v2æ¾G®;nÕœsõ|þSŸþeCCÅñ€cøoÐ’¿Óã£ý ž3T¡°º?KÂûa!ó7°¥µñ‹çÊ‹w´ÙSŒÝ}ÜknærN/GË1U'Ÿ¹xô)ö¹=Ж^ƒÝ™…i‰±RƦÞÀÏÏc—¿µvË¥cÛ}ª{ öäUý^“›‹1o{BAß#eEÏûT÷rm|4,?6Í#?ý)w 0ÿQþhk\_Zøt›Ð– ¥®O躅y¼g†}¿¯)Ýëw¤mìö›”AìšÓ Úpßu0À¼kZW^,üm‹%&ãö3xéSÉnoíÙVÉpÛÈ®óB8°ô°¢+´ `ÁFŠô@`IÙ±g½áPŠT»usïIìÀ’ðÝ,1TǴγ $¶¨ým†î,±h3%mmFNù‰Z>°Ê+Q¡++Ä~–Xœö·^ Û=„},zðB¡ª¿›& uU"_)ÙØ–=AuéU+§üÌ«WB¾›î+5=êØ£ë{›ðêáBDö<6×Únœ3L‹·ïÜ26ÛÛãÛñ¾õ‹MÓú¤±©´°™‚ ›Ý#¤å¡bó,ãZű`³—|ú™¶8PÑK9^æ¥üeU<ŽÑQŽn[Fg·Gý®+eXH¶7yíÉ?ð”ÛÙRRζ¨ö;±¢ã(cÁ½a•A>@lê†Ýÿ,÷§Ý3. «²^¸´U]x=XWïýõ;¹ÖÝh Õq®s±à¾@‰<€½`­ +–=NÝœšùõF(ÈõÊãÎ+U•«ÅûQ0cê,Ë膕8¸þ~ëë¢Ç¡µb1žm±5kBzŠæL yë½éÕWÚÞ^³•fT­8e (Þ0‰ŽŒä“kùÚò¥¬ÎÍ.‘ÍM¸JÊxçÉ]\HÚY–Ñ!ï 1ÐqÝk̘„ã'3yR6ÓÉŒ®¦[\;ô>'ß*¼ø°bÏeï–8áaÝ}ò“¿sb¯ey¯HÒ_-ܸÔl6w]Æû»KÀâÒ9·¾¶ø©»N€s®ôÖ·¾ ³3³¯úµ¡ÞKy!„\ï¬Õîä;{&`Ô:h­‘¦é®¼@wRÇ^,ñu#ÀÃÃ{ç:Œ1¯ Ýê+• J¥Ò0Ïk°¶;#À·5íÐëAÊXœs¯ÙÍî˜lÞh4î*àÛé7;wÁîß“oÌ¿ë!…wMÐPcáGwÎáÒ¥K·¸À‚bfìÛ·oOåÇÏ‹«xüÐû?½©BäðâëNÚß\úçßúŸ=pø=Ÿ:àIþW¥Z-7§¦™Ya<ì[û"tQ ¥z½¾c Ø+!D„<Ï÷T¾( h­Q®TðÀC‡7ß[cÃÕ«WÞÑët¿|èýO¾mñ_ûØ® 0Ä¿aéÁGßÊBÊt:}Y–!MS$I‚<Ïa­½cÐ7Ë`0¸A/„@E¸yÞ5Ö—ËeäyI„ÖôÌ y¦çæèø7º¤?øMÝO¯}—N|3om!IR0+$I²'@»Í³—òC ÈÐ_½ˆkמCûð[n„#€¹‚Å3§eá]¿ÿ©³OrcG|çÕâC³ûö)&c¯lùÛß@wù ´®ãÊòeôz=lô6^uòZ†¨Ýf¬A·ÛAž%X^ú¦…7ºn{n.œ=Xe~ÀŸìH@\? ˜Û7;¤nÔxg Ø"Ccæt¡ñì³G_¨×S^xáØðDµ’îUT&ænÈCÌhÏÏóòåKÇ;Ÿøs<óĦ¿Ü@€âggg}% ÑO¯û”ä~àc€þø6òÀ;ëæ܇å‹æî¯„:|îö?þ©}Þûw<´_J!`Ý]^ÃÞQÙóÏÿ;ê—NAZƒþÌ.?ú>di„Q„‰éißY[û-lG;ú¹€ÙíŸoË^jï¨o¤)ðãý«(ÅÔ™!½GïÊ1ǟ¿ÿìŸ"™œÇþûÉõ••Gî{ü÷Þ>žn „ø…C ÷q¨i·x£ñìYÚýË8üÈ›0uù2j€´ZÅ•ƒñÀêI›œÇTkµzC÷û½øð&‡Þÿä#Þû8rÚúïHópáG>=šÀ‘÷ˆNœÀjba“ÀýGÔ‹Ï?ÿGûƒý§ÿí„—ˆÊ¥bvª,­$°Ö¼¦Æ¼Ò:ˆ¿?9‹‡ŸüLퟅT Ý‹ñò}oÇâã?g rí1?7…/³Îþ$€?gðÀá©É: ¯ÑÙè£ÐîÆsGòÒ÷'ßòA”»ËÎ"y÷,,@¡h8-QiF¨Õk¾Ûé<Œc€€÷ÎC8ƒÑßÕoüÆÇÞùðÃoþucíìâù³]b¶Q¥`­Éö¡úÁú¾Å¥Å‹ö˜óÞû~¿OLL4ž}îè‰ïËÛ\][íLµ¦&—Î]úÚ׿væ§>úÓ?¼±±18úì7N¿û]ïydéüâ²³ÎßÿÂÜÓ_ú‹?òŽw¾IJ)¾ðôçO¾ï½=|îÜÙ«Þ;·°pdîé/~þøüð~¯”R<ýÅÏŸxï{{óVýçŸþã/]¼-•JôЃÎ@ B93Ó®}é™gŽó›Ï>—•‹?~ê/Ÿºa9#·# (ŠÂ:›¡’$¥N’´’¤UJ™Nw½µZ­’$qÂÌœfÃS)¤ö‚"˜œhÕI J)ǃ ¨×Qœ$}˜nMi–&DDRÊšÍf8ˆ“LLL†q§DDZÔëõ¨×FëÖÄdH6`6¥(òLl™Ø†Qïa¬19„ýð–è¾m´K’"—JÄa !¥“RZ)忨˜¥I A¨b´‹iG³'™ŸRЬµ¦Z­V ¤†þ™Yaª¢È £ˆ‹bLÐ0oFÊ@¥Z•f¢F‘€R©ÄFÛ Ê•2 –6Q)TÄäFíà±6…@þ¹Ï}î–ñ}[ HMZxã² )Ù2³'mtâ½G„Jëa#½÷X)ðJ)¥µ.¤”²^«Ó()Š"ߢO Š"ÒZCËa;}Dv¨”u6€R¹"KaT”Ëå¼V­XÅÊ0“ ÃÐ{ï´ÖEïãí°nk.Ïœr ˆ½ÂI 'éº -„pB éFÀ¥H^@ÆèˆÊ•j5Y‰RlÎLĨ 1z[Þm£÷[Æ­zÉÒª@™R¹ì9` Q¡(r­µ‰ÛNn¶X}!„'’VáH’'*ÁÌE©Tb"1ƒ™ááRJxøÂ:g • ]dQ‰±¾T*3Ã;Ÿ—¢33Ä–òÛêôvzVlH’ ‚rè¶Ž™¤÷Þ$Iœ ávO€4ÒK!¥bXÙqj6&*ÌŒ¢Èãf£YQJ¡\*«a…cfäyÞ/E*•2ÞÅí©™êX?9Ѫ*¥fI¯ÑlÔˆŠümõ¬°^)eˆÈ2+1&€˜…t'…ô2Þ=RúP…)¤#&#IlÆ!…iÏÔ™y‘ªÕjÍZ›6'šUfF©T3#KÓn¥Z­@@W*Cr´.â¹¹}5fFšÄÝ©ÖTƒ™‘Äñ V­Uœ³ñäädÄÌH’dcSŸ õƘdjª]ë[­V™±ÑívKQ©`fS Œ;Љ…÷^'IlœÜƒ ‚€B/…t#",1Yk,ffæšÌŒJ¹"ƒ nçr£ÖhÈ'Í23CGaÄišvªÕz‰™a¬IgÚí&3£7èwZ­V“ˆ|©\‘J)ôƒµéé©:3c0èw[­V“™½RSJ!˳õ¹¹Ù‰¡¾×i45fÆZg½•"MLV)Þ´&)œq…1Æ kwO€S¬µq™ Ò+O$íØ œ³¾9úðt»=ÍÌX_[½H³´Wo4*ÌŒ‰‰É:3ceõÚ…r¥ÌÌ cL>ÖâÁ \.—Œ1ñÜìL“™±ÑÛX-•GÖbM:Ôë´V¯G£2½ÉÉV‹™Ñév:AH)%tž%A ]@BáÇÉzSr/`½Íâ$6€ÏÃ(’RJGR:&²€pÕZ- ‚µj­¢µ âxƒˆ`­M*ÕJDD˜Ÿ›Ÿefœ[ˆûëD„‰F£p ‰¤Øœ³z¢91ADXY¹¶b­I‰õjUè0A©J)öð¹ÖyÇqWJ‰ù¹¹š÷Þ…Qh9`?vW)¥Ófx¦FD»' ЦÓ<δð> £€¤”N ¶Älá=7õšR EQô^xá¹QBJ "ö¬”Tj©¿õÊËÇ&&›é¥ËÎÚÓ3mV,¥”ˆ‚PˆÈU*•Äq//ŠXJ‰j­^&"'"Ôj•`HšËT˜~øø‡,B–R⥓/­O4bR !¤$_­TËD„,Ï6¾uêÄ©©©VÚï÷®¥i²ÞjMí'IRf–@Ì,¥D’Ä0tž¥!õÆÄhDÌÃùZ)*BXk³€•鬯]€…C‡ß”¤)Ga$H’#IŽ%;@ø"Ï54dc÷ÃàO<á´N4ò %ÙdÊ…C‡´§ÛGŒ1ÐZãÄÉãgÚíéDÆ{¥TP*•””/á«“q©TÒ“­V²taé83+ë,{ï!„—‰œsˆãA'ª”‹õÎÚŠ÷µjmÖ{!…ðÞï=‚0 s(t‘‡Q¨Ï_:Î9g¢(j>ø½¿)N’P’t’¤SŠ„ÞÆh!„ûìg?›ïšÈãµ¾¾¾lŒñyž£V«…BHŸgYf­…€ •••µ¢(°|uyµÑhBßl6Š—N¾ôbQ‰³®lŒ ÉÖZ0qd­E0è…¡²ëÝõkZk+„PZk0q9ÏóÜZ Å\¶ÖÂë„> U¼º¶z¾(Š, 6Š\‡ãè/%“wÎäin<|lJ»#©1¹uEN4´?k­˜™I¾þ¯}ic£Û±Ö¢•ËE‘Ë4 k-ˆ¨Òï÷ûiš¢•"kíæ~C³QëŸ]<ó‘e‘µ>0Æ`zÌÊ1+Ýë÷V’$îc ¥,gy®­µR–Œ10Ö:¨×ëúĉãÿû…ÿü¿Yë®|ûà›½L$É&ÍS+„Øq“sÇÍ¿´·Qërf©@@ˆ(Šì…«.-_:™¤IrõÚ•k3s3H³l$ILD•S¯¼üõõõõ¯­uW®ÍÏïßd½Þ¨ëc/>l~vß#¬¸†aåÄ·N<#<|£Ù˜^¾zu…‰<—Kæ¿¿ú•ëv×{½÷ñU*Õ}ýÁÆàüÅó/ÂÃAP­(E‘]\\\ª×ÅäätADÍñ÷„ì³I20Îa°gºÝ$wÆX)IŽ-ÍFñܱ£ÏÖëõâÀ} ¥ØÅqÜýÇù»¿¨Wš“«µîþ}sñ‘#Gn¹Ò1=ÕêÿÃ?ýý_–ÃÊåj­Ÿl¬Õj5mÏYa #gfg,1yçýr{vÏ|å‹«µŽŒó¸rùÒi°Þ cŒ U8tèÐ&8"qý¨$yëÌ`Ð7r‡¥ðm ps¬xó.ìø¾P½Q×õFýpív;k·Û™Öf”Wª•m–êºþîjeƒˆ|o£×#nÊÖtë–àÔl6Š-¿qǬX¹ 6—¿[Ýkk¯Ÿ¥¬)úý´pwâÈ!Å&ÖºWÝUŠÝ¸ñ; ù1¯VßX*•[ ׳U¤à­wÞô76¬pvGv ‚Dä%]Ÿ> aïùma!ÄÖÓnvÞ˜þ†ÛiÜÆ¤,¼p× pnG®î‘[b€$IÆÀdY¿Ã:¸d‚)„“’„p÷¶!„7^lÔEj)õÞ-€4yçEj¬1D¤ k kôÞ ïý=G†”¤œµ$¤ãx/ŠÑ^­äÞ È² kWWÁ³³Î9_)lfâÁÀº{<DQ9*t¡„`Œ¥^¯ÇZëðò¹e‡¡µßrî¿@´¸¸È‹‹Ka­ÙDE“×zÅpÜ‹À’+E¡7 `Võ ˆ&Œ1áéÓ§@CÏÎnG((]¹r…/^¹>rØ.,y°ßï“ÍÖ´Âoµ)!$© Þ I|ÛJ$¥¸Íá£RrÇ:$${YZH)¼ð^Bˆ0Ï eŒåµµµh > Åhmp3!€@´ºº*Ï/-~×™ýûôÂý‡ynf¾]­V•Âß‹/ ‹¢$rxçåêµemŒuʸN°`ä7À[’Ài’—Ïž>“Ç?ðöbv~¾Ý]_ïß³R²6&oMLNX«ñò˧Ò8Ž»v¬`¶`,øíb€%Ùí¬Ÿ=ϲ½t~éÚ»Ž|×w7ëºwÞYkîÊ52/à½óÛÔ*D ”:aéêÑgöÖ;ë—¶`ÂMÏ ›êØj4ÄÝ}ûç¸|åJ1;ÛF„!÷°¯{rÞII^JyÇÉ{oâ$‰¿ôâ…Ï|æ3¯ôz½kÇþ÷…¯8çr M¾Ø’4pkà 0ô—Ò(ES³SÓo~è¡wñü° ü=|[BˆáP—¦é™ž?þå~¿ßÇõèŸHF¿f;€¡¿”F¿áˆÕn·›“íÉIŠîÕ&7ƒåååµ^¯—Œ@j {?ßBÂõÚê¡-à ]BÞ”îU±qãh¯G©pCŒyµž#ÐbDÎ=k#€vD€Ãu+ØVþÊ£;‘þ tEXtAuthorJakub Steineræû÷/XtEXtCopyrightCC0 Public Domain Dedication http://creativecommons.org/publicdomain/zero/1.0/Æã½ù%tEXtdate:create2016-01-21T14:13:03+01:00[eš%tEXtdate:modify2016-01-21T14:13:03+01:00*8®&tEXtSoftwarewww.inkscape.org›î< tEXtTitleDelete5éZÕIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_shear.png0000644000175000017500000000065413561570220017534 0ustar otfriedotfried‰PNG  IHDRÄ´l;bKGDÿÿÿ ½§“aIDAT8í“¿kÂ@Ç¿—4†ËY‚š­ƒBAAˆâäÔ‚[–êÐÅ­cÁ¿¢sç¶›tîàÒÙÅA AÛk»TÔ¤C`®¹¤ØÕïvïûÞ—wD‚Ч[1Ñ?:¢ž­u¶YÄÔufÿ­ú –øƨÜhï"C×õž,KK¾'“ºõzõhµ¶‚B-×Àð årèõºhµ^<ïñ¡–¥¹•Êö _çv|•BáÍæ£Ñ‚Ÿd³Ôa çÁ~Q:G2ù†~.ð%˜¦2«Õª·¼'…çót:¯!>u ÁUlY÷h·§B¿\Ž;šæ]yBшCèÆÑ4!nã÷°?ŠÅÄ®'•T*á€ç- clLÈç;6 ™RJ.ÿìÎÏ73æd¢úP¥Ó¥'M£î÷Ù¶íá•6Úè—>’‡ZXøããšIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_arc1.png0000644000175000017500000000067113561570220017257 0ustar otfriedotfried‰PNG  IHDRשÍÊgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<6PLTEÿÿÿ?Bá?Bá?Bá?BáßBÿÿÿDˆ>tRNSXŠ?ŠÃéü¨>ÍXûÖdbKGDˆH pHYs  ÒÝ~üVIDAT(Ïc` ˜˜qóócç‡f&F¢tà¶7`aecçà`gceAN.nn.N^>„„  ª2ì’ e X¢#Ài+nwÒÛ *¤ôæm%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/copy_32x32@2x.png0000644000175000017500000000466113561570220017615 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð¼IDATxÚí[KŒÛÖ=ï‘’8²æŒ{f\âÂÍ.@óñ"(E. t_£í²@] ×îB‹ÖA>ëÙ4hºê2@6vŒ4iÙu?‹&“=Al>#оÛEJ¤Ñš ¹!éò ùιçÞ÷!øš€v»Ýj6—¬/»Ciæ3ßc¾úɵk×y]šÍÆå­'Ͼxé;—ø²¦Y·Û¥{ÿ¹÷4€·N€õg/=ËŸþÅeãLµ~¿ËîþónkÑ×U“Ž~¿¿l¬3Öl6+»ö©•ü㲯 âëN@U¦žüUZUqŸØ)V@õàS©€8pQ1§ˆ€Y¤Uƒ?EˆzEd" ÓéÀ²¬Üv÷îÝý^¯ßûöI;¥¨*>)Oœ+ÂcÀëoÜüî‰.NâöÞÞoÿPŠË² ëzf›G¾ÜÙ?ØÿáË/,XcUe' €ðÁÛ?¾ùæÍO®ÿúú? À Œ†e®ÀK/\®ü‰íƒ;·ÁH| @q¶·w±½Ýfd ±¿ÿi@†1‚ëºËƳZ­†fóÌŒÿÏR€að<'³eÛËÆRÝn7·æ_¶€€¯²À)õ|!¶¶¶°±±‘Ù¦×ï,«<å¶)D€¦igƒ)Z½^_6ÞRÀKPdž.Šß³Bà@Rƒ…¸ÿ0QäfçîGå¦@2ꓟّ)Yç_±Y–…^¯W9ð¼¦5°¹¹)!dšÍæÌt8 ¼‘Y'×u1 H—; Ä*677s•P€'žØ°!Ú_. \>xyÔ§Aå9”‘{~´Z-\¼x±rࡱ‰BFaâ€>ÌÚÚ³åÍcó/“‰(ö÷!ðÀŦ|c”h—nf+¼|?@ÄÛØÙkÏó`ϱ^(*÷ñ7@£Ñ€¢LC›c&˜”;çIã9Á5M<(|¶ãE}ÛÛ;X]]Åt &@–ç»»»áÙÔv#SÇ矘 ¾(ð¸?îË/%@néÀ‹š¦i8þ|)à2ðÙÀ¿¦i3¾ÜaPŽ+ð†Ïs2ÁÛ–™ ®V«a}]þþE9¹g2 |®Q NI§ÓÉ]ïçÛXŒÜ“¾À_dM4!@!°¹Ël8âðð‹XgÉHŸ2ô­­­áܹsHÏ}’¦Xj LƒßÚÚÂÚÚZ&Àþ ›K‘¨LîDò¨S”™`}YÔ5M›Ú·ÉÛPUUú¦G¹"—>Ái4´ÜÈV€9’žJQP™/\¸ <›Œ‰?ß—¾T ,x>È8€“¹¬ ¼ðÆEp>ðb¦šÇ[–…n·Wd9%$±­¬¬Ä†Ý´uÈT Ì \ÒhV~€ã8 ú‰6e@¦™<êB¬¯¯ƒ1Î9xÊó½D H/„èQ;Î9¸„áÅɽ(ð¸òBà! ÙÌõè&‰$ÁŸ9ÓÂ3Ï\ÄÉ‹\>pÆE¢(øÜ€Ë9xô=vƒøÜ;Ü :Áb¾ H6î|š/ÏÇBãk±èHF>‹„X d@)#¼Á4 L"±j«û¬Ü³Àç!%AõXäÃ#±[Sõ˜ZФ¯€°É§@BˆX™?ý9«€ò+¶ü¨O|Ór/ù„hÚ088øÔ¿#s•£££èš–eÁ4Íà¡ÎH‡aéh®4ßùå/~õáôýþš\H@±á.p†swιô3˧ª*|߃a‚y‹a0 ¦iBéY:q°[?ýÉÏ÷’½XB d¯ØŠFÞ÷ƒ\BÀu\èºÏó`YVtè#¦3"@|üÔÙݵZ­™½ûJF7k[jzÅV&òŒ1¸® × òܶmx¾Ó4£Ã0 ô{0Ñ{öÈåÊ•+}ÆØÌÃÉÊF„W:¦—¼çyð}/öéºx~4Òq<@DìÚõWo¼Å¦?Ôj5¬¬¬@Ó44 4Á®rè z½Žz½ŽZ­ªªBUÕ˜‚ë:ð<®ëŒ¦i@ãá1:½Gèë=¢Ï¸ÏÝØ»ñfø…*€Àÿýo`ŒE«Áè9>X0 ¶ã­àGr¥þö}DB„ð£O"^Ã4aÛ|á :À_u çív»]h_k¡/ö¿öúï÷Uù•R–l/!0J‡¡ ¢³ÄÈ!Ð}Fø£mx) üÛÿ¶ß\]«¬ÝýtEXtAuthorAndreas Nilsson+ïä£XtEXtCopyrightCC0 Public Domain Dedication http://creativecommons.org/publicdomain/zero/1.0/Æã½ùtEXtCreation Time2005-10-15 ”W%tEXtdate:create2016-01-21T14:13:01+01:00Ìú³%tEXtdate:modify2016-01-21T14:13:01+01:00½§¿tEXtSoftwarewww.inkscape.org›î<tEXtTitleEdit Copy¡EŽ IEND®B`‚ipe-7.2.13/src/ipe/icons/zoom_in_32x32@2x.png0000644000175000017500000000334513561570220020313 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ðËIDATxÚíY¿oEþÞì9¶ƒb# ÈB4©°AJ‰‰¤DT¦ ƒ?ƒ!ÑÅU¤)]ÒR!"!P°R¦J"G±"A0É9älßÎû(fgßoï²'.ûIw;73»û¾oÞ¼734hРAƒ 4hРAƒçR׋ÞÛøñežÍTªÌkÀ¹boûûöÅ/îÕaW«.Tìû„\ÉTBXì+.Øš*<¾ûúcHÎïLªâ›ïRj}öÔ.@+0øçßCt³,çN,/ÌÖmNýÀÁ‘¢ÝéfꈙI˜3‘·öGÄÿYRr…©€=« ¢4-L—=ùƒ¬ L$f!‰xû„= !ŸV€"ÓóôyÐÕ×ì€1Ç„|$LÝÆÔ#åìW[K€9 ÐòtPA@ Ö6*Áõ­M1øŒ@@òdÿÞ[@˜x¶2ò˜|,•/‹\Zûòò¥¡Œ\ùãâ…Ïk€¢ o¿±²øÑÚ›n#Ó/f‘#ïâ’Íd½hþo|òŽñõÊdº€‘§Ày ˜èµ×oîàöý¿«P©(Ĭœ^À[¯-c?·¦/öM&ö;!ºV‘Où¡º¶3K‹IB  ~?Uñb~ÆàÔ s•ÃG% ^ýݽ΀Þ‹RbîAWqÐ=*¶1›Òâ‚ÙÓ£…±ÊÀc&¼'TàÎ\Ÿy×'Wj€¦k-Bíur‘ˆS$OX, UÀ*£Oªl™´["ôõ$¨€õSÀëgN ý´ÿ4»""‡>:Ä­ûmãNu v Ê8pyRÉ.ñŽè+ø m’ië†Dh«!UxÓŒ@7*6–Øèœ[û£/[–’—b›÷„ŽÐªm†hD ÖW—DÑ:ŠÌ>Z+£¼Og##Øù«ƒ½ýÄm `q¾…W–g8×OîqÏPuÏVeä]îù2âö¹j Û»{¸úó­d„â‘IRVæ"‚ß]-y0Bü²}'ÎwiOòÏÈÜáá£'•WŽU³ÀõÇíÎÓÇíA)0CôUç>X[-ñ1ƒ ܹ÷PIÞ`¨ÿ(òkmložÿvØ{Ö7¶>¥ðœ#+…9Ï8†ùáÆæùéü_@Iç̺rz‹\'jß+“Ô˜l…]ì°:ŧÂ"LÇ»ìÜG’A¦Ua´Ç§f×I>—Òeò³Æ8c€¤®’û ™™‹ç†<$^?m7¤4zf‡e£ >qµÝ ˜™‹÷øùÕ?UkR¶±Ïgb䉚Ab„zd‚˜h–¼§cÝæ_"hõ!®ã¢Š½ˆ›>mB ^2'äcV~ 8ú–ÜïÊ»qy@?0Nk_båżtªï ¬ºôèçLÔ×ädÉJΞJžPU? þŠAeQCøíæ]ˆ¸ÑnµLɤ*“Uæ®~t|Ùº/ 2|²ËðèÚÝÎz‘3Ÿ{¢aØy€ÄÅóó}¬Áp”µç°¹r/q™+'Va\‹o/R×^”½›%åãŠ1²áãF¯/!Òàq®C€Qß7qƒ 4hРÁsˆÿókðx~§í„tEXtAuthorAndreas Nilsson+ïä£XtEXtCopyrightCC0 Public Domain Dedication http://creativecommons.org/publicdomain/zero/1.0/Æã½ùtEXtCreation Time2006-01-04×¼RÈ%tEXtdate:create2016-01-21T14:13:08+01:00YbB`%tEXtdate:modify2016-01-21T14:13:08+01:00(?úÜtEXtSoftwarewww.inkscape.org›î<tEXtSourcehttp://tango-project.orgïâ– tEXtTitleAdd é (IEND®B`‚ipe-7.2.13/src/ipe/icons/fit_objects.png0000644000175000017500000000215213561570220017714 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<§PLTEˆŠ…„†‚ƒˆŠ…ÿÿÿ4e¤îîìîïíïïîïïí6g¥ïîìîïìïîíððîCpª_„´ïðîððïññðNx®@n©8h¥5f¤\‚³ƒŸÃ¢¶Ïðñîññïñòð™°Ìz˜ÀW²óóñ7g¥ ´Ï¹ÇØÉÓàòñðòòðÍ×â½ËÜŸ´ÏôôòóôóÇÒßóòñòóñóóòôóòÎ×âõôóõõóôõôòòñóôòõõôöõõõöõôôóôõóööõ÷÷õ÷öö÷÷öõöôöõôööôö÷öøøöø÷öÌ×ãÙáêøø÷øùøùù÷ùøøªÊ·ÇÛÓÛæø÷÷ÛâêÊÖ䦺ÔùùøúúùùùùLw®g‹¹‹¦ÉøøøžµÑo‘½Kv®6f¤;j§Fr«ùúùúúúûúúûûúúûúûûûüûûûúûüüûûüüýüüüüýu"~#tRNS™   $&*.024+'"  1”»ÌbKGD$´ù™ pHYs  ÒÝ~üAIDATÓc`À•1#PXY(ƒ…U@ Ô54Al¸°–šš¶Ž®¦¦žžžBXKß@CCÃPÏÈØØÄÔ &l®iai¥gmccckgïàè62²qvqµu³u÷ðôòöñ† Û»Ùúºûù;‡„B…ÃüÃý½C"""£"¡Â@àŸöŽŽ ILJŽMIHHHMƒ ‡„D$¥GÆ‚32³²s Â±Éñ¹yù  ™…EÅ%¥e0w'”WTfVUe•”U×Ô–Â}YWßURRÒØØÔ¬ï„&ª¥e¥M-­mííà b‚…`KKGKgWw$™±‡7 +fì°…Ù98¹¸yxùøø…„EDÅÄ%€vJHJIËÈÊÉ+(*Š)ÈÉrH)I0£ _ûÞHdÀ5tEXtComment(c) 2004 Jakub Steiner Created with The GIMPÙ‹o%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_shear_32x32.png0000644000175000017500000000100713561570220020366 0ustar otfriedotfried‰PNG  IHDR szzôbKGDÿÿÿ ½§“¼IDATX…í”ÁjQ…¿{'× ¡ ÝdÑBt#¥´]‰]tku‘G(øn]µ®tQÐÜ mWæŒiƒ`@‰`2$3.JÁŒ3“¹¥¥ ç,ï9ÿ¹‡ÃÏ Ü3DùŒ.Øš†Û.ü|¯ãèSQäsp›p®À„Ž„o:3ÿ7ü;°éíyCÆËB¡PÈXÖâ¥e-~üDH×08¬ÕjG~ηF ֞³P3¥››hµF €ü Õ[–ÁÖV!Ä^°„O€f¨¡m_ å1Æc/Tw,޳ÐÝÝ­ñr®ƒëë_hµF±>ØØÈŒ•â]¯@)—R©Ïéé0–~iÉ`eE™À‡[ `Û}¤œÒnbéËå Žã}­×ëí[  [¥²06MZ¿V€›Ô¿ºªL!DhýZ®êwµêŸLD¯Z­n¿v€«úkÕ¯oçéb¸«úc¸«úáŸKèyp4…Oάá‹R>4ö÷—}ãR)åôï×lV¦¢ŽOD÷ ?ÃlÕÃaÿñÉÉtA>Ÿï‹Å^õ1N€ $¸wüídŒ.’™¨IEND®B`‚ipe-7.2.13/src/ipe/icons/undo_32x32@2x.png0000644000175000017500000000732613561570220017611 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð ÚIDATxÚíš{t×}€¿;3ûÐê…$„"^Š©Ç®0vmœ8~ÇvjÇ)Ðâ»I°Û„øqŽ“ö”ÔŽcJÇ96ìúE îiÆ)(b0‡—ÁÈaBH«•vW;{û‡Vb%v¥]!!NŽçÌ™Ù;»wî÷ÝßÜ™¹³ðE|Ã;V’9ÜmІ~÷ ³l¸á‡E@åjGã=!HnxãrhíZô¢0/†Ç6‡›¸L°uÞ/…yG =2µô1‘WüU9Üà—MÀî5äy4¶é.ï]3þêWZÖèûˆáæîŽ!=v®f¢›¼™£Š§Þ¼Ü0¼ãâÊ0dPù:3•`ofþÄâkæ½æÒ=£1k;\A0$*×p·&Ù^0~Væ”9+]Bsaúß@Úç¢èÂ*×ðCëÆL»Ý5þ†åº’-˜­ï TÆ•v Ú bÇ~äÇ“f.&oÂbd¤ +¸ ¥,@Ñé[ Ïý×Ð ø`ž]¯ó†¦éßþó›Ÿ!3ÿNìðìðG @ ¥Îÿ?¡ Øõ*¹ÊÅÝí»aú¼—4OæõØ¡mØ‘*:{]‚ÒyüÊá¿4•¯q•2ØäË(3µl¥axа‚@Zµ*¶ÇElÏ_9,`Ç*f¡±qDá´ôɳ_v ͋پeŸï ­zà B(¨Ø±†û˜ÀgJñ©ì3[oœÏÑË%`@]Q¹†»5Å;…“çéc¯{NGu`· d(p@Ù(ìÎÏÑm oî#t´Ä Á±ÎcGšèh«¥­¥Úœ¯C9Ê‚z©xM×Y=û{¿¢ì\Í”`ù„k¤àêŸ iŸÅV‚2QQðnÊlPNT€†+ó@‚’ ¼͇Ð| "8N‘ÀAZvÓP½Û2#ACÀ:?+™Ïáa žAÛ9žçQühJÉ?3¶Ç<†Ú¨ P8Qà.Q1Ûa¡ìF¤UƒrÚÐ\cÐ=Sѽע{¯íM[9}xô7è þ-¨ñô-ó ^v»Ö’æ„xKÓô;¦•=«¥ü:vx/NGl§D% c€;e€Š®QҮÉE9þøÒÒ1|7ãμaäã?³žÏ¼g;V¤ÎÛoZÀ¡Ë&`÷òlø@wg\?mÞ‹†'svð‘æ‰î›nJE{Þ‰ÊpzÈP2ˆÓ±iÕ&Ù:WÆ­x²¿‹c·srßrÙRØT’ï–V°~Èì\ÍD!ØäÍ(,žZö—áÕö!Òi´µ •ïÊ„. vvx'J†So¤žƒ7çaô´¯PôEU{t‹R‚‡æ”óö øè?Ȳª ÃUpÝ·Þ×4O!fë»(çÁ9l+-ç1Sò%iG–ÔZßöé–G-+Ò‚¯ð—èÞé ï˜ÇñeOB)Ò\5L¹lº¢´œeB±¸æÐFYä9åÊø&Þ¼% ô”ëš[AGI9+”ÃÕáö–½‡·ðsi¤Í"mä“ <“ººÖVæ:¶ó‡£;—ÛV¸oÞcq¥*çBÏBÓ…­ pX””³‡o4œ<9±ç)GsOÁ—ÿs„–1 únýÍÇ}Ò²W¼ÂÖ\Ÿ2¾qñeÀåñ*9Ã& äûlApSsñÀ±]Km´Q¤üKô®1õ˜}?a!y ½¥NµÖˆ;óNz/JE:atoç”Äp (Ï^eqcÛ¹ÓU•K-%]ø þÍH);/H¨  Å«gª>´5£Ý;­Ç~¡e PØfMÒÃǽ£*]ÈgºÎÌPkãÉ#Û–Z¶ÙNZþÏ\Ÿ#y1è?mDÂuèžžãœ0F¢œVÄt!¨»"ÌzˆZa1Ë µ<²í)Ë }>àºnú>Ÿ Á©ÿº{RO£;Ò„RhJPu%èš*Òf/Â_Õ@™ÙÚþÉ–gœPs%²óµ‘gÑz-ݯ””â£H{“znƒéž„Z"ÀÔ¼¹œºAcŒÞP BÇ۸˶­÷l^Î×TbF¢r¥¨·"!'öª"ô4÷g÷K •³ï'¥IÇTÄŽí9=Á>ý¥ßá<úÊ-K¾ ·‹>$Z4é  ÝÑQÀð• ¤IãéO”’¬Kµ“Ð û9.tï^=tñµ…<ê`™#Ñ¢åÉfF‘Û›©+èê~Ü™whØŒ´#fõ)ÞæÂi“Tôõà ¸ø…¾è§<Þvì@|ýaž]þ8“£`±¡âlw¯u¯¤eŽŽuWú<„žÃéOÖYŽÃÊŠgFÄþV‘øù<¡1€%ÝÛ?zž)Pÿþc& Ý•ïöå:vh³ž'=#*\-uÿ-BÁs퇪X:®„ÞÞW–ôÑ[Fïè- [Â䫸7;o²ií‘о6oî¢ôH¨Ö©9°Æ †xâïŸÅG@¢%®€d5RÐßéH@Þ_²€üLwä™4ƒÆï&-[?ùñ V¨=üûŸâ­hÛ’ýj·„.ƒŸJ†ôPéépËLþ.+7ÏíÉÈnTÊ–Âãª9ôšË®nÿ{ù§ææîúº2 ? ˆ¾ŸŒ¬dDÅoàR¿}’oee‹¯Ž(šXëX–º~öć¹Mu{6Wòô¯×ÓS—ŠS÷EÐļϋ7Ä‹DïºTQÇVþ›¥Ì;VÜ™[”W'D›?hs·Ö*jlîÜòG~½lqÚÓ¶Ï}½ÏÛ¾zo ûúúMžˆ•àõ"~ùCfN»†Û²r1½éÔ[¶–Û`Tc½Ü¿ú?ywÝfü$äd’å}\Kv,ˆêkAú‚{˜5a×ù2 h.ZecÂíÈêSl{îö­ÁL¸¿}qS6Y¸\z³;rrÐÿö.Šo˜Î—Gå3Rœu¤ÛÉh9ÏÉ]ûØÿ›ԧØ×wã6f°Gû~/ƒÅyè·–‘{ÝÆ3J÷âi*<óøVq|õêÏž¥ëýz²°} èÜ;>¸˜9ÏŒ‰ø®žLná(2<^té ƒh;OëÁ*š7졵¡§wÚ^¢„‹`ãEª7:‰À»ëÏÊBËÈ@Ëõ ¿#Gà7Íq¡ëNC ²ÑOää ìCÕXq€!9 ýíKJ@"ý•%êýdŽ Ÿ ’‘¨,!`²1ðÁªˆ¤ ý p‰À“9žêg»?)ƒ F$#b ÇûÞ%5|¨CôSfP¿ˆ~âÿŽº/bÆ.4çtEXtAuthorJakub Steineræû÷/XtEXtCopyrightCC0 Public Domain Dedication http://creativecommons.org/publicdomain/zero/1.0/Æã½ù%tEXtdate:create2016-01-21T14:13:08+01:00YbB`%tEXtdate:modify2016-01-21T14:13:08+01:00(?úÜtEXtSoftwarewww.inkscape.org›î<!tEXtSourcehttp://jimmac.musichall.czifã^tEXtTitleEdit UndoŽPIEND®B`‚ipe-7.2.13/src/ipe/icons/delete.png0000644000175000017500000000303113561570220016660 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<¬PLTE‘“‹Œ‡ J‡ I‡J†ßàßÍÍÌhie«¬ªwxu¯°®rsq±²°‚„€³³²xzw­®¬~}—˜—kmiÈÈÇÚÚÙáâàÈÉÇ{~yžŸžŽ­®­ŒŒ®¯®“•’·¸·‘‘‘¤¤£‘ªªª°±°y{vÖØÖáááåå厒‹ŽŒÄÄĤ¦£ËÌÊœ›ÀÀÀ¡¢ ÏÐά­¬ÄÅÃ¥¦£ÊËÊàáà“•èêèñññçè王ÊÊÉØÙØÄÅÄÞßÞžŸœÍÎ̳³²ÝÝÝÆÇÅרף¥¡ÙÙÙëì릨¤À¾óôóèèè‘”Žðñð´´²äääîî툌…àáàÓÓÒëëê©«¦ææåÜÝÛÞßÞ–˜“›™®°«ÖÖÔšœ—”–‘ÎÎËÔÔÓ¢¤Ÿ¡£ŸÐÑÏöööÞÞÞ¼Á¹´¸°‘“ŽŽŠ¬°¨°´¬’ŒŽ‘‹¶º²¬°©“–¬¯©äåäÜÜÛºº·³·¯´¸°³·¯¶º²ÃÇÂêìéãä⟡žÄÆÄ¾¿¾¶¸¶¶·¶·¸·¹¹¸ºº¸»»¹¼¼º½½»ÀÀ¿ÎÎÌááà ¡Ÿoqm××ÖØØÖËËÉÆÆÄÅÅÃÈÈÆÅÅÅÂÃÂÄÄÄÇÇÅÌÌÊÔÔÔÅÅÃwytegcrtpˆŠ…ñññëëëêêêéééïïï J‡ççç×××ÖÖÖÕÕÕÚÚÚÜÜÜÛÛÛœ»ÝrŸÏz|wÙÙÙ½½½¼¼¼¿¿¿ÀÀÀÉÉÉT†ÆN[jœœœ›››\djYŠÊ+Q†,R†X‰ÊXŠÊž(7¥¦££¤¡ÆÈÆ÷ø÷§¨¥ÏÑ̦§£½¾¼ÌÍËÎÐˇ‰„†ˆƒ…‡‚¾¶}´tRNS¿™ÀÄëúôùùûôúõûôùó÷óüëçëèéöíñçòëåâóäöàíìä¢èéðëèßðéããôçøÞëðß×ÕäçíÆÛçæÑäòäöÞîìÚ×õ¼âñ—åÛéòáåÄÖäšÑãÌÅÑëëÈð¾Í΄ƒÎÏ›ÍÈù¦ƒƒ„‚—Ò¼ÃõõõõööööööööøÊ‚ìõõõõõõõõõõõç® #—µ<)/1230,-*"ÿ`tbKGDˆH pHYs  ÒÝ~ü€IDATÓc````Ü‚˜ `ËÖmÛ¶m;¶oß¹$Ƽk×–Ý{öÁ¾}û8xpÛ–]»˜v:|äè1 8~üø‰“§N:zäðá]@áÓgN={öœ?þÄ…‹`á‹—@à2\ _E×À˜,|ìb`Ù…°=ÃÆÎÁÉÅÍÃËÇ/ ($(,"*òÐq I)iY9yE%eU5u °°¦–¶Ž®ž¾¡‘±‰©™¹…¥XØÚÆÖÎÞÁÑÉÙÅÕÍÝÃÓËÛ,ìëçvýFxÄÍ[·#ÁÂQÑ1±qñ ‰IÉw޽—v,œž‘™•“›—_ðàNaQBñí°piYyT‚AEUuM-P¸nK}CcSssKk[k{G{gWwOï–>†þ [&Nš|øèÑcxôpËâ%K–õ-_±rÕê5«Ö®]µvåºõk×oظi3,É ‹éC,JtEXtCommentid logo†Æw¹%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/stop_32x32.png0000644000175000017500000000410713561570220017251 0ustar otfriedotfried‰PNG  IHDR szzôgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs  ÒÝ~ü5D½w!îî^„’¹Ë?Ë¥ÆTU,]§}çNe<ðû“ÉôücYp¬®±ñW{ô%’Á`T³¾XþR”.Ü:ªŠetúýJ$ØùµT*y®/!0ÇÖ®ýå·ô%ÆÆPC¡¬Ü9å²Ìz‡„eá<´FQ¨Sî›&ŽãàUŶ,:úú”p °Ë¯ióC0œ'pN6®[÷‹=øâ##$Ãá¼Ôå²LmC©Ý»Y3:ŠšÉH,"°Æã¡¼µ£·—Uá0ñ\œè9[{z”p Ðÿ”®O_…[@?|úÒéÓJìóϳà®Ä9ðšúzæOÂhj‚úzªoßFÕõlû嬺¬ŒŠ–b'NioG¶,V‡ÃÜ×õ|LZUÁqèÞ±C¹yóæ·>†ÓbL–QC¡¢9ŽCzöYŸAзo'ý⋬¯¬DÌõ}µ×Ky[ñ“'=DQD{æ*2IÂìܺñéiDEÉcÈ¥Úp1‰ aðØåËPQA¦»A0úúd™õƒƒ$S)ÊÛÚPÉvŠã ¦RT=K0“!µ¨œÜ¦°íeä·“%Db16¼û.¢,“Ù¶ A0·oG”$*¯^%qô(ˆ"" $“Tž;Çd(D\ÓŠ€óDJpGiî8N~èØ–E$eÃûï#* FGG–DOfOù<&“”¿þ:“ccĉè—QÇÉ÷ûb"¶ã yìòeDAÀèì,LEMÃwñ"wîÅŠÀmÃÀ6Ml7™LiÛ.^4GÆ­v˶IÅãT^»†ÕÕU+MM!¥Ó¨ dfg1ãq¬dSÓpl» `ÖÕ-Ÿ‚| ¸J¸)ToÜHEo/éçŸGÅ|«ØÍÍhÏ=Çá0ÿÆ0Œ"P×m(JA>}NîŽmgçqŸW?ù$U~?™^@eDQD2 ¤éé|ËZ]]8бo’dzØvïKÖ€mgÝ•ÕU¨ni¡jçNô½{$ Q3¤7Þ@šœÄØ¿«£Û¶±»»e™NŸ bèzxq!–"à8ÎùkÛÛ©ôûIïÙS×uÄóç}ï=â‘튂¬(˜mmÙZioGÜ¿ŸîŠ >»pK׋”LmY”¯[·DþŠÇÇÚ¸ܳ€¦!^¼ÈØ0?:Š¡ëüûí·1?üid$ûªìµkñ56¢¬ZU.ˆbQ $€o@ÍL0عµ¿_¶R)Œx<_ ##Tz<ȲŒU]gp±wÞaþÎü¢–i2}ëõµµˆ Ix>úˆáW_Eš*¢¹™ùD‹ńá´0ê[X¨Ÿ™˜èÜÚ×'›sshããss葳Ÿ|Âêª*ªÆÇ¹t‰ù/¾XRݦi2uãë6lÀ 1|æ ‰‰‰ü÷¢$ÑÔÚJ,¶¯†Ã1¾:sEgŠ8×PSóãoö÷{gnÜ  ò&IxjjÐff–T÷â{ÉëE,+#‹Àe™¦–f“IûoáðlvüîåSàÚüy‡¦UOF£Û:ý~ÅL&ÑïßÏW®‘L>ÜM‡™NÉ2M­­D ëï‘È$Ð÷3È¿ó—œ ‡à/þtzõx4ÚÕÕ×§X©éxü‘À¥\Vš7m"‹™ÿœ˜¸'ÂS' º¯ä©ø \ÙžNWG§¦¶mëéQLMË“X)¸âñмy3£ssægÑèÝ›ðõ×`êA¬åþ”_…á-º¾fvjjkWw·l¤Óh‰ÄÊÀËÊhÞ¼™ÿÎ̘ק§GÞ‚\ƒÙ)ŸY ´ÜéºÒõcðò¦ŠŠïíÞµ«LpG³mc»“s‘»ÏÛæf0hܘ½ý{82s@ˆ1·®—#à*³ ¨*~ Çjá%¾„¥àúy8ž€ Iö3žËâCxÈW\"¹kOβ“Ô]Ã̜ę,€ ¤^)RñbŽ˜ .PÜ …Z}¤ýC+ ïP$ý/%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_label@2x.png0000644000175000017500000000256613561570220020067 0ustar otfriedotfried‰PNG  IHDR,,´’ŠgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿ‡Ì¿ pHYs%%IR$ðoIDATHÇÕ–[E€¿ê®žÙë΀°\ÜjXˆqUÀKÄÔƒ˜UxÁ€ 7׆5†ߌ¢^â 1hˆr1Q0 ;» °·a™K_ʇéé©w†]x²*ÝÓU]ç«Óçœ:gàÿÖÄmWl¦k–Ù*§î¼¹ç›Õ~s¨ÂûïöäËœì$(;sãC¯'ûD9‚* XÉçïVϯ?ãA­ƒ— ž¦‡Éö¢V'®½cÀžÄG…Ø ì>S¬°­ÁN²ÁòГ‰Ñ§ÃK,Oȃw îÏõå™ÔÀAd—näbÖÞØÙólr¬ÛÄûô¥½w¶Ä®õvAƒ¹Ô øR[ ¶w~{ðÖÕ²JE W~™ÑÁ’ ¼0op×Ц¬î8Ÿ+î¨ò —çœwæ ^Û¼’¢Ã:c¾j€ó¨zç¶Þ|BñÃø{ªz¤vôŸ)Ó…‹¥µk^`y`c׈¨2¡øšo§TÕй·[ì›x}ï‚.¦5@!Ÿáá‰/Æ'žfãœÁξ-éC³ËÓîîÇ…i3¢eíýsÇ­ík,\¢:ÍY~¨Tʦ-µî¹_ZkO‡¡Pñ?j¼ Ž]¥e AV±mNàØÐ@êŠÁ/8–Í”´ #ͼ4õp/×5ð8üJ!zÿ§ºzÓHI XEßmÁr÷ã±–}GKî}…ÿáµ²Íù.ë­VNkÍrä½%¸ 3%1emÍ=òÒC)´ŠRãb1è bCÁðc÷%=f4¡*a§¹È¿YJ%µ56N¬º‰Ó4v>Ù>ˆÑ„²J¹JS&|ŽikSêú§þŽö§ìWß…s™ˆÇšºñ LÁ'ŵÉ0Ýüê#VϹ`Œ”±©ÞÜ|cmLáœß³î/&Ûˆv†W)Z ÔÃíþÜŠ mª\kA5ÇGÜKÿ¬`¹÷ÑÄ¥9`Mxӭ鄵w6Sز¸?ÿµvüo7‚Âx°¿ÕyO= oP5ìx©T6ef‹%icLLTžã»pl¨?S0t½EeÌhV'«ëâÆL:çò[À9ç™,— ðøLð>íÁÁáÒÑxRŸéFma!×5çYo¬rÆðd9Ip‚i²ô#Gž<9rô%MНÊÊ´” a[; ­ƒËºF }Kˆ³t“ÄÂÂBDnÖbMüXÞš0Йĭýn‚×ez6RsÞDÉ?Á"llìÝ×?ÈÇ÷¿, $ :Xù`çêà˜µÛŸ©RSP Ê‚ßÈá ‘ÈNõððpù£ÆD ô¸³’ÖÛÁj‡ ¬Fb‡W4ÎEb8Ñåà...µèZÅ2|¼úàáã1Ì)\¡PC¸ñ$Ã{½7ŒQ7„éì†÷Z¸eôÔ°œÔp2êvdcº¯qzüHÇæ&-<óH׃Oâ„&iº­m‚U“M¸x³åŠÖ&B ý†çBË?ÊÈBFû]y*ÏË”%%tEXtdate:create2016-01-20T14:40:38+01:00ãåÃS%tEXtdate:modify2016-01-20T14:40:38+01:00’¸{ïIEND®B`‚ipe-7.2.13/src/ipe/icons/fit_page@2x.png0000644000175000017500000000273713561570220017562 0ustar otfriedotfried‰PNG  IHDR,,)Zª3gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTEˆˆˆ‡‡‡ˆˆ‚–˜’ªª§—˜•ˆˆ‚‡Š„ÔÕÓÕÖÔÕÕÔÕÕÓÔÕÓÔÔÓÔÔÒÓÔÒÓÓÑÒÓÑÔÔÓÒÓÐÑÒÐÔÔÒÓÔÒÑÑÐÓÔÑÑÑÏÓÓÑÒÓÑÒÓÐÑÒÐmpkÏÐÎÐÐÎqsnceafidMMI”–‘¤¦¢¤¦¡£¥¡¤¦¢•—’SSO&&&888333222///555<<<,,,þþþýýýüüûøø÷÷÷öûûúööõúúúúúùõõõõõôùùù÷÷÷ôôóôôôóóóùùø¯¯¯©©©©©¨¨¨¨¯¯®óóòøøø   ™™™òòòòòñöööñññññððððððïØØØØØ×××ÖÖÖÖÖÖÕÕÕÕÕÕÔÔÔÔïïïïïîêêéîîîÉÉÈÈÈÈÈÈÇÇÇÇÇÇÆÆÆÆÆÆÅÅÅÅííìíííîîíìììììëëë먨§§§§áááêêêßßÞëëêéééèèèûûûèèçÔÔÓÓÓÓÓÓÒÒÒÒÒÒÑÑÑÑÐÐÐÐÐÏÏÏÏÏÏÎÎÎÎçç矟ŸççæÅÅÄÄÄÄÄÄÃÃÃÃÂÂÂÁÁÁææåææäååäååãÝÝܦ¦¦ÌÌÌååâääâññïääáããàððîééèããßââßââÞüüü€mÄ'AtRNS"-òññ+U÷øøøøøøøøø÷øø÷÷ø÷ø÷÷÷÷iùùf  tp Iõ÷÷÷öõD)-.1+&JËÞ1 pHYs%%IR$ð‰IDAT8ËÔé[Qplµ}ßKÛµÅö²ÍrÙ) Œe—ETB2t&+¤ˆ,„2û'»wæ^æ:3ïçßó>çž3Ï( 5Ë*¦F²|ÅÊŠYµáÚ5­w+¤umm ßk+J¹®ZLQ*uµXUûúª0¤­nCX­Vk¨óÔh0™Åøþi::>2,«w>–M§Éb³[ËAQð0#¬µÛmËaô0¬uÒ]ú2˜ßxWKw¹ô›ÄØÓÝÝÓÓÛÛ×÷¤ßãñêplcÙ÷ Bë“â!¿ß?<<22:žƒÁ ¾°c‹ÜÌ¥3ðãjŸ…CÌïK‹öE#ŽDd°h_./_‹J0Eƒãy>òÔF£1£SÔ€Ì2&@ídL„ÆÓ†¸ÚضOkÁÓÂ} ¸Z†aIü’Ü—P;Æ×²ì”MÀÛ”°ÖÝ®ëyõúM<ŸN$Þ‚¼{ÿácؤm»€Õ°v‰ïùÓT2™²í(áj8í¼îçt:ýeä+È7˜™d*•± xW»pšvM h*³ëÈë–öŲlÖf²Y'‰‰}Ik³³9šÀf´¯ïã(?øLsµ¹\ŽÞ-`+ªu‹6ñ“«ÍýÊÏ xUz<-¨Íç s{KxŸ}¶âi3¸¶P(ºH,®ÅÚâoï§p-Ãüö…k‹Åy;d÷…kçÿ.ø€Cz†YîaKâƒ*²–x_» àºC‡ë5²ûµ79 ì±ã'NÖÿÓñ1›­0ø·þû(ʆSM@ŸnÍæ‹åj½ ¶»}pXOß?¿g o!kó|Ü%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯tEXtSoftwarewww.inkscape.org›î<IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_lines.png0000644000175000017500000000053213561570220017537 0ustar otfriedotfried‰PNG  IHDRY ËgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTEßBÿÿÿ(L!×tRNS)4!UTbKGD Lò pHYs  ÒÝ~ü+IDATÓc`@LJ Hcœ%Ed]"HFÇA/¥¤„ÄS6ÂÅAQ†"Ÿï0{óV%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/fit_page_32x32@2x.png0000644000175000017500000000335413561570220020417 0ustar otfriedotfried‰PNG  IHDR@@·ìgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<¶PLTE………ˆ‰†‰Š†‰Š…ž¡œ ¡ˆ‰…‡‰„‚ƒ‚„€}{€|{}y}~zvxs  œŸ œxzu===z{w~€{}~z|}y{}y}{€||~yDD>ÉÊÇÈÉÇÿÿÿËÌÉøø÷÷÷öööõÊËÉõõõõõô÷÷÷ôôôôôóöööÊËÈóóóóóòÉËÈääã¹¹¸¸¸¸¸¸·àààòòòØØØ™™™ÖÖÕòòñÕÕÕñññññððððÉËÇððïïïïïïî·····¶ÉÉÉîîî¶¶¶îîííííþþþííììììììëëëëÍÍ̶¶µµµµÜÜÛëëêêêêÈÉÆÑÑÑÇÉÆÑÑÐêêééééééèèèèèèçççç´´´³³³×××ççæÕÕÔÎÎÎÇÈÆÍÍÍææåææäÇÈÅååäååãÇÉŵµ´ÄÄÃååâääâ³³²ääáÆÇÄããàÆÇÅããßââßââÞÅÇÄÈÈÆ §œË6tRNSªŒûû©ª ±° "·µ(º¸$ ûü2¸º»¼¹·š-\ŠÉbKGD8 ¥Ö pHYs%%IR$ðóIDATXí”û_ÒP†Õ, »b¥V¨]© {É),ŒÊJìbB€2‰41“ÀŒ2A* ¤ÿ¸íœmœíœíl³÷÷çyÙy¿ZZþKZÛv˜N[+&hß9h:»Ú1A‡˜Îí¥àŽ©x½Ûx·'àñ¡!pײòÖ¿ç³(F¼ÏgQ Õûîû­xüˆûýà¡iüëyþÑxLhB€m'áÁxmP0 ·SÕCa0hL ÜNÂCáˆ1~:<.ׇ#QM¹} ˜D™šzƒê#ј¦@Ã8£±i«‚0¬M'Xo@ß.$á‰çÑÐN>žÈÏ$u¬ú™dRO 8åv2ÿ6¥-Ð<¬>•Òx½ïÐö“òöq”ÙÙ¹¹÷b}j>Í-P|ý¨ÎŠžJ§ÓÜ"E/WOðQ¬O/ehövR}&C0O=¬Ï|Êcõó¨>›¥Ôõ´íd<›#×=¬>·¼¬,t:cŠéãüôb>KYù’Íñ|ž _ÿ•ý·þMÀóynU!Xèë ¾C~жÿ~Iþz_£˜§ƒp‘/íÓI‹§ƒÕ ®¨Ù./ñë%•à`ŸN³~}½¤^¦ÿÙÜæW³¾TÚ x=}¿•&^Ú(“±^ØŽ.øÝ¬/—+„ÀÐvR}¹Ráª*¼æé`õš@³>¯x<Ä×j*Á&PmG9f}­F0Oâ"_¯öé`õõúR@¯'á[[„@ýx9Úvxµ  m'Õ‚Ý À>G<.ØcëÜË (õÄvR=ìÛòÙ»7ûtp\9ÚÙ-l=½ÇŽ7àÌTOtÙÂoèë8yê´‡Ï_eVù±l*sæloíü‡óü…‹.·û’ѸܮËW®^ëï–Ÿ±ÏÑé´_¿a4vgÏMÛ-Èþ>8ÿ¥hÞ`tEXtAuthorAndreas Nilsson+ïä£XtEXtCopyrightCC0 Public Domain Dedication http://creativecommons.org/publicdomain/zero/1.0/Æã½ùtEXtCreation Time2005-10-29/¿%tEXtdate:create2016-01-21T14:13:04+01:00žÂ(%tEXtdate:modify2016-01-21T14:13:04+01:00tEXtSoftwarewww.inkscape.org›î<tEXtTitleJustify Centerûy<ƒIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_math@2x.png0000644000175000017500000000115713561570220017734 0ustar otfriedotfried‰PNG  IHDR,,„ZbKGDÿÿÿ ½§“$IDATX…íØMˆMaÇñÏÌÍšòz7Hˆ”,¤,0aÁ°¡D± ”’…%Ô°V”…,„ ‰¦¼,lX©± X°…±iFÍxYK› W;^ã;–Wð™†9X†¸Œ!ôN†Àr¬Â0^azuà>rU‹£Â0_ˆQg V7FN}ÜD÷4SDºð §aŸ0ÇOFì»ÐŸ²íqlÆO_bë¨⺘…mÂVš˜na}šF„T>¤(¸W„k{“êÒtt{cø/Òz9öà*ŽáÞã›âšhÃ!@‰8Ó1üçâ¦úöê<~ ‡¦Rîà°ç‘ݸV¥<‡ÙXŒ-…އqª‚ÿcaÎŽqI8 F£_±U•¨\Á|a!´ãMÑQ>C^‰ÁÂ{' Sí]ħ…ÅX––‚Ò°+°N8GŸÁÛIêûÿ££Ùâr»Ù2þ&$×O&’ëÓçÊó…«RÓˆ#xT˜}šøï!.5s}£‰{ ®™ë32222¦6 ›fh”ò± IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_circle2.png0000644000175000017500000000071313561570220017751 0ustar otfriedotfried‰PNG  IHDRY ËgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<-PLTEßBÿÿÿßBÿÿÿ1‹?R tRNS_¬àû{!’¥ؤ åbKGDf |d pHYs  ÒÝ~üsIDATÓc`À LÂRalÓŠ œíwï‚Ù\{@ä½·`Îr‡y˜s÷®d=ÑÉ$Ìa汌ÓÄ‘@,($¦q ) 6tŠ2PŒF±”ê^n$÷V!¹÷ô¨{Až Ææmì"º!$ÅÌ¢(%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/cut.png0000644000175000017500000000236713561570220016224 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTE‘ŒˆŠ…ˆŠ…’Ž‘“Žœ™’ˆŠ…“•›œ˜“• ¡‘Œ›œ˜ˆŠ…•—’ˆŠ…žš¤¦¢•—’ˆŠ…‘“ˆŠ…’ª«¨”–‘ˆŠ…ÂÃÀœžšˆŠ…ˆŠ…­®«ŠŒ‡›œ˜ˆŠ…°¤³µ ®°µ ª®­Ä°¤®XU®®ª¢¤® ¾ ™±³­ ¯Ì² ”•³ µ  Ÿ­ ¬®¬“©­¦ŠˆŠ…ÂÄÁÒÓÑ’”רÖââ⟟œ«¬¨ãããÐÑÐëëëÜÝÜŒŽ‰ããâàààØÙØèèèááá²³±ÅÆÃßßߘš•ààß’”ÞÞÞËÌËÉÉÈÔÕÓÝÝÝžš¤¥¢ÜÜܱ²°ŠŒ‡êêéÖÖÖ©«§ÁÃÁÛÛÛÞÞݰ²¯¾¿½—™•ßàÞÚÚÚØØØ³´±º¼º›‹¿À¾©•’”ok¶³±Ú10Ç:9ªÔÜá!!ÜÎËç%%É×±ï))â""Çã##ÅØÐ¶ µ× ?gtRNSǨ(qikP¸ª½£³«»G@*.T\ÚÖÛÞ× ý„EÌžØY:iÒä)S§MŸ!аsfé¬ÒâââÙbsæÎGqK)ÐÝ’Ró,”–† ËÈ})'''¯ ¨´HY**§¢ªV\¬®®®ª¡©µXªTN[GWW¯X Œµå jµMôMÍÌÍ-,--­¬mlíÔAâ2*꺦öŽNÎ.®nÚ2 a}/o_?ÿ€À àßÐ0°r9U;SsïP—ðˆÈ¨è˜Ø¸ø¨):v ^‰IÉ)©ié¡ñ–a&ª@a™ŒÌ¬ìœÜ¼ü‚B/SÓ}u¨U´ÕutŠŠLLŠtԵ倢EX]ݺüŒY%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_shear@2x.png0000644000175000017500000000102213561570220020074 0ustar otfriedotfried‰PNG  IHDR,,„ZbKGDÿÿÿ ½§“ÇIDATX…í—½JÃP†Ÿ+H¡¢CKS‘Vp±:t[/ S°…æ¼WÁ;p‹ƒ ^‚"Rü™êÿ$ˆX”Š„ãbE06=9%=Ï”Ÿï|ß“ärÀ`0þCQ“ °æÀõ><†éëµpâqp é°¨¼Ã4PÕée0|"|®ÙÀŒj#Çq¦Òéôxç<•J= …{Õ>±Xì¢Z­Þýzßo6°¡:¨\.cÛ¶ê²xž7( ²Ìö4$—ƶ“œž¶99i+*‚eA­6†\ºní¨[má% ÒÓÀÅÅpÎÎÎ3†ºðÜÜ–RÊzP­¥Ü݇……;Z-ÉÙÙ[¨õ¥R¼s¸T«-œË=‘É´8<|Áó¤òzË‚b1.¥äÊuÝãÀúP–ß(•n88x µ>ŸatÔ ·„O¬-\,FÐŽ: )u@S8ê8€†ð ⃈h"RxPq…-Òwúê*q€o¸_ÿB¥8@×7¼ì{5›Í21±67'Uç}!eð¯¤~Â7Àø©|~&Ól6M‰ÄC2™ì²ã»=: ƒÁ`0ü_>Ó¦¶­8ªqU9ãxÇÉw&â϶æv$ºG(¹æÐŠD#º 10CZ»\sn.5!{HbKGDˆH pHYs%%IR$ð{IDATHÇí”iSÂ0†Á*ZPñ¨'*xß ‚'¸\©ISJQÿÿ?1-µ4jÓfü¢3>3ït3³o²ÛM›Hü5’0¢È䌥d ãªÜ0)4LM§ÓéLÖ[ÍÌÌå%Í/€Çb2›Í8«%m9¼é•U–±¶¾Cò›¢|VÀÖ¶–+ó;»{,{ÿàðHŸ88ÑNÕ³ó‹Rù²P¼ºÖ*UU¯°=oJ^Â-s ³w÷9™!=<–d®3Ôâ U œ¾RЈK*¬K­íV»íÊÜ…O«š:0 éº+ýycFЀ‰(1 E&Â!BÜ F“.¢Ýð|Ì02£Ä•D‰EzB„3°ò±Xˆr»×·úBÙ_2"dò%Ùû÷-»Ç÷€£º@ÆÏÞ’ÿ¶ B §á$ôoGÑ z ˆ† Î߆|>b8lýËmuî+ÿäã€!&†f'&ožAǪԟâRw¾iE­–ãõ7üç÷ò—¾7ǤŽld%tEXtdate:create2016-01-20T14:40:38+01:00ãåÃS%tEXtdate:modify2016-01-20T14:40:38+01:00’¸{ïIEND®B`‚ipe-7.2.13/src/ipe/icons/Makefile0000644000175000017500000000244113561570220016354 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for icons (only for OSX) # -------------------------------------------------------------------- IPESRCDIR = ../.. include ../../common.mak all: ifdef IPEAPP ICONDIR = $(RESOURCEDIR)/icons icons = copy cut delete fit_objects fit_page fit_width \ grid_visible ipe keyboard mode_arc1 mode_arc2 mode_arc3 \ mode_circle1 mode_circle2 mode_circle3 mode_ink \ mode_label mode_lines mode_marks mode_math mode_pan \ mode_paragraph mode_parallelogram mode_polygons \ mode_rectangles1 mode_rectangles2 mode_rectangles3 \ mode_rotate mode_shear mode_graph \ mode_select mode_shredder mode_splinegons mode_splines \ mode_stretch mode_translate paste pen redo shift_key \ snapangle snapauto snapbd snapctl snapgrid snapint \ snapvtx stop undo zoom_in zoom_out app: $(INSTALL_DIR) $(ICONDIR) for f in $(icons) ; do \ f1=$$f.png; f2=$$f@2x.png; \ f3=$${f}_32x32.png; f4=$${f}_32x32@2x.png; \ if [ ! -e $$f2 ]; then f2=""; fi; \ if [ ! -e $$f3 ]; then f3=""; fi; \ if [ ! -e $$f4 ]; then f4=""; fi; \ ft=$$f.tiff; \ tiffutil -catnosizecheck $$f1 $$f2 $$f3 $$f4 -out $(ICONDIR)/$$ft; \ done endif # -------------------------------------------------------------------- ipe-7.2.13/src/ipe/icons/delete_32x32.png0000644000175000017500000000427613561570220017535 0ustar otfriedotfried‰PNG  IHDR szzôgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs  ÒÝ~üŽIDATXÃÅW[ˆ]WþþuÛ—³Ï9sfN3·¤M2IkmjAl1/…Ђ—§Ò‡Š H±"µ‚Ð×ÐB½áƒ(h-ˆF¨RMkµ­EJ›Ú6 šIfÒ$siÎÌ™3ç쳯ký>Ì…™8“ -ø¿¬½nÿÿýß¿×Úß&fÆÿÓÔvOÿÉ7‹²<øa‘RÎ|û[ß¿! ÚóÈ7…R 7ÊÒ•ëü“Œ]7{Žõ ;76uüñΕ <4<:ꢊ¬pˆã­V N­Vk+35Æ Ùl^µ4qÜ" Z«£14„v«õuOmb`ßOMÝsï'wë0Âô;¯`Ÿüû˜á\y–K%13ö9zàžÄ®•ÿ«ÒÈ¿Ÿ:ñÝ/­Ã| y×Ç=}ðàǾýÎÛ§Ó4¥ÃŸùìç“4M ßï§õZ=Z\\èŒŽŽ OŸŸºèy¾i6›ƒZi57?·P…h4ªF}n~örÇi„ÞK¯üýµýûöG{÷îÝ¡”¡ýðéGŽ{îek€ÊÒO{q·`lY*D^¥³Î­Þxdåz½i­u‘…B()¥µÖ‚Ù*¥X+-™Ù9ç¬ ¥”TRQU¼À<ÏccŒó2ÖtŽw3“¦•ÚA1hE›À Zi×±J6™(Mó0Ë‹ªã·Û†ˆªÌÜÝ€ˆäþýûù­»óCŸúô¨ç{QQ«z{C‘6'·òñÇ"eÃ"A¾ç‡çß;¿4?;/ ‘bæöFÌ™3gúûöÌ;7yùö;Œ@kµYE¹’ø¦p›—l~\áϺÒÍ\ší<û«g/=;Ýð€ ²œˆ€æÄmnÙuË礠›@ôÁ4ù+í^xï©ÉO¾   à"3g´Q„ÒÊ/Ž Š•rmxý¬úëH˜ÙÀˆâ¶Ú“ØÍ%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯tEXtSoftwarewww.inkscape.org›î<IEND®B`‚ipe-7.2.13/src/ipe/icons/snapint.png0000644000175000017500000000056013561570220017076 0ustar otfriedotfried‰PNG  IHDRÕkgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ< PLTEÿ€€ÿÿÿÿvn÷³tRNS@æØfbKGD Lò pHYs  ÒÝ~üEIDAT×c`@‚D900IF0 ,"‘g %ÁZÀŠ´€)ýX(¨D%TÔ¨™ öAm€;Rßj“ÜH%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/zoom_out_32x32@2x.png0000644000175000017500000000325513561570220020514 0ustar otfriedotfried‰PNG  IHDR@@·ìgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<²PLTE3fª-i¥3f™3f¤5d¥5g£Dr­4e¤Lx±3f£Kw°2e¤5c¦Dr­4d¥Ap¬3f£6e¤5d¥Yƒ¸Xƒ¸W‚·Wƒ¸W‚¸V‚·U·T€¶V‚·T€·R}µQ}³P|²Ly°Kw¯Jw¯Mz²Ly²Ky±Kx±Kx°N{´7h¥3f£4f£3e¤5e¤4f¤5d¤5e£4f£3e¥3e¥3e¥3e£5d¤4e¤¡»Ú¢½Ü¤¾Ü¥ÀÞ¥¿Ý¤¾Ý£¾Ý¢¼Ü¡¼Ü ¼Ûœ¸Ù›¸Ùš¸Ùš·Ø™¶Ø—µ×–µ×–´×•³×”³×“²Ö’²Ö’±Õ‘±Õ°Ô¯ÔÄ×ë¾Óé¹Ïç¸Ïç·Îç¶ÍæµÍæ´Ìæ³Ëå²Ëå±Êå°Éå°Èå¯Èå®Èå®Ç嬯嫯äªÅä©Ää¨Ãä§Ãã¦Âã¥Âã¦Âä­Çãž½Þž½ß¼ßœ»ß›»ßšºßš¹ß™¹ß˜¹ß—¹ß—¸ß—¸à—·àšºá¬ÆäÅ×꛺ߖ·à«Æã¾Óè«Æâœ»Þ™¹Þ—¸Ý•¶Ý’µÝ³ÜŽ±Û‹°Ûˆ®Ú†¬Ùƒ«Ù€©Ø~¦×|¥Öy£Öu¡ÕtŸÔqžÕoœÔo›Ôn›Ôk™ÓoÕ‹¯Ù‡­Öv¢Ðx£Ñz¤Ñ|¦Ò¨Ó|¥Ò|¥Ó{¥Óy¥Ów¢Òt¡ÑsŸÑpÐoÐnœÑm›Ñl›ÑlšÑkšÑk™Ñj™Ñi™Ñi˜Ñh˜Òh—Òg—Òf–ÒlšÔ„ª×Н×w¢Ñv¢Ñv¡Ñu¡Ñt Ñs ÑrŸÑržÑqžÑpÑoÒi˜Òg–Ò¬ÆâªÅâ©Äâ¨Äá§Ãá¦Âá¤Áá¢Àà¢¿à ¿àŸ¾ßœ»Ý›»ÞšºÝ™¹Ý—¸Ü•¸Ü•¶Ü“¶Û‘´Û‘³Û³ÛŽ²ÛŒ±ÚŠ¯Ú‰¯Ù‡­Ø†­Ø„«Ø‚ªØ†¬×V·aÜ`$8tRNSF‚HúIøKøLMøOøPQRûûûúúúúûüúúùùùùùøøøøùúý2™šª£‘ˆ€w|¤W]E>› pHYs%%IR$ð IDATXÃc`£`Œ‚Q0 †=`dBÌÄêc± °b5€ÍÂÒ ¬mlllíìì­œœ]\ÝÜÝ=<=½¼}|ýüƒØ±Àa aáá‘QQÑ11±qñ ‰IÉ))©iié™YÙ‰œØ à²ÎÉ…ƒ¼¼üüü(,,‚â’’’Ò²òŠŠÊªjnìðXÔä`Ó_ ÒÒÑ_WUÃ^‹†F¸v°þ¦æ–Ö¶öŽÎ®îžÞ¾þ 'Mž2uÚô3ù°ÀoÑ8köœ¹óæ/X¸hñ’%K—-_±båÊU«V­^³víºõë7lÜ´ió–-[·mÀn€ EÎŽ@°k÷î={öîÛ·lÿƒ:|ªÿHÿÑ­¸ ²È‚cÇŽŸ8yêô™³çÎ_È»xéò•«×®ß¸yëö»÷î?xøè1<Áa€°…ˆˆˆ¨¨˜˜¸„„¤¤”ôSYYY9yyE%%eU5uu M0ÐÂn€¶2ÐÕÓÓR†††FÆÆ&†`` ‘33'6u‚Q0 FÁ($QoÀü£k8ìtEXtAuthorAndreas Nilsson+ïä£XtEXtCopyrightCC0 Public Domain Dedication http://creativecommons.org/publicdomain/zero/1.0/Æã½ùtEXtCreation Time2006-01-04×¼RÈ%tEXtdate:create2016-01-21T14:13:09+01:00ÿIÔ%tEXtdate:modify2016-01-21T14:13:09+01:00ŽHñhtEXtSoftwarewww.inkscape.org›î<tEXtSourcehttp://tango-project.orgïâ– tEXtTitleRemoveg{;bIEND®B`‚ipe-7.2.13/src/ipe/icons/fit_objects_32x32.png0000644000175000017500000000255113561570220020560 0ustar otfriedotfried‰PNG  IHDR D¤ŠÆgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<RPLTEÿÿÿŒ‰ŒŽŠ‹‰‹‰y{wŠŒˆŠŒ‡rtoˆŠ…ïòñúûûúüü+T4Z‘½ÍÚéññ¿ÍÚ/VŽ%N‰ J‡(P‹´ÅÕ»ËÙ(RŒ­¿Ñ²ÂÓdƒ«ãëíêññj‡­)RŒ!J‡7]“OpŸˆŸ½æíÂ\|¦Dhšûüü"K‡9_”OqŸg„¬|—¸ª½Ðèðñëòò¸È×¥Áv‘´^}§Fi›-UŽ«½Ð`~¨Pq h…¬—¸–ªÄ¬¾ÑÍØáëñòìòòàçëÂÐܪ¼Ï‘§Âx“µmа¶ÅÕ·ÇÖâê태»€˜¸•«Å­¾ÐÄÑÝÛäéÝåꓨÔ©ÃäìîÀÍÚ¹ÉØíóó©ºÎ¯¿ÒÆÓÞÝæêßçë¼ÊØèïðÀÎÛîóóêïñÏÙâßæëäêííòóïôôüüüðôôñôôüýýñõõòõõéîðèìïïóôÉÓÞóõõïñóÂÎÜÍÕàæêîåêíÌÕàÀÌÚîñòÅÐÝ,TÉÔßóööíñó›®È˜«Å±ÀÓËÕàäêîãéîÊÔà°¿Ò—ªÅëðòÂÍÜu³d«~–¸±¿ÒËÔàçëïôööÉÓ߯¾Ñ}•¸c€ªp‹±»ÈØýýýIkœb€ª|•·–©Ä¾ÊÙòôõõööÀËÚ•©Ä{”·a©Hjœ.UŽ”¨Ãñòô—ªÄ_~¨k‡®íðòö÷÷nа+S÷÷÷¼ÇØÅÏÝÎÖáÊÒß0Wôôôö÷ùùùûÕ,6tRNS]ññòkóôr &8E69J@0 IGbKGDˆH pHYs  ÒÝ~ü»IDAT8Ëc` ™$q&F&)i\@Š ¤@RFää @QId$! TÀ@UMÔ5 B¨ 4@ ›m]ÐÑÓÇP``hdl•7153—ER`dZZYÛØÚÙ;€€‚£“³‹«PÔ¦@ÕÝÃÓËÛÇ×Ï?ƒ‚CB=ÂÂõá T#"£¢cbãâÀ !Î=1)9 E¦ 5--Í$=#3+ ²3srTLA>åÃA±?˜BQ_’` Jq¨‚²r\  ª €*¨¬Â*¡ ªA ¼¦jëÀLA}CCCcSsK ´¶µw©N˜‚®îžÞ¾þ 'õ@Àä)S§õOïéÔ‡)Péš1sÖìisæÎ›ó,ôY´xÉR}¨‚eÀxSZ¾båªÕkÖ‚@úõ6nÚ ]†P ²yÓÆ-k!`ë¶í®]*h TºvìÜ»÷¨`(PY·ö©`QÐÕ—߯MÊæPùƒ‡ ù¢€ùð(8º fʳ²±ãÌ›œ\@Ü<¼|üX€€ °+ÈQ.1q,@BŒK”³Œ#é}l}k%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯tEXtSoftwarewww.inkscape.org›î<IEND®B`‚ipe-7.2.13/src/ipe/icons/delete@2x.png0000644000175000017500000000654213561570220017244 0ustar otfriedotfried‰PNG  IHDR,,„ZgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð WIDATXÃŘYŒœWVÇÿwý¶úª¾ªêÕn·—Øž$ΰP2Ì$  ! h&“G4ð!^xÍ"ü„„F^<Á[$ò0d€ÉBd3‰;Nb·#··Óí^ª»«º¾õnθs”RA€8®Ýö$o Ø9k-ò<‡µöcƒí¤K”ÎÎÙO|ìKÇkYèÿ6F\˜•nØÁ]Ý x'0)%Â0ÜQ×9ç”!ÑÇžù6‹ÔÀ½rù?¾÷Þ-'žüÛ (홡á¡DJ/bœ‹ÒÎA+ªª`­…µÛ{b§Ih=°½•(¥ -j“‡ÿXmÌÂü\zè±g¾6óÂw_ÚØ/Ôד¡‘áÃw‹®YsÝneYbii ƘÛZº&Q¯×!¥Ü¢§”ÂÞÉ׆X£Õ®O¿3õ}÷mÖ¥›¿ÆÿdlïÞhóXUVèõzèõz×7Êí4Bȶãyž_Þµ¶¾ÞCUÞ¼ õ$”rïþßùË›RÝußõå?ßÃõz×ü2õÿGó¾zë=”E¹m8܉ŒA)EÚïbîÊëØsÏÃ×Ç'JfÎOð•­!áËßß»oÂãœ@UôQå=d¹çŸÿ7(³Ý!tg¿ÀÒµ«€sƒÄ  5<Š‹ïOÿÚäcϺüÂwgn&„<}`ÿ„§7 ü~åkßC  ¼#X;ËúFä@­Ñ Fø سo8wùÒ·üÑuíü/~1©%/é‘/$‹ÝÏogyè_¿ƒ¡ ?A6ðÚüúÍ=8õãÿé¹ÌLμô.Aå=r0®ôí%ïÏB‚²‡‡îÁpü ˜ÖèŒ!ýðNŒ}ãããlnnþ›¾?ÈO½k‚¥…þ¹—"ÂìW‘~þ—>ô0zx§qÚ8Üuä`D)ùc ‡¿z¼ÎÃxöë?RŸšYù¹œCcù0]¡×Þ-Àx+À¿ò©ôÒ×9*pM9²~wðÖø‰$õ[ƒ¥4.& ÎáÝ%X~éÕãÅÁÇþúÜì•«¿|ÿd ;űÛÈÎÎ×µƒ»>ÁACg³þ 'lÒÇœ¼Õv y¡pu%E‘3(g ¼z\s Ðß|åÄÙWGZ!÷œÃuj礠ÒZç(a0Î:8J)3Öhkƒƒe”B®ÛS眡”rm¬bŒcÜ ×VSB˜¬`´Q×ò¯s¡Ž*el·_èåùë¬ûS`SæýòßD‡ê+üî#w{nn–jë*ƽÊMî9ú¹¤¢Ýl%KKK0 #ç¬ÑÚ˜( ƒ§~òÞþÂçO¿sæü/Üwÿ‘sÓïÏîß¿odee¥'¥àRxrqy±wpÿÑéóïÏ»÷žSï¾séÁc÷í?;=={`rrô…_<ø>|`_½ÕŒ½¡öPíĩӗNL]ø÷KÕØóüàÏ.›Ž…}+ý'Ÿ|{røþ%¦D’åyx6(†BµvàÀÄ%$X ÷ŒûóóóW}?ôÛí!oñrP™HðáŒî™HHÚýí;{®³¶ob|O·»ÖÛÓÚCk‘Lí¾ØÞÛp½%¿82‘îòŽŒËS¯y½.‹}C^Çnùz8¬–FÙÕ·_ûÁ?\¼ÆyÓ匭º¡ª9çŠs®”V…”RTJU”2G)£ZkÅÄõX@U”PJ,bŒ1»ªô¤Ç•ªª0©Rªò¤g@J_ IÒ²aq\ÓBrÍ7ÚšÌR’mæ» ˜1戣«¾ïΘaœiÆ™f„â(¥`”ZçcÎZ« #1Ø6V niЄ0εsÎrÎáœ3B zÆ! †˜.)ýÀ¯‚ pÒó´B[cúÄܸb•3Fw|ßaL .”àB5’Ä·Ödz=à‚[Êh™$‰§ÉcžÕ"H)áy!*Žci­I›IÓWZ¥qܬ³YE’ ¦¥”ð=ßB”µÈJƘa„˜4Ë JõÎÀžõв,Ö¼À#œP#„P„“4›>€¢V‹=)¥µÖfF#¤”()%/$òfÒö¥”¶V«1ëlÚnµC­u¿‘$¡±º_¯×F™’R" BÇ9·q3kM²ò}ßp) ç\SJmžç¥â·ð0ç<ׯ¥œ K×B Ój¶âZ­ÆW~@´Ö½$iÖ¢0¢Î¹, ¸bdd$ÒZ§ív+ªªª;2<Úê§ý•¤Ñ¨Á¹Êó<êyžãœ»f’J©n½Þð”Ö}Ïóª ôcÌ0Æ eÜdY¦YÅv.Š¢¨ª²`”YΩ–R(À™fÒŒ‡††“Å奙F# ѹçylxxdh¹³|‰s¦¤ç¹f³Z«ûI£cÒ8Ž£µÞÚ²”©Õb&„@Ä9—  ×˲XåŒ*ß÷‰BAl9cFráqz}=µcccéŽÀÏ=÷œ±ÎœQË5Bíœsq=–RJöÖ[ož3F•Íf³~áâ…éÕÕÕ«µZ-ƒDy¾Ç‚ÀçB¬®v1E½^8ç³ P$©WJõ{ëýN»ÕVÚOJPF-—’ÀÚÒåž}öÙrG` –\Í9×Zi÷Ň}8ðÚYé\¶ÐK”q"=K)Ñëõæò¢qaiþ¼‚xžPÆgaúÖÚ²RÕŠÖ:¢($„À“‚0B\F‘ÒU¾ÚíÌK)åäÄþ OJ"¸Ðž°Öf„-¯9[€+k ÎÀ•Òlxdd²( wåÊìL’$¹ÑFK!œ;÷îOÇÇÇúI³Õ]ZZ<Ï9O8çT­|Ïúi5ŠjEo}m1 £!k-œ¦” k-µÖYÞ¿TÅúçŽÞ},ÏsÉ83Br¢µÎ8¥Å®À È Ü††ÚÙ©S'_^__Ï)%ÒZ‹²,ʲªl¿ßG–çcÌ…¡oμ3u’1QB[EžW„Ð`½×ëo–—:‹UU)¥´Ö „„J)h¥]ÖÔÔÛ§ÿ÷Ç'^ÿ¯v»i€PÎò,+ aùGñ¶T~L‘ŽÀQ:˜Kgmiæä'~´´tõƒ8ŽÝÌÅ ïù~Ðx{êô¿”ºœG“ó?˜9Õ¨'{Þšzóµ¸EZk#·ç/œš¾pîÜ÷>ø«s ó kÝî‹Î:t»+k~¸åÕ…·'&ÆK)ä$kIY•Ì¥»÷UUÀZÍ£ÆXÒn·K£Í™½{-ôÒµ“Wæ/ ßóMkxôzŒ…¡of¯\ziF+Z©ŠJ?É™¡„1æ¢(êÀìüåæiʹ 8â¸ܶÛí!¥®¬´¶ÊöwÎ×òŠrÆ q„1î»Qö}ßø¾¿mù§Þ¨ß´I6Û]›TÞ°ý¨>|Àc-ª²0† ·k w:ÖTœs®µùL«î[`åžvi–ëJU[Bb p𦯒 &ø6[ò3‚p@–¦54û¨Î¶õá²Êú†³~æ¥o¯èý)…1F+Uy„Ç™à½^ÏZ›oIk…ñÏŸ?ß쬬šfÒj/./®*(sw,48lÛq!DQ”!ĵ’¡±µn7˜ž¾¨cPröÔWWWã³ïž%?þĤƒC#®‹í€£Ô¹í‹kü¿í$„ÀeYV1Æ£4Z¸zU,¯-û¼Êõ¸ÍÀ¿Óé˜Óožn?úèoV{FÇ÷ôûëùvÀÚî\%2Ÿ¸c…'C™å¹ýpnžw:@ Â ÄWl‰Ï4Mm^–so¼ñÆå§¾ñÔƒc£cCw2$n%eQ•/¿òÒôòòòE¥Ô¯l¾6‹ìÍ7ÞüOÊ)ë­Ÿ.ÄqL­µì¶ÿõSJ¿ŸVËË˳g¦Î¼ opUÀÖ¯ †Á2øI’DQùιŸp–eÙÚÚZ¶Xl@÷±QëØi©=Ã`~–ˆÙhzø¦Sõÿ”V} yhæD%tEXtdate:create2016-01-20T14:40:38+01:00ãåÃS%tEXtdate:modify2016-01-20T14:40:38+01:00’¸{ïIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_arc3.png0000644000175000017500000000073213561570220017257 0ustar otfriedotfried‰PNG  IHDRשÍÊgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<HPLTEßBÿÿÿÌÆjÁtRNS?ŠÃéü¨>ÍXÄc!ïPÅð= CfbKGDåØù£ pHYs  ÒÝ~ü_IDAT(Ïc` '`dbfaeeafbD6vNNv6.n„„˜˜(ª2ìp’d &^TgÀ”ññsbw§€ qàÁ!!ŽCÕ©È(ž#J—QæF&jëDz%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_rectangles3_32x32@2x.png0000644000175000017500000000205013561570220022047 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞbKGDÿÿÿ ½§“ÝIDATxœíÚOheÇñO›’VÔ¨Á jƒ-ZD©`Õ‚µ/zЃÄ?ôàE‚…‚¢UP½ño½¤"ˆª¢ µVÚC0 Å–&1mª1ÙŒ‡wÃÌnvÓÙl’Î^Ø—™÷™çùÍû癇¥          à\¤+ãøÛp Žåà˲äGDø{pÎk«G‹H?f’íÞÀXÕ.烧̾ºâÜ‹žö¸Ù:¾ú^–B=1Nã<€ Úào®\†’Ø¿¸0qíÃ^|#TAÄ#¸2ųwwp&•·U<$~[_f1T¦Wâ]œRf ¹Æ­èœq "JÑú²:üq©dz«¢Û1ÆÕãxùží³|»˜¬ÁdÙ‰Yé¦^ZV ™å!¹ª)Æ÷Lg mÚºM¾Ã<Sø¢ÜžÆÍÂRÙ!qZ”ªcع“u‰“u×.FGssê}±úÏäf5Ø„Ý8z ú <UÐߟÛX¿Å\“K89ÅÏYè¬g¸[Ä)ì/8’WY8?ã‘–fØ‘ø=˜å¡-e`€ÞÞ¸òd.f»„£gnúߘ‹ÕÈš4º6‹ã§<ƒh'D FLU·öM çÒ W%®]ß·ó£zX¥F^Þ¥¢x˜ì¦ÙD[Åsè{‹[¾âQèå·WC¢u-E|šr=mhA@Í2(Þ£žltЧ@W‰ÆR)„½ôXƒ­‰þ'\x  1=·›ô¯ålÅÚò!–Â΃dŽòQš™ØÂ³Ú_þîÆ=‰þ‡i/¼LN2>÷K¥ŠËǹ_hcÂWÛÞ²§Ó8‘‘Û…*¡‚t¸iKiO µ¿ÑÏe¬UV‹[Å›‰gd²”V€m¼náò÷ŒÖ–¿;UKnÊd-CЮò÷æ„ýaÍyc"ÞŽø3E»¶†™õ¯üýrÂÞKÍȦØÙÉ\þŽÂ 3RkÐ úJå´übF»ùG;ÂÌXr4UþŽèN¹,›?‘†Ëß=¼·H²`ù»;]ðËR€$]BbóšPrŸ/@ooMLÄíðá%@’lZË‹óH22²bó6ÁœX)_ƒM³üþÑ56Fg~ïmù €<«RÅh· áŸ÷§¹·       àÜåãûu‚©" IEND®B`‚ipe-7.2.13/src/ipe/icons/copy_32x32.png0000644000175000017500000000163113561570220017235 0ustar otfriedotfried‰PNG  IHDR D¤ŠÆgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTEЇ‰…Šÿÿÿïïïííí–™”ŠÇÇÇÅÅÅëëëÃÃÃéééýýýûûûùùùççç÷÷÷õõõóóóñññŠˆ‹†‰Žˆ€€€ˆ‹…²¸²‰ˆ‰ŒˆŸŽ‰ˆ‡„‹„ˆŠ…ÿÿÿïïïðððîîîÇÇÇÆÆÆÅÅÅêêêíííìììÄÄÄëëëÃÃÃéééþþþèèèüüüçççúúúÂÂÂÁÁÁÀÀÀùùùóóóûûûòòòõõõøøøáâᇊ„†Š„ŒŠ’••˜“‡‹…ÐÐÐÎÎÎÍÍÍ•—”‰‡½½½¼¼¼˜š—öööñññôôô÷÷÷±±±’”‘ýýýóóò¢£¡ÃòzÕ"tRNSi€k€€€êÒ€€€€€€€€€€€€€i¥ð î+þ¾ÔèM„vÛjbKGDhÙQ pHYs  ÒÝ~üTIDAT8Ë¥“[W‚@FÍrJÔÊŠî×I@qÐ2S±Ì®j×ÿÿS:3Œz0V¶VûõÛìyáÄbsYˆG°ˆ„øRñøÁB"…eÁŠ’ÍE@Qæ´Yò‚'fw]ûµ H „ çS Ü IEQBøÚ²ŠÖX $3€„TjúÔ £T²m[ „(étz\ŸÃlN„'Æu˜$d2â Y/¦ã8!¬òY¨Îgש aMì à:Ì.s=!¬s!›¥9Ë’õr­V¯×/˜s)„ > Õ]Ƙ©¦ØAÀuÆœ¢Ö¸–ª&ªJ+“v×Ö›×­v„my ´Šë¶ßíÞto{èߤ^¨îßõï‡,´BõÇþÓóËî²n G¯^¥Wz{ß?À7JÍa>?lŽ-ï£úÙû:<:ñIè :þéÙüÃç|‹„avîÚÇ—%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_math.png0000644000175000017500000000052413561570220017357 0ustar otfriedotfried‰PNG  IHDRÚ¹¯»gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTEÿ€€ªtRNS@æØf pHYs  ÒÝ~ü¸åîòÞwÉ{á á¿ÓʘïVk$E6v©`„ºd—92›"Æ9´^Öâ9 p]‚À=0ÉZ¼(!@íy]p‚¤U}£YÚ¶à£r}òwÍü ðMƒÙ‚Nú}ð<ënžË%ŒÇ5 $ Ìç°Z9 ØÔ@Êz ƒSr[-iÁ³ø}«W{µÿˆþ®€À•@ðÃx%Üæ={¸}9 ¢/?÷+Â6éeŠg>(¾q 3]óœRÊ08œx4 ÃÂo`D¦'>Fîˆcˆ"˜N]CšQF ¸ò ¼jæß*ÌÙ`Î7î£]Z¼þIEND®B`‚ipe-7.2.13/src/ipe/icons/snapctl.png0000644000175000017500000000055313561570220017070 0ustar otfriedotfried‰PNG  IHDRÕkgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ< PLTEÿ€€ÿÿÿÿvn÷³tRNS@æØfbKGD Lò pHYs  ÒÝ~ü@IDAT×c`ÀDC@$££ba``c ‹(§@, “‘k˜â~€LA!ªQôÁ ƒ µj-ïÛ¿ûÁ %tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/stop.png0000644000175000017500000000262113561570220016407 0ustar otfriedotfried‰PNG  IHDRÄ´l;gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDùC» pHYs  ÒÝ~ü†IDAT8Ë”[hTW†¿}ÎLæ’Lâ µµjH[M œfÄ •R ¾DÄ”¶ØB)¶T‹Ñ•ÄzúЇBû¡PA©­¶ ¥(Ú‚¦sÑ´I›Û83Iœ™Ì™ë9ûì>Ì8šD¥ûaïóíµ×ú×/xÆw–âG"-`?iã©?„/|*@>i_&༄wZ@ý/ðI8]ÝÐðÑÖ¦&·îrRÅP¶ –…•Jñs{{f°¯ï{ {fÃç€OÀ™êúú¶íÜéŽ÷õ‘ÛÛÎC¥DI‰{Ñ"æ¯YÕsç2C½½ß}ï>ÎÑgA¿ª®«{Û®]žx_éP! w+õhU Ë0° ƒšúzG4¯~-^Þ?ÌŸ€¯W{¶77{b==¤#bR)\¶=£†L—”àˆÅ0“IÖ¬_Åjj'&–vÀOEð øvµßß¼}÷nOôömÒ‘Q·QUEÆ4±³Ù"Ðt]G‚ôýûPxº×²9ƒ‚e*/Ç(-ååÖVœ¥¥üuènÓÄ(¥0ÂatMCzá(êR©|ç…¥¨°mâSSOŸfÅÁƒ¼xü8º¦¡)ÅÀáà âËåPJ¡”ÂV ¤,6Y{¤xU”ÓCI•çr09ÉÔ… 8=œ^/‘‹±ÆÆŠPÛ¶±Âå£Yr<ƶó™kùûºŽt»YÜØˆ&ð\c#ñ[·°¤Duw#MÛ4Qš%%ùäæd,e~¤$/;†³¬ŒN¢oÿ~4!¨9z”©ñqâR’ìé!yïF?rxÛ4g‚B•”d¤$9o«ÚÚн^þnk#ÓÕEôìYúÁér±±½ŒËEм 9/Fù|3K!¥ÄDLM‘ ±L6m"qó&÷/]"wý:¥££”‰Ë—éÖ4^hjÂUQ•7$t— ±téÌ‘ÞfÛÖØðpݺ†g.!713‘àA8ŒÁ30€]hÓÓDïÜ!—LâŠFÉŒàY¹’ª@€ž7ÌÐääíøF耫u©”Û¸nófgÎ0ȃhCCè¡PjÂ)%¹Þ^²##”VVRp§·×üóîÝ?lx½¬¢WtÀÕé´¯÷××;sÉ$Ùx¼SOXË*+YY[ËïÙþ±±_mx³²sÜ­®Õe2æh0¸É8s™ Ùtt¥ë i¨B”WU±ÜïçÚ/¿d†b±mx»¬§ù±Xò1|Vãó}øÖ† %Îùóeeyñé*˜“––Í9R»,Ÿ•"t%1)f¨m-’¢ë’ë²%‹ÙÌ*±tìÌ©vO¥žv¥æS¹¼Aç¯ö°õ°\þù¬\ÞzN=¬/õßÀ¼ýEN1I pHYs  šœ IDATxœìw˜ŵöU&ílPBH$I$"ƒA$c \’-.þ°}Á˜dƒÁ€ FÁ¾¶/á#‚Á&øWˆd²DY€@q¥Íº«¾?ª{vvµ’vW»Ó«aÞç™gv{º»Îôt× uÎ{ ‚ *¨ ‚ *¨ ‚ *¨ ‚ *¨ ‚ *¨ ‚ *¨ ‚ *¨ ‚ S§N•³fͲµÖ®Ö:¡µNj­SË–-Kk­k´Öƒ‡455 ÓZoôúë¯;QË\AßCD-@Tð‡lÀ ^²è=|‰àþ_¼¿|À ÞU°M¿ü¢}Âý74­µýùçŸ[®ëJ)¥>|¸ èÚ577Ë¥-ˆ»^ÎX?Ù·*¶ym<Ä‚}  †µÁçÕÀP¥Ô0!Ä0­õ`!„%„Ø_1+Š/[AÿÁŽZ€ *¨àƒà½l l l¼o„QHC:Œbªª€DÆò X4+€eÀR` °0x-2@>xå€,Æ@èsL:UN›6­Ø ±«¡¡Á®©© +ؾ¬l6+c±Xìûþ°Í7ß|°¢F)åq`PðªK&“i'ï»ÚÍÇòž¬Â(öx(ƒÖ!Dá½3„…íÁ~[j­_BäûãšT *@TÐ×@ £°å=ØØŒ ÞÝ^œ_Óuô²x»…QzÕÀ&Ý8ç2`>ðð1ðaðZ´mÁ{6<àõ×_w&Mšä`ÙvÛm›·ÜrK»®®.¤•RC¤”µJ)7™L¦€ÚX,68žñë,!Ó¾P.HKkíVèyç/(îP‘ ¶+éP!wùåÃý´!ˆ;‚º¤`qƒ_¼¹§×I(¥6—RÆzp\*@TÐSHL¨y0ÆKÝØ˜Œ >)ù(s‘Ö¨LµÖh­«ZZZvliiÙqÑ¢E¼òÊ+ 2„ &°Ë.»°óÎ;3zôhjkk2dUUU…ãë’ž†•­š¤KgEŽRJ ƒ®+ Á½¯óZi!ÌÚ‚€aUKšüàøžÚYíRŽjkk‹¯{Ï 6$T € *¨ ;HÃ׶ÀîÀåß]iš *á8ôлÂòåËyúé§yú駨ªªb=ö`=ö`çwf³Í6cøðáÔ JUL²¬Ùgd­µÚy¤”ýrM“JC«,>^æÞÿz ·eYÕ} ^ ‚ *XÒÀfÀÀÎÀ^ÀÞ¬žŒ×YáoPʾ·£ÍÍÍ<õÔS<õÔSŒ=š}öÙ‡]wÛµób£?bK„”%½0R@]Â"ã)V¶ù J®n„tÁRDZJ¹‰Öz^° QA bTPÁ7Zk¹téÒä°aÃR@âù矯¾çž{F}üñÇ[~ùå—–.]:©¡¡alW‡Ò®è¿ ¿3Š£¡w­µfþüùÌŸ?Ÿ;ªšA<¿ÓÞ,™;™Çg«­·fÓM7-‰|¨N˜å€¥Íª×@Q"àVüñ³%BV°aãùàVPA9@kmd“766ZÕÕÕ6¦Ô+‘Ë‘8çá± ¿[mÕűÇIxž—²m;áû~°¤” -„¨{饗6Ÿ;wîˆ×^{m諯¾:xÞ¼y5Ç+N^«`íèêZ :”}÷Ý—½÷Þ› &0~üxêêêúUŽ•­>ÿór3“6‹1yËõ^¿~ÅŠ¿2dHc_ÈVAô¨D*¨ bL:Užzê©ÉaÆUe2™ªx<žÈårŽëºò<¯Ê¶í”ïûI˲ß÷mÌš|š >¾ªªÊÑZ»Bˆ$¶m•ŽÇI´å°‡¤,Wk²m;­µN‡%dõõõ¼ñƼúê«<÷Üs<÷Üsd2™5ÊYQþÝGW×jÙ²e<øàƒ<øàƒŒ=šýöÛ=÷Ü“wÞ™ñãÇ÷µ€ f êR²¸¦ºÿnbìàÁƒãn… Ê ‚ ÖS§N•gœqFU<OZ–Çã–ÖÚ½wNcre³J°[:•ŠÙ1ð,ß1˲’Zë*¥Tʲ¬8&c>T)¥ªãñxZ)•r]7$ËIK)Ó@µ”2t¨ÑyR—RR³hÈh6ë”}þÑG1{ölýâ‹/ŠÙ³góù矯v®Š²ï„×6\&¸ë®»Øu×]™zÇTb‡ávÚ¶í´ïû) .¥´”Rq˲ª”RURÊ$†Èƪ­­MI­uÒ²¬¤RÊ•RÚ=eYV:xï0¶”r5¥Y“°Èzy½zص˜ðE)¥;—ƒuet…Âý‡¤,–6äyô±§yò‰'xá…xûí·W;oPïÞ1*èCt& £?þ8»í¶“'Oæ°Ãcûí·ïõR@MÜ"ëÊVÅFéÞ%°J)·˜:uê¼éÓ§«^ UÁ€AŨ RL:Uþ×ýWlÓM7uíêêjC•2Ë¥<Ïs„1˲Ҿï×!j1!ñæN©D"‘‰˜åºŽ”™<1-dHJ)ãBG)eYFƒ;kd`ÕXÙ`ÍYßáÿ¢×€¨KJ2ž&³6ùþªÏçó¼3û!žú±ü“×øì³Ï:È^Qú#@+W®ä‰'žà™gžáÑGeŸ}öá˜cŽaÒ¤I=>·ªã ,mö×ÇÀ¶ííN8á„§§OŸ¾æd‘ 6T € ú J©j!Ä {_k©kóTõãîà*;®µ®VJÕ5–eUÑÞ&¡”Ja¼îDuuµ¥”²‚Pz£Ø]Û¶-­µ Ä-ËJ`à:hèâIÔµLòSk¾½RmMáõðpºð ;cMMS:ý-Ò1‰¯5myÕYÔ~…RŠ3fðàƒò¿_eÙâEä«(þ‹5-üûßÿfæÌ™ì³Ï>üñì´ÓNÝ>§‚TLP“,mòaãžó.‡§ î étÚÅ4Oª`GŨ€Y³fÙ&L¨ª­­Me2™X<wr¹\ÜuÝÏój…Õåë™è5˜.mµJ©`ëáq Q›‰Uõ:¦ƒŽfBˆ˜"(v—ö¶¥«q‡áô5…Á‹? &$-¥ìäÌ ¶ %§Pt] ÛÐÇH8¦þº-§{;áö>ø wÝuo¾ù&‹-ZíóŠâßpPlÐ*¥xã7˜3g³fÍbòäÉœtÒIl·Ývë: ˆY&di³‰Ú‹¢¦½ÀD×u+=Ê Œ µ–s?_Uý÷Ä Lr†l=Ü­; ¸¾ï×H) !+¥j¥”U½ÁµÖñ ÓW"Û€t]×\˲bAy™ H!„´ !¬âNd`2S® ¯4ŠvEÝUDz.}H8²ÆïØYwÞ9wÇñ<¯FQkYVïûi˲\¥T\JY¥µ®B„½ÒÀZ›tÒÉÖXs^Æ´¶\ЖÖZ !­uLk ÷…vO£«5oX·‡^ì…‡û$]IÞUp¿»ôº» ©¯·š Ï™r-Y]ˆ¬ŸÓÓsÄAÂ4dýåw¿ûî»\qÅ<÷Üs|ñÅ…í•2¾òBç<Ïó˜3gï¿ÿ>Ï<ó Çw§žz*±XGÇ<¼ß-µqIsNÓ–×$œõ~†_­ïI*ˆ –’üèWÎO¶¯NOé ŠÅbƒ1]ÓÂþßÕJ©!ÀP)åÀÇ:BW)å*¥Çq¤RJÚ¶mc¼tDz,RJ©”²¯Ü*ž ËÂO B<ĺְïÂ:ñº¼ð¤+ð”ÆSá>¥÷«’å-ª CI‡Ç–fíµ¡UÑ׺¸¹¹™‹/¾˜üãÌŸ?ßo¯ñ®¬ñ—/:™L†×^{?üGy„3Ï<“#Ž8bµã¤„š¸ÄSPßê3²¦×Ó~ø o­µ~Oá÷öD T €"h­–––Á©TjH>Ÿ¯B¤œk­ !ê”RI)¥£”JH)ÓJ©j ÊWÄvV%¿nÖN–ck­í°¸”Rh­­à8G)å!dç0xèq‡ÍÃíEr®öYØZÔ±AHMÖ7áo«“ß ¬·ªLº_ 2ùÕ#¥BmBÒšo7Bú=ßf¬š˜¤!Ó·€»îº‹k®¹†>úˆ°Ž¿¢ø¿Yèl466òì³Ï2oÞ<xà.¸àÆŽmoß … —XR³¬I1r5’çnCóÕÎÀc@ÅØÀQ–€Ö:•Éd†Y–5Èqœ!¾ïªƒ$¶*!Ä`)å0¥Ô0)å`L]V2™´Ûq+ðÌ •R¶”Ò ”xa;f]\H¡q,‰¯@éŽáóbE¿¦p{ñWXÛBxW…!xרBóLø{ýŠ~z‡”+n\OêÑ^£&&Éæ5y?#D P“,]ž/ë³ 1oÞ<Î;ï<^zé%êëë Û+áþo.:/Å-]º”3fðòË/óóŸÿœ_þò—8ŽY®O¹A%@sH Üû{Q)µ«¢R P(KÀ÷ý£âñøEJ©AJ)¤”–B*¥„B‡ ]Õp¯q:TÚk"t ?³%ÚSZxh2º«‹KÉz×8– ëi|N@ÂH!hËFH-§ªâ’¼2@©×ÿýOMBš*€@?÷v)ä²Ë.ãæ›ofáÂ…¨`M£3AßLtæð}ŸO?ý” /¼ýë_\zé%ì¹ç^ÄlÁ „dyK¸\Ô»{1˜#'544”¥îø¦¡tÊ%DÀÔVxúƒ‹ˆcÒRÊ”"!¥tBå*Õ^¡X¹Çm!ò>xëÏJÇ2¯œG_zÄl%5Y¿ï׿»‹„#P2ž†~KÃëáÝP—d}Èzax¾gî믿ξûîË¥—^Ê‚ :(ÿJÈ¿‚b„÷C8e³Yž}öY?ü¦OŸN>ÛF]R²²U±>ËaÁ=W]SSS©(”¥ày^³Öºu]^w§ÏûÄGtmià"[3€¼¯ñ#Ò¶8RͳZ~©p–€L¾Ôê¿Õq¯0¥€=Äe—]Æa‡Ö¡C_Åë˜XgE(Ždj­©¯_Á´iÓ8ü»³è£9´æ5M™Þß?B­µ&ŸÏoNÉ=ô)ÊÒZµÖm¥(ÍXŽž—J ×ä”.dÀ—B˜(@ÎבqÛB-¹è¢é˜D iÎvÿ‡øàƒøÎw¾ÃÔ©SY²d Ð11´‚Îù=!lj,ï%DçhÀ‹/¾È™?ü.Ï=x#‹W¶­Ïé…)åN³fÍŠ"Ũ‚>DY¶m·ÙR>„Z›±l ¾Žj ÀŒ³Q.C$\£|ýˆ”–m ’® © 6ÀR!X»Y pçwòío›'Ÿ|²RÚ7ѹGkM<çðÃgÆŒ,Z´ˆK.¹¤ðyÔèœÐÜÔÈc=ŸŸp\ވޜײ¬=&Ož\ÉØÀQ– ÖgM¿7çÇ28~àôE±úl €v¢@Ò‘´å‰, PåJš3ÑEâ¶éIИYûE¨¯¯çŒ3ÎàÄOäË/¿\MÑTPz¬)¬/¥$™Lrä‘G2cÆ –.]Ê#<±Çˈ#8î¸ãøÿø5ž' t¾‡žù(ßúÖ·xâ‰' †fO|§]/^\‰là(W £µÎF1yº–DiÈngIÿàë&~÷Jº –Š Ú"Š„C¦c‚æ¢@)E “þŽ )«×ø#¼ùæ›yä‘\wÝuxžW õGˆ® /)%¶m“N§9æ˜c˜1cõõõ<üðÃ{챤ÓéçØl³ÍøÍo~Ã&›lÒá< _~ù%‡rW]uMMMkܯ£øþ»ÑFU € eih­[)ñ@ˆ˜mÆŒ" 0X… á€ç1ñ•p /yÊ1D@QDBBªã’Öht‡í¥‘Á –^ïûÜwß}üÇüÏ?ÿ|e?"t¥ômÛ&‹1xð`¦L™ÂŒ3X¶l<ðßÿþ÷W£ÜíŒÝwß½°ÐyŒ†óÏ?ŸN8a=$:ˆ® = ´Öš¶¶¶t—U°Á ,×p„­BˆHH*bÁõ )ø¥c  G‰;_‰ö*€¨x®‰BjàK]Œ¤â‚ÖåÅK!¥¿5 ÉâF¥A—`ÕªU\wÝu\tÑEš½TP_ïðÝq\×%NsàrôÑGsÄGt‡´«Kyä‘Ì™3‡?ÿùÏö7ez衇˜;w.ûÛ½L˜8˶¡(h¥µÉkR |­ñ"ï+šÚä8LO€õÅ*è6ÊÒÀ0Te£8fKà‰h¢Jë¢$ÀÒËr¤ID,ˆPzªc’L^‘/Dc¢¡$þdyž¼§±]øì³Ï¹øâ‹¹ãŽ;ŒDP1”;Âëíº.ñxœºº:&OžÌ1Çá‡Úk¥_ŒÚÚZ~ö³Ÿñæœ9¼ðüóò7.–iþüùìý­½¹ðw°ãÞ£dœLÞ°yf<óÊú÷LdQ)%Åîß¿ÿþ§˜2¥B ¼¢, €†††|MMXÞ%uûì`U,Ê |×h çE'C*f"Ù|t2Ô$$Y MiVmÂ"“×d|ͼ7ÞäœsÎaöìÙ•šþ +ãÊv\ªÓU 2˜o}kŽ>úh>øàPé °Á¢, €šÓíb}iu{Ç2zQ±ðn𫆠tQ(¾¤+ÑZó*2Ò1CʔЪM²9Ÿ'žx’‹ÎýŸ~úiEù÷#º ïÇãqª««IÔ c“±»pá)S8ðÀ1}¾zrîÂ_…mÚ „6o(mÞÃÿ÷ÿöw9õô_0í¢ ×÷«• Ýz1iSÒ¸ñƯm×ñ#vÚ©,óȾ)(Kóüù@É•OÌŒ÷•â‹Û†/ëEÇÅŸtRi?€tÜ!OG°úo Už÷_x˜¿üõlš››*!ÿ~@WJ?‘H0hÐ 6Þxcvß}w;ìpÜQ{ñê‚<ì_ƒ-;ÕôÓQq«ÂK”ºÒ&ŸÄSàí®=yß™™¼&“Wd H–(oÇð8ÄmAM\³Íß Ç¬…'sÛvûþ¡Ñ¹&îÏ ìYüêì³iXµªt«—£—ï¾û.Gy$wÞy'ûí·_ñ.BïûµÖsKM¼VAß , !„¯µŽ„À–&üîÞAÞ·-Í+ï‡K„¸¶ ãEÕÈ|ç”+hζ—#–âj,]º”«®ºŠ+¯¼²ŸGúfÂM¤¨¶ µmÊ&[ïÄè û°Å¸=‘R‚÷+©pmc™e¹T\28)YÞ¬5ØaÇ‘.–43qGÞ‹—Ö—ÿ´†þð‡¼üú[ÜzÓuh¥ürP(Û—_~ɱÇË­·ÞÚå@±Ë´iÓî R ¸A¢, €ù(,) áÁ( 8V”ÍxŒšM:‚ÖœŠÄ 3¶ÓqÙ‹¿¿kB/^ÌôéÓ¹ñÆÍx|’ßPHV1|“-±Ù(ÆMØ™]÷ü»ï¹ [ ·m bVØŽzõ9ïk>¯÷”’l3¬»ÝlÍ ÓS‹Õ©„ ×ÀÏO;ƒç_{‡^Ÿeî !JKQÙC„÷ï²eË8ᄸþúë9î¸ãc H)'D,bër6"c¡·¤)ŒÚûÎzDÔÀ|ç¤Èοµ ɪŒÂ×à´‹Ö/øê«¯¸ð ¹ýöÛ T”ÿú ººš­¶ÚŠ­·ÞšI“&±çž{²Ç{tÿZ£…(üäžÒ¤ã‚Å=©Z3G÷U0q«1£9òÇ¿äö¯?cɢϴò‡öH†Öš•+WrÊ)§Íf9á„Âí[Ÿp îôéÓ#!^«`ýP¶€R*’$@Z+iKà¸%hΫB?€(Š ¾jˆ®.€E>ºØ5aDAóÕW_sî¹çrÏ=÷Ï¿;èêUWW3vìX¶Ûn;vÚi'vÛm7vÙegB/¼‡tø¥¥ JZ,\éUŠ®k ö?ðÛ|ôþ1ó®Ëinnð÷J±ÐÐÐÀYgE>Ÿç¤“N4|øðM€O"³‚^ l !D“RÊ“R–ü;º¶ -§#R¾fb‹;‚mš(èÂÈfÊ•´å½H €ê˜4¿E!dÓy9 ç !d™X²d)çœs÷Þ{¯Ù>À'ô‚ðUWW3nÜ8vÜqG&L˜À¤I“ºÊ:_o/Ü08%ù`‰¢5§Iº–‘aÂ!ÿE¢áî½÷^Ô’ʸjÕ*Î;ï<”Rúg?û™ˆÇãã¨$ÊÚúT•nT£D\KÐU@ wùˆ–‰:é„•a¹Vÿ0¯¡-d=µ3ãêQÓAÍ·¯MÍ·–‹)Ãñ JÆ–-_Áï/<‹'þq_‡c+hÇš<ývÚ‰‰'2qâDÆÏøñãû•7CJ”0ÕÍ9MÒí·¡Ö!Õq‰¶œqöoxÿý÷yóÍ7l¿€bt^¸ð …eYüä'?Ùx8jù*è9ÊÖð}¿Å²¬ŒÖºªtÕfœ˜%È+ p ÿ‰Û¦±¿•ïÚŠÉ Áüß+sG¹z–튡-D‘ä|XѬðäŠê½ó¾á7Ïyš¼§ÉJÞÔzk²…ßÑWQŒn¯ýδ63ãê³yå‰ûV÷›Ž®Èyªªª2fOÞý÷œÄöÛoÏØ±cû„{¿;˜%!€¦ŒbXUiktBjªC7Ýš .¸€“O>™åË——T–Þ¢ØX¾|9¿ûÝïXºtéwK£–­‚ž£l ˲²J©|)KCef[àû:ï;xwm0–Ûû9ý½+Ežr¾Òä¼ÎÒÉ»/<,§ô•.¶ä:³®ÿ\ÀÆ–ó ‰‹ñÖ5MkNó¯÷ÛÌïVgh ÂTLX°ZR˜*–%p¤©ù3Ìí€ÛÀµÀÒWM½ˆWž˜Ñ×—rƒEWJ¿ººš=÷܃=öØ“±ÛgvýÆüà€qì9:…€$]óûÕ·*ÆPZÃ8œ‹\KP“,oQ}ôѼñÆüñ$›Íø(t4/^Ìu×]7 ø>ð@Ô²UÐ3”­àû¾’R–ôI 'Ç2e€¡ò"Ý(a›´½!К%è[/¼}¬t<𶲊ڼ 0¬åªT£ÀUÁ φÊ[ûûå}TUtLš"xÑþnI%R·ÔÆE ؤÎ&n iösÂ×»r(͵Œâïª4ü¬³ÎâŸ÷ÝY$ËÀŸ¸û])ýt:ÍäÉ“Ùk¯½˜0a£Ff̘ÑxZ²ð…FâØR*ßPi9RŠI–5ûü¥:c¶ 6! 2œwÞy¼ñÆÌœ9sƒX €ŽFÀ×_íJ)/SJ£~Áü IDAT5OF-[ÝGÙ–e) ]eÉÇv-QX;†þ¯=Q<¡Æ“5íFàZ½pt;÷¹rŸ+²žáØÏæªT²žÙžÍ¼1£hÎiþß¼VbŽ BéUD“lxÚ•®-)(pÇ6Œk®²Åm‡ŠÛ ޱÌñ¶4Æ—c&BKšHÈ{‹ól7Üa÷-â}q•™>ýbn¾ùf<Ï ®ßÀŸ°ûáw.öô8àöÙg&L˜Àæ›oΦ›nÚ¡áŽïk'%õ-*8Gé”oè}K ÕqÉŠ–0<A¯ê&æÚ]qÅ|ðÁ|ñŤ ”Ú ¸h^ŽX´ º‰²5´Ö9À‹‚ 0f›0s¾sLŸd¥í^—%q{C“0|žñÚ•äR‰*X+Ê×pЀî¨ÄòÎùšlžÀãVd}mBèy£ÄÛòEžxåf¡³ÎC¯Ù ÂâJ›žáR@]Ò´ ׳ GxÜĉkmHE{=ô¶Ãí2ðÀÿ»ãHç|MÌ(Õžé¾:4Zwï|]£ýÀÕÏaŒƒ¤+hÉE×Lí÷GË<”ÒhËDFº ­5çž{.Ï=÷P>Ê¿+¥?lØ0=ôPŽ:ê(ÆGmm-ÕÕÕ}T§0TÚæþ®oõQE¯LÓ£"fÃòVÅV”ºмÇAU\²¢Å¬Ë0qâD®¾újN=õTr¹\ië{$€ /€Ç"–¥‚5 l €‡Þnñ2y­²žQì™ 6Ü ’â|M¡I¬côÿ–ÄC"“Š%íÚí-CãŽñº¥$X÷n÷ÂmK°ªÍçïoµ²ýp‡Ý¶ˆZŒÊ l-|ï‰"Z;ÌäZ<‰XAÒ–)‰»k}”ÿº`N\“,iê½÷ݨMHÚòÆø‹õЙ:u*=ô¾ß“2ÅJÿˆ#Žàè£füøñTWW“L&ûœœ'44¥€*W²¼UÛKHP æuø+",L8‚š¸dYsÇŠˆ††n¹ån¼ñFòùHš®/Â(€†‹€9Q UA×([`y½j%u6áX JZ$Ôy›pz<(1K n‚vO\ÞwAYÓî·+ð5OŽ$¹›0þÚ×¾×× ‡pò*>‡%ÌZÆ‹¦Oq^kNEÚô¬*& ‘œT&ú{ï½—Ûo¿––`Ãôþ»’¹vÐPþsÊ1sÌ1Lœ8‘d2I,ëWF¾ðÞj’‚ú‚òí·!WCØЖP3á÷@ªÒ  î.€–˜ë°dÉR®¹æî¾ûnêëëÉd2T@'1 ¿ÆäT0€P¶À1»ZMq+Ö&ƒä3A'Ò˜Âß}œ•މXÒÔàû äZ#ýç…»¶$“ˆ‘0øN)W’Éi á^†vR¤uãÍ7ßäꫯfáÂ…À†¥ü»"çÙh£8ê裩Ùáp¶?‘ì:ÇqJ^!c Áà¤UT‡_B.€àÝ–‚š„)ÃËù׊¦±6a±è«Ï9å´xèÁûY¹rå†êõw…b#àÀ;À5@6J¡*舲5'“ô uýËÛu,ãexÞº“ß>üðCî¹çfϞ͇~HCC–e1dÈÆÏÀá‡ÎèÑ£{ ‹yîb4g5v%&䊢çQ”e&ÄPwK–,ᢋ.âõ×_6 åß•Ò>|8S¦Lá˜cŽa·ÝvCZO¼ŸãËU®A'ÂJ‹ÏëÃø(”¯É Éä5m9›(µ š+ê¹ñŠË¹÷ÿþ­õò36PÓ÷€G#•¨‚([`Ú´i-]tQFÑ-…Ó·JI`IA^­Ùó}ë­·8÷Üs™9s&RÊÕ&ïÖÖV,XÀã?ÎÙgŸÍ¶ÛnËa‡ÆqǷήiá’BÜ1 ´ Ï]Ú+@Ò•øÊ$SB__çî!ášuߦl÷&Óßÿþ÷<þøãÀÀWþùFŒÁ”)SøÞ÷¾Ç{ìAñý¯´fhÚâ­¯LbY÷ƒ0(i*Crž^Crjÿ"dT ZòªÐ ¨hkkãúëoàê«ÿÈ×_Ýá³Î¿e™ÁþÌÇ ”¶¶„˜>}º""&@0Yü†¿¾ãÜÏç¹ä’K˜0a3gÎìðÐ?øÅÛ”R¼÷Þ{\~ùåL˜0í¶ÛŽéÓ§óÉ'Ÿ Ôêþ}!ÓØú^³½ôKÊhL2bT[Xuј]w"ߌ3xàÓÓd )ÿÎ÷q±bßl³Í8ûì³ù÷¿ÿÍ¢E‹¸æškØk¯½Rv8Nƒ“ÍÙÐ+ýw“ÂÔáç•¢5MlJ A•+ÚJ'Ã?ÿùOvÝuW~ýësVSþP¶m¤ÃPÛ¿†F'NÅ([(ö¬Kød™¡‹ï}ˆL&à 'œÀE]tÏâ/þ<œô?øà¦M›ÆV[mÅ~ûíÇŒ3hjjZÍH¸"`,pàõÝ×ì&’®I lÎêRþ „ åJ3k—á³Ï>ãÎ;ïä믿Ê¿Xy‡K'–eaÛ6£Gæ×¿þ5¯¾ú*_|ñW]u»ï¾û:ÏY“4Q¡¼QÜBŠh A} •og$éæ"ôçOýöÛosøá‡sä‘Gòî»ïÒݨd™!üÂ?¾KGŸ7$”õ¶ÖZ‹Ò=pA" %Èz?˜Y|ßç¿øûÛßzêëjð¹çžã¹çžcðàÁüä'?á´ÓNcĈ¸®KÒ1<ù+ØbA;Ý–° äóž´:.hʬYá(¥¸é¦›xâ‰'ÌQ(ÿ®¨w…ض”’Q£Fqä‘Grì±Ç2a„^·ÍòÔÊ6Űt4öÌ–$\A}‹bôàRwË òcl“ º¢Õ××sóÍ7ó‡?üÆÆÆ`œè Ë^ä?os£§‚²6¤”­Q· N˜÷ÝwsË-·ôÙÐÙX±bW]uW]uÇnh(k@)••R*­µ,•÷fV»¶ÀS ”æOú«V­ê÷‡µó¤ðÌ“óÌ“óÑ“GrÉïÎc‡í·'N÷Ûø]H˜¼¶|”ň¦ì«5ŒÈÕ}çóyþö·¿1sæL ÿBÿû0"“L&I¥RŒ3†C9„ï}ï{Œ;¶ïÇ/z”° ÞwBP›0-y£‚% AT&¯iÍCl=m¡|>Ï+¯¼Âo~ó^xá ”sçyl& ¸xx7jA¾©(k@Jé—vý¿=ß ’} ·ß~;PºuåÎã<ó¯ðÌ¿þÁI'ÄYgÅ[lA"‘($æb¤\Is&Ú†@5 ‹¶€:á´ßO=õ7ÝtÐ÷vWµù©ª4uµ5Œ=šƒ>˜£Ž:ª_”~×BAmR²¸Ñ ä*}) ¦CcKNE×Xše¥¡9«¨Kö>°|ùrî¿ÿ~Î>ûl2™L¿xýÅÐZcÛ6›m¶Ÿ}öÙ†h„Q€L¿€“†H%ú†¢¬«¢„m |ï¾ó6 .Y¿·Ür »îº+×\s ,(Ù„‘Š š"¦®‰KryÓf9ÄÂ… ¹ýöÛY¼xqŸM 3÷CÔÖÖ0zôÆLœÌq??Ÿ§žzŠÙ³góÛßþ¶tÊ3ó¦c’UmÅÉo¥…P7I²m=`gìK„ÕRÀªLï+æÍ›Ç¹çžËi§VPþýµÖ_|Ž;–Gy„qãÆõù8%Bh Dë@”wÀ÷ý¼eY>Pò¶c1Kà+Ík¯¿Œ”rÀ4“innæ‚ .àÞ{ïå’K.aß}÷¥®®nÝö¡w™v ê5ºÄùÞÅHÇJCk`(¥xôÑGyðÁYûfÂ.>Ï AƒØh£5jx‡òžX<‚Mê,¶Ý6O:. \Qü2HÔÚ)·Ô~ˆ¹“®éÔYß‹J€|>ϬY³8ûì³ ¥}пQ¾ð܉D‚ŸýüT6ßr,—]q5ÿyÌ…~(®^F-È7 emX–Õª”Ê !ÜR{à1Û°.ü²tžvwzï¾û.Gu'tgœq;ì°CŸG)ÂÓUÅd@dþ„‘0fº7†¹o½õ7ÜpC gßyÿ±XŒm¶Ù†Ñ£G³ÿþûóío›­·Þº°Ï «šhl+&â)í…D<~tL|†—AàÚPߦQSÚ{¢À”i›äÐ5Wtýû444pß}÷ñ«_ýŠ–––’‡ßGŒÚ–!»Ïs[h°Ç3ù¿æñ[¦•lü>DØøð``xJß”µ4J)³ZëªR³% Cý9P\¨µæ–[naÖ¬YL:•Ã?œššš>3éšpoÁç,¹âÓXBàtÀ---Üwß}Ï­/'ï-·Ü’‡~˜Q£FuùyM\²h•(¼h¢!Õq‰‚†ŒbhU©ƒca¾ìÔ’·GYKÙk¸9f ÒqYXèbÏÂ_J›ÒÏ¿XÀ ×_ǵW_Õa¬RÁvcðŸ¿$ç™ÜšÁÃSüä§?¥iÁž{òŸ%“£^ä_÷oD(Ë7emø¾ßhYV&’úwÐàÆ“%{]è\-ðÉ'Ÿpâ‰'ròÉ'sê©§²Í6ÛôéxI×äCxÛ¾Ô¿G˜Œ(hÌ(^yånøë_ûe¤aÆ­QùÔ%$/Í“ó5±ˆ¼ï„k*3ê[Ko„Þ·cc¨½%o×F¡1”zn0vÎÅPÚŒ µ‰Ì)­Éä5¶e耿nôLÿŽ ƒ§¯Ì1ž2]$3žæÝwßáþt/ÌüG¯¿ÿúA°ã¸¸éw?î´=ÉVW\̱_|È|°¡%‚ùi,à2à*K†²6,Ëj J#[ Ñ ßdó ýðÀ{(‹½¤l6ËŸÿügÞxã ~÷»ßqÐAõYø”k²­Ûòšêxé ‰ ¹qɯ—óÿn¹…¦ÆÆ~ùMÖ•ëQ›”d<£|JoEêZ¦n}«ýÈЕòz[š:üú–µñ˜ýÛ#V¾¦ƒ‚öøÚðmø*TÞFÁçä=ç›±Â{ç‹w^`æÿ\Âó^í¯ËµF„÷©m[œsÎ9EŸ×VÃãÆ1uêTN<ñÄH–%ÖáRÀÁÀ!@TÖ7em¹ 0‚¾çæ®Þ~âîø¾U]¡s4àÅ_äg?ûçw?úѨªZÿÕ“„cÖß›sŠ"(< /}M\ðÊÿ¾À}3fÑÐýÖÄ%¾†–¼¦¦•˜E½o) O¸ö½.ÿº÷^8EǘÐ ÷”Ƶ«Ú«Ú~@šå)ïC>Pæ^ðžóÑO9_ãûå<Èùмñà5(E!éT ƒï-°„©ÐqmˆÛ’„#±¥¢:.Ù¤Önßn bŽIæù¯pëõçñÅgó{zÉûáü5vìX¦L™Rô‰(¼I‡v§vW\qņXâRà )jA¾ (w@: åëX)#FmØ1cøôÓOK.COPl$-X°€ßüæ7|ñÅœuÖY >|½Îw¶lo•)¤[–ñ¯{®ŒrŠbnLÅ hË)JQœRœ\¾›Ž|íÉoëú=:*r:(k´¼=k¯HyûÚ„ÏsAÂa^çk-í ´ÖœqÆkÊUUUqÊ)§ðÖ[oñä“O–Pº>AØø ðçhÅùf ¬ €|>ßæ8N$4“1ÛLVYN:ùçœî¯¼EB¹úê«ùꫯ˜>}:£Gîõy]Ë„[#kdøÙ?|c6Ÿ¾ýò‡°´äz.@o"Y]í.T'$_¬ÌãkMkNŠÙ„Ïó¾QÚy_“÷)PZ›Ðy»'ž ÖË•6Ÿ…ÊÛWẻYA4 !è@‘·¯Å{¾fh•…m+p“(³ «¦kµßGŽmŽ—}`ØÇlk –6ùl7LÜÀÐ&_wÝuL:•úúz ºv½BFŽÉ~ðƒuî»Å[pî¹çòñÇ3þü?笿îVD-H¹£¬ ­u‹R*E€k lKó4Çÿðn¼áz>ÿüóÿ@/ xžÇÝwßÍÊ•+¹âŠ+Øn»ízuN'˜Ø3ùè¾÷òåË™qËÕ‘Œ]ì…Çmã•ö¦}±ò7Š3ðƒµð¼jWÚ¹P¡û¡Yß(Ûœ¯Y°ÒgI“Ï?ßi#“W…P»Rí ?d² C÷R€%¶Ž8–À±Ìï[åe+x႘e”k̆¸#‰YÁs_®ò¹÷föÙ2ÎèÁ뛋ÐnYv§¤0Ü'á’®`e[;/‚þøÇ?rñÅGÞÅ/÷G?ú©Tª[ÇLž<™3Ï<“óÎ;¶¶¶?ç!Œl‚) œ­8å²7‚2À’¯Á L¦sÎ×Ô Äå—_αÇ»Á¬ÍËùøãÓÚÚʵ×^ÛëŽt¦@4óù<ÿú׿øäƒh(Ç‹o½„k’ß2&YPëv…®k{J“óMø<ëµ{ãÅ^xÖ ’ÛÂd5eBì~ñ®Šì‹â ‹FÏ7I™«Ú|ª\IÒ•í^¶m<íxè}ÿ;Å^xð¿%¡·!TP°üðÃ>{]XÖìó·[Q” D€0<ñË[+Z$–4J¼:. ܱL¢[èy‡JÛ•fý;ôÄË”ÓY½X\KÒ”í|ÿ]×{áŽ]›8Å¥€é˜dÕ™øú–4÷fÎ÷¸êWsí•W°jÕª@ÎhŸÏpüÓO?½WÇï°Ãœyæ™|ñÅ,Z´(òïÓ„K?®¡è7”µ ¥Ô¥ì XÜ0“o÷àÒé4çž{.£FbÚ´i|ùå—Áþíu΀ÓO?Ûo¿‘#Gvã`@.þ¯:Fú¦¼¬èEi“enj¿YV¬jàÒ?ô¿÷"îÆwp­öºmc”w ´ß\˜ãíE9ŽÞ1…c™Ò4Kš,÷¾Cמxø¿À„à›²2ÑáÏþ|b, U1ÁW >DTbKAULðÂ#·óìÝWþ‚²ÔZ³Å[°ï¾ûöúÇs o¿ý6—_~9ù|~@|¯nBC3€ "–¥lQÖ@kk«—J¥¼(rÀ$|5gU¡”IcŒ€N8wÜ‘¿ÿýïÜ}÷ÝC Ä@|H‹€§žzŠ_ýêln¾ùFjjj×~`XƒŸ´æ5NQå[gEnjºƒ’±`-<ÖçÛ×¾ó*ø;܆σ¤5$®ù¾ÏÜÙðÙ'¥ñþ%-&o¹öÿ¯}ÞøRÖ×»FÏ’ÚVGמxq)`u¼½+`•osÖä<¸%oÙe0ë±ûxæž?²ré’`KôÏ_ø¬{ì±Äb±^ŸGJÉ/~ñ ÞyçþùÏn0‘Çøp•vÁý‚²6R©TFkŠ„'îH<¥ðƒg-tv¥”Lš4‰­·Þšã?ž÷ߟ§žzЧŸ~šO?ý´ÃÃ9ÖâÉãþûïcÔ¨-˜>}újTXû–‹ùJSߪhÎ*^˜Ÿ%¯4m¹0Á­½ì¬8ÙMëŽñg ÈÀK¶ÂZðÀ£N¹¦¾»sf:^Ž›þ^ºrâÕï³ÕÃéhMÒ‘ä4eƒí5i½ž%µõRj’-í­pKý˜Xªc’L^ÓœU J–¾/ÁÌ™OqÓµ`å’öhÜ@yÞ~øÃ®÷9†ÊùçŸÏ'Ÿ|Â{ï½×R•áóp2ƨ QÖÀ³Ï>Û=ö?ü0ŸþùjL}Q£X†+¯¼’–ª-Ùù )ä•00>…ÚpäüKm9Mk^óæ—9lÛ0%ÚÒ°²9RP7eba™l•yA±kÞ¶…d¸ðÿàÅ„¸5ÿû¿/òÁ»s£ºTtNטÞZ@*·WJ¨KJæ/÷Œxt&”Â4ãQ@cF3¨Äm3æÎ}›‹/¾˜O>ú °m ·Õ0¦éöp·¬iÇ,SíÚ‚ª˜dHJpíe¬k›õmÇJáÈAˆƒÎ¦åœŸpÿßîä/×\Áª•+ûøŠuÅIW^y%Gq{î¹g—Ê=¤m)AC ÖÖVn»í¶‚Œ R@*&ijðKŸ€UYæ>lÌ(jÑ,“9–Éh7†ú÷B<ôÐC\{íµ´¶¶öë8ë‹Ã;ÇéŸVÍt?ýéO¹êª«hnnèF@8]Tcr*@¢ì €LŽ&Oû~ÎÇ ;’e½Pq+Zsæï\^ÓV¤Ôà vO66M\&À&Í–¢}jÌ6^•ë@Ò‘´æo.Ì±Ûæ1Æ qpƒcl‹BC+`w Ãæ2›‡ÑÁ<F±Ú0dcvøÝùœüÓrñÅsÇwËåÌ~%~˜‹€“O>™×^{Dbõ28Ç2]ÙzÓ§§¸ï¾û LnÕ1IC°þ^꼨ʒ‚¤#XÑâ³Y]4Sc™Ð%M>¾Ò}Ì…ÐóæÍã†n`áÂ…ÀÀõþ&p–Õ ¢S§Nåõ×_çñÇè¥á á“1 K#“¦ÌPöÀÿ»ªÑS:«4I¥MŸ/!Áà„LkVЬÄ6ÚƒS Çð”ÇQ(/‹Ù±‹%pe»7_PÜsþ Ã}i“ÏKòŒ¨±Øz¨½ZÝûúA3räHnºé&~ú“ŸrÊi§2wΜãJý@¿÷Þ{\ýõœ}öÙ«E„ÄmI›§úóe †ÿ‹Q|Õ^‹R‡ßÍ»% ,oŽ.Á‘P7­yM:Ö×â…^`Ö¬YÀÀ¾7„l¿ã.ýž³tÝu×ññÇóá‡Øk œ1ÿI¥UpŸ¡ì €ý·Œ5Ç\‘Oº’xQy™mµ³¯…Ll¡ò6Þv;ctôÄ ö[®DQc–®ëÄׇè`·Ýwã×_ç0ëð---==Ùz¡xò˜>}:?þñ:thñ€ ´dú·!Ð|À+¯¼2À'x¨K2yE›§I8Ñdà[Ò…\Q@JAU\÷ @:ÖK‹/Þ ²ß·ž¸7Êê=ùOw±ùæ›3}útN;í4V¬0ÉÅôÚ„H5ð=*@Ÿ!š…¿b·QnÛÄ‘®7v#‡Ñƒm6­µ^-’²””ÔÄ%U1I‘ăôÝHg,)‚F,!Š•Ç¥ósc«Í²C×T÷ÛÖ!¿ýío™={6Ûm·]!|XJî!ÍÍÍ\zé¥? Ê4®F=Û·¸õÖ[¹ö_Œê„IÀkÍE§|-iÈ€VFX¦Pú¬WÄšPUUÐ!J6Ê´ÍNû’ñÍóÛß÷ñ±ÇË”)S d^ø¹ ì¥ 儲7ËR¶%u»ò.Vâá$ОŒÕ3tswüT†ƒç—® Þ¤I“˜3gG}4®ë–<à†n`Ñ¢E«}^“4gý9ÍßsÏ=ýxö¾ªc¦D´µ9k‚~(ýäŽ.±…e‘ý%Å„ ;vlaìf„×cô»Ò”ƒþ—ñ/ù &L(Œ5ЮK€P¨AÀQQ RN({À÷}”Rë˜ÜúÎ/†-MëÖŒ×].€¾ëºÜÿýL:•d²´ôjB<ÏãòË//l /}u\Ð’Óýf =ýôÓ,^¼x N`r%BˆÈ €ª˜ ãEÔŽçÚ¦]t¡°Ÿný÷ߟ“O>™êêj Ýh÷Ëf[mGcJE|gY·Ür Çt 'Àd¢b®*3”½`YVð¢Û–Æ»Éyº¤@ˆßþö·Üzë­¤ƒ ¯'Ûn»­¨­ªù¬*&iË+”êM´eݸûî»êæjˆ;¦ ¯¿—DÖcH<2ùèäˆYFŽ ¨?“"ùË_ò׿þ•­¶Ú 0÷ë@Šì´ÓNT§â4´™n–¥Â¸qã¸à‚ H•Øaè!Â{8pH”‚” ÊÞð}¿ÈGñ€[Òä„ q¢ÀqÇÇ]÷>@"½Ž®}}!D‡ZüIW’õÀך¾ön|ßçÑGíÓsöŒ²±¥ aS´þ^úûCãyÛ¬lÎpmA:&ú= Ä~ð~øa9äB­ý@1wÞygjS1Úòºäù!ÿŸ½7“¬ªï¿ßçÜ¥¶Þfe†``ÆVAùdÑÄŸ5Š&"@£> HDT¶òà¦h¢‰š€FäAÆ ÑaŸfïYz¦·Zîvž?Î=·ª§÷ž®º½}^¯êêºUuï¹·Î=ßýóýÄ'>Á;Þùκ–î'Ì">øË42U0å˲z¤”~ZÇw-¨„éx þï_üg_ú=ZÚfõwõÖzj‘w%‘/ÿ‹qß}÷ÑÙÙ9aòÁ¡¯½%uü=±zîÑÔ×)çrŽdwÊ @k΢·¢I´+VðÓŸþ”Ï|æ3Ì›7¿!Ç æž<úè£iÍ»( ä57iìø·û7?üðÆpôP@xP¦¤i„)¯E á @m‚“ßà€}a[‚#Þðf.¼ú›äóù†¸<…<óÌ3<úè£É¶¬­½»Eoü÷ãÿxÿêb.4ç¬Xhü¸•2T¼‚&W¤Z hKAKV{ÊAeÉdøÊW¾ÂM7ÝÈqÇ×ç½F{ ÍÜ=úè£™×šé“ ª‰¢ƒ¦¦&n»í6ÚÚç1#‘ö &;¦¼àû~¨F ³€Ø–îwŸ¦ ¸N|Ó_qÅUW#¥¬» ”BJÉ÷¿ÿýd[ÆÖ QO\½+W®œ @Â'! 5+认37Ì8l Í‘„~ ãæ]A¤Ý)äDœ}öÙÜqÇüÕ»ÏÂÍæâa¥“pØa‡1;o†ºE²FcÇqê©§rÑE!'f(À\ŒùèdÀ즼à8N¨´’|2¶Ð @Ôxwž%GPô">þ‰Orî¹çÆc©ï`”RÜ{ï½É댭ÙÇ{‘衇èèè˜PÉ\ÃA—ên|^ƒÜÞA MXeB´6”¨z",Ù·+`#qÄGpç?æÝç~ŠÙ ŠÇÐØêˆ%K–ÉdhËK„ •n‘朿ð…/pò›ÞÚðã9àuib²cÊ+è@*UY[è~ñ‚–†|@ÖÖ½ ¤”\{íµ{ì±ñxêëØ´ik×®´«7눤î|¼ð?ÿó?DQ:µìc…@çDx”SËPÑÊaÖ©­Fhp)`üœ±‹Ô€¬ksþ…_æ¬_É'U¹f¥X.]ºÛ¶ireÒ.z¤Ê¡JþôÙ2jÔžçõ_¿•Ù —Œi?u†9¹EÀIid²c:(ÝQUÒ:x΄‘"L-Ī#(š†wþüù\{íµØ¶ÝÅmåÊ•€N|Ë9‚^|÷•+W©éxcƒ€œ«ÃbŠ%xVLÔë©4RdAÎì-§•©Ñœ‘¬8õ\}ãw9÷Üs)Ô°Ö‡vŽ£{†4ç´Ç®íALfLy ©©© ¨CÞùÈu%QD Îo9[™5¬©)ÏyçÇ~ô£ºöFWJ±zõjPº³RSF‡:þ¼¿˜”ÖŒœ#±kâÞi@ ÝÂZ¢Ãi)¦•öÖÎH)d£³ð…@M®¦%îõtÓ ‹.¾˜üð´··×} ms²§ Ù(D½^Ä‹;ö”B*¡N(®å*~„ ü(ê~,ØC… r¨ä~“B· ·¤À‘ºÓµµ˜‰[šglíiv%m(sÈÇ/ÁéXσ¿]Y÷k0 Kê0à þ?ÐÄ”W„e¥”E‘’²Ž Ç@ÆÒÝþÒ"20¹µŠÈòåËyÿûßÏw¿ûݺXÏfŸlkßΠhr%;{|­ˆˆý÷†üæ7¿Á÷u}²Xÿ·GŽ›O¥‘쥡¯.Gw9‚”<®ÓûÚÍ»ãs›V§ÙÐsͼ£ƒ z+z.mÛ¶—_~¥!sëÅÒ,~ºÖ#£è)v÷„ìîÈ:Ä‚\S M1n Í&éZZiiÊꎧYG$Ï®¥•«l,Øõ6‘tBµãçÁÐÞòòn¸îºÿ—÷ÿõ³lܸq¢xÚjïîâ³3S^ˆHÙxëÆµtü-H·áYWÄÖq½·µµñ×ý×|÷»ß­Ë mö©”býºu,\°€æ¬Ž7ÑÐ ÏHñÈ#LB€FŽ4øÕÌ÷F¾&çê½aþÏçóœ}öÙ¼ð <øàƒý>7´¶¶Æ €H<…my­”UBEaØ=ÔÍIÞ‘t•#ÂHqàrå•WñÞ÷¾‡;v¤­ÔæÎŒ0jL (¡¢áç›±µ[ÓxÒ‚kkEÄ è#,ËâCêgE+¥Ø³g û€q}óPxì±Ç’ÀÉ) 9+ðB(úŠæÌÈ€‘¸ÔÂ@¥âY[0+'Y[ލ*ñX…Iݸq›'–vœOâº|Ì‹·‘±¾cË=RDQUA0‡B!¨†Bl©OÅ–‚J (¸’–¬Ò[Ïߌ¥»kšÄ7×Òì™XÀ›Ä6£ŒW¿[yߦl6Ëe—]Fww77ÝtS’K3¡ØÚÚZÍQŠÝ%³ò’Ý:¡ÇÐx"1K ÚrZñCÈ:ðgvW]uçwÞD)¿5 Àýib2bº(R’¿¶¥ÝŒ~¥ª8R/´^¨ú £P¨¯}¡”J©2¶ÀлŸl€{÷îeûöíi/<û! 9+ CEoEÑœÝwãÿj¶VëÂý¨*¨ý~áÅ1ïJPµ¼½6îñÙ] ùÙÚÞØZ¯§+üHsY¨H¡ŒàŽKÊìëÙŠ“ ®Ô‰jdl‰ci!Ÿ±E0×ÀvÜ6Û "~ó|‰0¼ç˜Â8 »jbÛHÑ”ÑczbÕC„aØï}#ô–.]Ê¡‡ Àµ×^ËÑGÍÕW_Í®]»’PãHçg>ŸO3Ô9y‹’ïíÓ¨‘€>ÞÜ&Éó;Ê¢°,›÷½ï}<ùä“ÜvÛm Ï ˜ ¼&íALFL  Š¢T* Ž5 V3Ó€Y KAÀ²,r¹\]³¥îÄ »²‚{õêÕ”Ëe`¢%Ž|Ræ,„‰•ÚÝDÕ7óö‚¾Öµ±¾%î‡ÕØ·î&ÎXà*&©%–TBíbßÝ%5á¶Ç’Õ¬óXp;–ÜNnÜì‰[ÞÒßM= Z²Û:‚HáXû~wô¼6±m¤È»‚½[^`OÇ®A-\ÇqxÓ›Þ”¼ž7oŸøÄ'8âˆ#¸úê«y衇ôÑG873™L¿ü¤Ùy‰¤GÓl®õ¼‚Í“žO¯1 ÚÚÚøÔ§>Å“O>ɪU«Ò¼ÍT^„–g“­$(UL €t½ïØVM@Jp¤¶Æ¢|¢¨î®t+î,fúì/ãÛÚµkñ<Íï4q„?ÔÆÆƒˆ$n¬h/N\+ÇÏ»{#J¾â¡—Ë<»C³$+=5»[ÇуØnÎVÆîsm…Ç5Ý–~íXud·¹Its­ª0·ã:ñöî_>Sâä%?À‰÷¯º¥ ï},×j¢z‘f ]P õÂk_ûZ.»ì2xà HÀ¼>è ƒÜ߬œ¤ì+¼ ZÉÓh4e$M®`OIWÔ†f2™ ÿ÷ÏSO=ÅwÜ‘¦`°8OfL ;Š"?­<€Œ­3›ÓSô*š±e¿¯ ««+i×[¯›WÁœ9s’×MIqÀÀjuCÇÂý@Qô|¶µï÷qŽæ,Î:&Ç«–¸%@È*•«±½@ñø& K0(ùÍÀ‹%^ Ë¡_¹– ©†  Ñ¤Uæ\ò®V’ ;bã5ÅæÍ[èíÞ;è',Ëâo|ã°{’RòÆ7¾‘Ûo¿ë®»Ž[o½5aÑKŽßoguV¬$W· !˜[¼ÒQÓˆt|ˆmyÉîž0á廓-âŸþéŸX½z5O?ýtZJÀù$¾78¿„eYüÙŸ¼ íÈW¿úU^÷º×q饗²m[ßrõ/ùËœ~úé}®¹ùNÁbývŸR¬ˆ×A?¯`±f›G%P4eúÏ“O>™Ï}îs|ô£Å÷ý´”€…>àdÇtQz¢(ò…©X5®U¥ÖÛë׺Ôͱ²®À «ž! ½½ßþö·uK¤Ï—pÛº "ØÕPà?íÁ°¬š²2CêbÛàJ‘¸Ò›\“¸@鹈hâ¹ÿQ'zJ-YÁæ½:£?“Ò©›É^éH7¡2cëðGï~戌Bèüßï?¿ŒPBŒJä÷Á~“O>™»ï¾›'Ÿ|’yóæqöÙgó†7¼!ΑéYy͈ØëÕÜ( „Y/ç7[”^UôT³ó{‡þæoþ†uëÖqà 74ZøÍyºUg#>™1-€ <)e”–UãØº®:ã=<&êÕäO-Y¡ë¹C…' £«‡»vÏè3HËbùáË9¨Í&c væ%ë·{œ¾,G“ ®%±-Íì–(q¼\Šššóøõ3÷m%ò'&àh[)´å] "ʾ"c§“èeØË®:°û•à5nœQô#‚Hí¡ÏX±fͼ&ð_¸p!³fÍÓ¾—/_Î%—\’ô°m{H£¤-'ˆtUC ‡Á0¯ÉB]奬ǑÏçùèG?ÊÚµk¹ï¾ûéH¨ÐJÀŒ0BL À¶m_)•Z~ÆÖ€*ûí(…ù>Ò<ŒëÃ#¥Kż@·P-Å¥e•¸>¼äG=E)v¥oÚÒÑò퇻QÀŽ-/ó¯ÿú½ñ;ÑAϺ|ìíÇ%Ä1Ïïôyz»Ïáófç£ugoÚøê¤f¬…Ž{ ÂÊJ«/9G ›/¢-7š|„ñCƆ‚ %=§›FÁŽ8^xöÙg$müñûµ˲’²Øá`Úw–uU‰›’‚8§ =pÅþ•µX¾|9ÿôOÿÄÓO?ͦM› ˜V^lÔ';¦…àû~¯eYÁX=£ÍPßͽ°V­ýlˆ[Î󘡭èE}Eѫ֋Wb_öM³S^+‘ª©7t¨$D-9G’w»zaa‹EÁòذò—tîÜ<¦k2RH)9ꨣ(¸Õ%£-' •Žé 1ÐRÒ7C}_¼úꫲ`,B ^”ü´Üïúzgm°·¨hË¥3K š3~Òëéxs#ÑÕÕEWW× ï !8öØc8"]†×ëéµ"- cë$Ñ=!a¤H †w¼ã¬_¿žK/½´acÌæ6ò€“ÓBPJuK)ý*)Çè\êCg¨ÇÄ-F8Ǭl^ -ïrÏïè(Füdu/–¤ÊÞæ×4KQµ±yD%%`Ž%ÈXu%9[0;¯­‚ŒS¥TÍÖ49Ѽè"±¸­8ŽþònŸ;/ò†ƒ3”wnæGßþʸ\ß¡ ¥ää“Oî³-çh«Àd6÷Gß õ}±eË–A-´É¾R²ßäHcEm®Šk ö”B–¤¸44eô=Ú]Ñméú~á…†l0%„`ÅŠLBÅkÑÞâ ¬ÕŽcV^²«7"TC+èçŸ>ëÖ­ã?ÿó?†±u¶¡•€ŒÓBp]·[)åW[è6½aM§±0Ò–xÙ×»D”}ðâ×Å êR/yÕ¶£šíMï§¶[™[ê}—ؾ}û ¦i(¶¥ðº¼?ÅžâŽ%hÉ vt‡£b5]°`^x!‡~8Pwãhªç¦¦… ¹¹ÙFÌS,)•JT**• ¾ï•J%y¯X,†¡ÎØ—˲Èçó477ãº.Žã$‹J·GGgˆ7¿™\Æ­ãÙöÇÆùЇ>Ä~¸!Ç3þÙgŸëö=WãV.¸U¶·ÑˆšŽŽŽ©£Äñõ¨øŠ’ Ó¯~°¥ÎmÑîfEs6%2 š3Å€¢§Ú§³SsÈ f¥.ZÔXºù„Š·É¢³áJ—6澓—lëÒí‰õ];²»÷-oy þð‡¹úê«éêêªg( ?f0L `ýúõ¥+V ¨„aÈž={سglÞ¼™õë׳aÃ6nÜÈæÍ›Ù±c£:¦ã8Ì›7yóæ1ÿ€ùtˆy¼ºì^:æP–v(óæÍ#ŸÏÓÔÔDss3MMõQZŸ}öY.¸àî¿ÿþ†eÍ+¥p]—}ìcýÞ3ÞÜBFTyçGlîîîž2%€R@!# BEoƒ^_èn|ÝŒ§9›–ƒPМÉõ˜ShL>BíÜì>9à€õÄ>H¨x [ö†x¡©hl³¦$°Ùâ¹~š*bäc¸øâ‹Y³f ·ß~{=óò˜¡Í`XL ਣŽò”R‰Ùèy[·neëÖ­¬_¿žU«V±jÕ*Ö­[7쾆›´æ}ß÷“c<~ügü&“aùòå,_¾œ×¾öµ}ôÑrÈ!´µµ1gΜ>ÝóÆŠ?ýéO|ìcÓÝþ$üÍùŸ~úéC¦\IÑK¾4âýwuu·i¬HØôTsS±_´%—suü}oI±¸-…QÄ‚­9£•“؈|„={ö ;·,˜_×1 †YIg9J€FÓš,hµñÃ2]åˆæìè{«\~ùå¼ð ¬ZµÊ¬GãýÃæ˜QFŒi¡DQíܹ“—^z‰U«VñË_þ’x éÇp~8!:R![©TX»v-k×®å'?ù ®ërÜqÇqâ‰'râ‰'²lÙ2,XÀ¢E‹Èçó#Ú/èÆ=÷Üç>õ)ÚÛÛZ/¯”BJÉ¥—^:äçš2‚J 4w¼óSÕݺi“ålÝѰ³wERÈhþ‹ÏÌÛú ¼ÎÎÎa€9sÒ!škËJ*J­I’Áœ‚D ØÙq`ëÈ*j±téR.¾øb>ùÉOš®ˆ##Œ YR¢KšŒ˜. ÀÂÿ÷_ðÇ?þ‘ŸýìgìÞ½;yc_á˜Fm¹ƒçy<òÈ#<òÈ#€n®qÒI'qÊ)§püñÇs衇rØa‡õé¾/6lØÀøC®ºêª$G¡QçdŽuÆgô«ýß͉jÒ¥Ñ(Åb±Ñô¢uFly;)I (“uWÒq5ä]]zÛÓÀëÑÕÕ5¤r©”s ýE[NbKÁÞRD)¬š$´f%9GÒÞ1òJ€Z¼÷½ïåÉ'Ÿä†n’uqŒpãÇ F€©®d3€÷ìc;ÑŽZ¡8Èdöƒ_±Xäw¿û¿ûÝï8öØc9í´Óø?ÿçÿpä‘GrÄGËioWÜÿý|ík_ãÞ{ïtßõ>Û¶¹òÊ+‡ýlSܧä)Zî„: Êåò”RŒåmX ÓªÁ704Ò=•ê½’rŽxÝ^Ô0%d$ÊesssÝÇ12Ž -'u)`¤;c6º;c[NÐÞ$•c™«—]v«W¯æž{îñõÌ(£ÀTV–.f×ÞØAè…Úñ™…O)ÅêÕ«Y½z5·Ür 'žx"§žz*§œr ‹-â׿þ5·Ür Û·oï÷½FÀ(-÷wÇ)§œ2ìçó®D EÑ€‘6O5À,œ–ÔÄS=ãM§ O+"$ @Z0Tؽ]>›iÀJe*{†B½’u‡†ž óš$EÝ0¶Ñ %p³Í†Ý~RÒ\;W«ÊÀÐó7›Íªk®¹F¬Y³¦²qãÆ ã§8Lm¹6®˜ªê àŸ·š “•7~0ïÀ£>Ê£>ÊüǰxñbÖ¬YÓï3‚9Þüùóùâ¿8¢ïdÍ¿0ÚxžçM)ÀÀ:1²×K— ȱt%À®žˆ Tأό'2¶î“ÑQ )ûxžç {ßd³£pWŒà= Ùâéí~R 0þ^"ût>­¾0Ç:°ÅbÍ/0¿K yyòï¾ÓëQõ!–±‚ ?÷ùîÿ瓟PJEãua-¦®\wLÅ õà_€#â×:ÕT©tV²q†Y Œ…ßÑÑ‘”(6ÚêßwL—_~9Ë–-Ñw\KàŒA(•J£ßd€%¡)+ØÑ¥æþ­4e^¤èõ­))Bè6ÚÛº´—¨5WŸ·ïûÃÞ;®ë¦F‘<» Ù[R ÐP^¢¾‚|ä†u–Óê sÞs ?Rìè ±-ˆ"UMS5A7I‹[–û¡Â5j% i¸6÷¤s ¯9ö‡zþ©‡Ï`|¼r?¿?­0Õ€÷7Kâ×éÑ™Õ-Ti&0¾óïäþáFü=ÛÒ^€¢7º1—ËåÑqRÀ’ºômÓž€rJd/ÍPº¯5.€ÚRÀHé<½½¾‚×°z˲ž1ç=+')ùQMÍÁÇÐW÷ýœf.Õ‚:Š·~ÖmɃ‚¸M¹ùßuçS?Tì)évçx¹Â¬œLº¢–ã6èÉw¢¾ÍǪ̃- ¶Ô Ÿ²ŽÈ]påw×}毎 €7³ÿì´rö1m0•€7W3 „ÿDþ‹/檫®U|ÔºSb×(³¼§¢ûôõhμÊ~DÎIð=–4yWb[¤VrV[ ( QÓÊ‹¨…0\à#ÄP.õ‘S?Ï-XH¡{5,Ž«(R‰õDµÏú?Æž±ÆcAîP‰«p¼øý Ôùú;U«Þ( ñh±x}¶ÝcA³kC&n°6;gáÚÚ×ut^‹~H2vµ¨i{®«Ž˜÷ùl¶\.¡;Ø ö SE8¸”¾nÿá_GÔæ\wÝuC’þô‡BJÝ…1­²·‰)u@AÑW©ô4Uq¬LÜκÛK·"¡àêñ4Š Àôû ~¢Ù­G¶Ä åR‡¸§HMlÜp?¬>‡±]sF¬Ûæér@~Üμ(ÊT‚(ù®Q"[ýûÄê-)°…öÆ9Rw¥Ì;’LÜÚ<çè¹àÚº+ªè…ŒäÎ'z°¤àïOl•ºKê ñï|çhÏó2>–»i™8ƒ`ª(ŸN‹ÿŸþuFí"ùùÏž÷¼ç=£ÛéûÞ§Þè=• c6@Pcê‘00ÇÊÚG ºËéZÞM‰-¡{+†ŠÛ¶=ìüªx…|Ž}¯G¨”Ž…Çqð@UÝèµño#Ƚ@Q ~[ç‘ÂÀ´÷ðãíA¤P‘>d%P¬Þâ³yo˜´$·DœSWN\©«9ìj[óœ£xƸV,ÔmA6¶ÖG{_<ËfÝ6)öþJ%Šä ^zé%®¿þúeQ™Ò½ýl ­Ì`˜ ÀÀ_¡Ë?f„ƒ ”â}ï{Ÿüä'.‚Wè©ìêžQ4ô¢lÉ* OZﬣË;SnO\põ5é©èس'$ö•ߣ»HCÅÆ]wxæÃ§6ö0¿”£âƒFx!x‘Ž}Wð½-0 qq][úº¸ñ¦ @ Íx(¥Vm©rSF&ÛpD\ÁÓÛ}¶w‡¼sEžÖœž/ŽÔÂÞµÄ8 TÖ×÷-6z¥BO%bVNVïË‘ .ºè"6lØ0^ dF1¦‚p6ºæ €qýŸ|òÉ|éK_báÂ…£ßGüÜä ŠAºŒszÝs-½Ø'y)i[[‹£ÍÏ FÏ»šu®×‹¢ªÐW~\nÆIm~’À¦­n?Tx‘¶Æ½$þ­-î5;$~4´ú×ëv3ÿÀ&@$¸±Âm©C'Æ•n[ºªÂ¸Ï5Ë¢ÞæXƯn³¤VlÉ ‚\ Áæ½%¶XC4kRIéàØ0PY_ßwfç%~{‹Z ®¸â î»ï¾ñî ÄŒ“]88!þÆú¯3Œð?üðùþúëY±bÅ~í¯àJ¼ ºï‘ŽaêAŸ“ki÷{ÕåιflAÞtôêö³î05øc)9.6)…Zpvt†lï iÍêÒ1/$î#¡…º.-3Ûµ[Ý]íÆý®3Ú#ÂHЌٸ°- ~¦Oœ| ÔTæä×dq,™n[Š$ñ͸×Ç©·¯0oÉjŬä+š­œßá?2´dµ¢³³7äÐ9£#÷Þ{/ÿöoÿ–”õ !Ä8U1yñc#ÀdWN–¦=ˆé#ü:è n¼ñƱý ‡‚+ðãE{¤D/SQ0nV[ê |Ñx}֌Ò:Ñ«”üá€ÁÝêq<<Že{á¾yD% IbÓ–¸¢ ö0R¼º' ³¬øŸuEl)>Œø¯š´ÈZ0YR[åy×XÞRÇ»ãü»&ݸϟs¹+k³wˆso÷r좱ôšÑ¿çè*û óÙy]Ò]‰˜×$S» IKF²£Ë´Oùyµ··så•W²yóf oBñ8À3&»°’„é©'&Ì º`Án¾ùfÞúÖ·ÿ¥ ÉÕuÞ½ÞÈ)§^‰¯Y8mK‡EvCÂ1ð½ïoÉYíÞœ‘(¥˜„G»T]éåPQñkJÊ]^ T’à–¸Üð"ðÍcª$ÂŒ@[ß–XBÇÂ-¡]é9G7Ÿ)y!m9ÉÂV[$°elí.·e5NîÚ"q§[&Ó]šk9ôµ(8gØ<€-í»‡|ˆ«Ûï-Ù*Sã’ÙúÓ€#óš,¶÷„D ,9ò¹vÉ%—ðØcã.üÊÀ¸wšª˜Ì @0è÷`nÐ<[o½•w½ë]ã¶ï|\æÕ[‰˜™´›ŠKr®¤ÜâŠ\\0Ò©=”[=RÚ"ð•Î8¯„_óTB]Ff„ö+»zC~±®DÆ Œ3¼…JïKçnèßŶ´0v­jLÛ±-9]'ž±l2±®³#N²Íô¼+yn‡Ïý/”8v‘Ëqc²¼÷ÁYê³fͶ‡^·lÛAé¦8i@ÁÜ&Ý/ͦ@ XØbñø¦J`*X†Ç7ÞÈ/~ñ‹aÛ.ïÊñc#ÀdVæ-ib*ÃÿÃ;Œ›o¾™3Ï7B»)#Èäu¸áOO˜ÚlÁöî^,sÒ!Ž[¬;ÏY±å-M’\lå[„„ÑQ¯ †¾‚<Ó¿ÏPß’3+®Œèõ´ò”­s“¤ƒ:Çq¨TÎ#Û¹m#¾N|O»bNAEŠ^/¢5;z¿ñB>#hÍJÚ»Â8u`WÄí·ßÎwÜç5¤:¯ èiĦ&³°’Š™$À:Àhê¥R‰O|âDQÄG?úÑa¥†C\•Ðߎ”xÿ æ5YœóúKÄìn"vÍWÝç†@FŠj滌O.ç yU»æçÆÚh,%g}yÖä3‚ÎbD©±r½ï'ôyäãʈr h­ó/^<¤°§}•ÀP$§3![³š igwÄÂf+µû‚ùͺ $1rýúõÜrË-lÙ²¨«õod@7š p#ÀdV|`Küÿ$ “æFB†!ÿøÇ±m›s?øA\ÛñK-Lí¶%¡9+銉oLQ/îRV "Jž.E+ÅîôÝûÞÎ;‚ÃæŒ=@lÇYñF)[|wÿKÎ,¡É€Úã&3ywøïŒ7ŒGBóEèß_o¯Ÿ2xðÁã8ƒÿ~¡ïñÂË9xÖaé ^)˜·ØÞ²B9©ô¾5Þ-/ïÖ|Í™¾¤\.sà 7ðÇ?þ±Ï÷êsðÎz`*b2+«íÀf¼uƒ¹Ù•RœþùäóyÎ>ûl,Ë¢zÉ‘º›™‚0Nr+Š’§Üо¢èi³’§ãâv”<ÅW×I9P„!J™·83Ì””õx—æ{ßnr£q¡æÄl€½©¶ÀÕÇÌÚ?Ò ØH²¼ÇUö;‹P êM–.]Š«Ûý l­*ź§ŸåŒãÅN¥_ŸûÍ’m]AMµHcaæõ‚›¢W¦«ќ髊Üzë­ÜyçÉçë(ü Š@G½2•0Ù€?/ €á_G˜›7Š"þñ?̆î,GýÙ[)P®Iv«q׳P7?1•J2¶ø“ ô˜oÞ‘PRpävŽôœ£c¿ùšr3<Øfó|ªWbä‹8!’‚œ+(6¨î@0–wÆDJÑSQÌ)4| Zs”æ‹Ð¨ß59ì°Ã` (ë×­#ˆþ2Àü6 Z,þôj3"¦·ôÍÉKÐUR,ª‰ÏÜwß}|ç;ß¡T*5Jøƒ¶þ÷4â@S“]x Xœ‚î%=ãh<¯ÂW>>ù—;yÍÑ'’±u÷²ùÍš¥¬à¡Mµé‰#Èʼne&PxlS…•Ï–ùË# D‘ê“ .’lõêOšŽÕÕ8Ø Ž ½¦F8c.wÞÑJWÏ8¶ã Z³Kz+ªî%ox ù|Ä]­Ï?»?¥R@sî4[t–¢ÄVBbkN'²îª©Ø´q#·Ür Ï?ÿ|#…?蜰À(0Ù€ÿÞ„n 4:ê´Œ½{wñûï^Ìy·ßÉÒeKû mó?ìûºïOSp%A †î1ƒÛT‡éPBŠž¢%›Þ9ç]Òi•F½Ðœ•86tïÓ°^8ì°ÃxñÅ Ãþù&J)6<»š -ß{Œ¹ /&}Ê»é%$fmA[N°5î àW*|ó›ßäž{îIc8»ÑÉá3!&«Êàx øotYà !O>ñ_¹öjº÷v$î{[jÆ7]o.â:s¯æ (¥Ó\ìf– `”}Æ'+,©“Þ‚PçK¤‰‚«¹L8"­2LÓ°§á5 ÿ¨£Ž2 °cã‹T|Ó'‹Ò–Ó¬Œ»zÂÔÆ`hXæ7ÛlïÒ•?¾ë.n»í6 aqÿê@´°£œ*˜ À×{ãÿ`u„á€ÿþ÷¿Ïý×áû£iÀ%jÜÌHÝÍûÙÏÒÞÞ>ê}¸Ž.}ë*ÏüLÆ¢ÊØ!IJÓ²ð\KWc”|]Õ‘&Z²RóC$€úgÅŠ455é£ pñ£(dÕŸN¨xDð¶Z´w‡ÉüH-‘‰X÷Ûs÷?Låø1z¨òÂÌ`„˜J ÀƒÀg€â×&ð<¥¤Ë¾õæû¾×H%àÑGå¶Ûn”C}0¸–ˆëÞg<ÕR@p$É5IËõ.4¹’JÀ¨:6Öm9w'4[ê;Ï_ûÚׯ<ý¡¢ˆõO=šš`°¸Å¢£TÓÏ1¥pÄ£ý†?ý÷MÉRRDv1£ŒSM8¸ƒjb`5ûlÃÜàJ)”R¸®ËQGÅgœAkkkòÞP B=qÍ5×ðÔSOâ:i0ãˆÔÍ&Léd•ô(-ÂhÊj¾´Ã­9]o^EçÈýÁÉ'Ÿ Ÿßþæ×\zÉ…)i­š7£9c±­+dÉ»¡wM†Ü}÷ÝÜzë­ <ê€0§½ Qc*+«âÇ›O8á„OJ)Ï\»v­[.÷í$œ†B0Ð1ÍëÙ³g³lÙ2^óš×°bÅ Ž?þxN8áæÍ›7èþ^÷º×ñ­o}‹cŽ9†›o¾™W^yeÐãÔ=à  IDAT_úÒ—xË[Þ2d-5 Yÿâ8s{Òägz Ð @SF°³GQ ®Þ5ÉÅíwë½ÞL|ƒA]2ÚS‰ðE¦Î×ÄqŽ=öXÚÛÛ&Š"Ö®]Moo/…Bãy’ %ð¼&ÉÖÎ8°¿Ëã?Îå—_NEÁ˜ª/§9€ÉŠé üö±ÇË?ú裧<þøãó{ì1Ö¬YÃ3Ïð.¹ä’A]•Ëe~ÿûرc'óçÏG)E%/P±•]cûŠr ¸±¸½@o+ûf›Nt •6¢H‘¨_ñxµðd°¥`gOÈM[SIgAƸ¶î&×&cë\$ר–À‘ºÜÓ–z?¶„§×¯ãö[®$„1e˜æ9tÀŒÓNÊ"­ëèìîHÑŽfƒA°,‹Þp —˶ë—C£”âå—_Æó¼~½Dbè8óîž0Þ>C ,¥.ïŠ"RoÄcKA!#(yZh¥Ù› -/ •J”Å}1—úÀÊfu£*œBïx×Yü÷]wºŸç_z™Ïõ?ø¿ûq*±ûÝ‹ÝïQÜØÑ<H©¹#µpv,-œ ®®xpbÁíZ×é+ÈÝøý‚+øÎÃÝ,Ÿçò–óH!R3Jê¦I£û½‚ àœsÎaïÞ½QøìJ{“ÓQh,qö>°¥ Š jk>$/ZÈÑþwl{qu]nt³Oß÷yöÙg9æ˜cù Î4ß´'ýš÷‰„¼+P@¯—v)  9#é.‡TÍÃß#Pëß’•XJÁÀ×d_—:@¤JÅ–¶?jâÞɶ@y¾Gµ ^{bŸþaBèíÚ˃+Á‰oÿ¹ŒK“+Èdl…-q­Ank÷»“XãZ °¥»ÈØÒŽó`q«Mg)"ï•×]£)]q2Ð^Ï;ï<Ö¯_?äñRD-ýïoRˤÇtTR…¡RõÂ…•ª¨kÉgY|äIäóyŠÅâ¸ï¿Ú;=ä¹çžT莀¥ØýéN{:à˜ ÈÑ–\š¡¦)¸‚P©1¹ÞÇ#Ñ­Ökf[‚ö®ˆ{ÂHQô%/N| eXG±›] rW£ØZÉ‹Y`[U¡ìÚš 1k –½édþ¿#åÅg÷˜íÝúêù_pÖßÿƒv©[KhÎøfõ%[ÔfñèFH)ä “Dôùw OÝ~ûíÜqÇIÄ hý›a¿?f°˜Ž @-@ÃáZ)DÒÐ$MdA¾m.'Ÿöf~ýË{êvœ(ŠxõÕW}_ÝÀ$6MwÀÝLl–RìÄgdI!&* h_«¼DTb÷¸¶®ËADÑ×®ý’_…W}ÌJ3÷CŶ®=ň§·{HÊߤTØqR©m¡-n)i΀ck—zƸ–$ãÄ×׸± N¬ï8nI°„¶Ä-©ù.ù úàûyÌÌë;Ú¹÷çwóñœ;‚+« cRìDŸ§Åm6+Ÿ+SòwlsdãÆ\xá…”J%½ë‰ëþï~ö ¦¦£ÐEQ4R:àñFÆÖq¿²ß7+7 äA¦ÐÂk=¡® €RŠ-[¶ ù™‚+“Zä4ÛßNTY#µ:.Ío’¹6¶I7· AA­ç=Œ¥—º©X(yPô#Š^DÑÓ^/ˆ“â|…'Äù¡ê®]ânœÄÖ”Ì)Hš2)¼þ`—Y9©?'ºÙÆ‚«Æ•n ãNIÜ]f¿}ßûøçK.¡½½½ïå­9‘§žzŠ;3¿ýÛ¿fo"9ïýÅ‚‹J Ø[Œ( çœs;vTsê& ð7“wð¿)eJ`Ú)QuI)ÃFq‰ï‹Œ­¥F64 YW’É6±`é‘u=NEttt ú¾ Zk><#®¥çKÑÓIdÆ…<&—úD0Fñ*Š¢i‹;Ô–wÉ(ùŠÝÛºþg]‘ß½(¨ø:9.4¥fJÄ–¸B ’Ò2Û6%fÍIÖÑ¿wÖd-‰cëLt“ôfAn¬p t©¿ð\»ÇŠ…. [¬qª¥©îe(‹<“Épá…ò¹Ï}nÐ=mÞ¼™;3¿ù›¿¡Q†FKVbKØÕ²¨môËú?ÿó?óÈ#$ Î& ð‡jóŸg€—SË”À´S¤”¤Ø9ʱôZ Ò"x­"[ZM­C7ëÙ_(¥†åJw-mgy×DÇp‚<çš\+ÕØn­K]űñ@‘$—–}•Xß%_[é_ÿoÜìe?¢hK<ulÌgg0BL;芢(L' ç°m KMù>Ó±RE(tãÁjœÇÃíÛã®ÅT3Þ÷£]8ûrt½—0·i7z%PlëyàEM`YŒKñJ~5V^®©5¢ê´¢»ÖÖ¸Ž}»– )+™ck¡±4CeÖ•dk¶9VU°-ÁŸì¥5'y빸ms_!n<ããYë›äV«&µæ$^% b¢áÝö---|ö³qÅ—2nغu+wÝuï~÷»ijjªÃ(ª0×û€f‹Ý&yod¡…;wòéOš½{÷Æß›Âª?åN ñ¦(¦†a¯”2J#`’»\©]Ýißj2vÑVBêK]M};Ù™ùD:+½'¯yŽ{½ˆ^z*½žv­—ãd¸Jl¥û5Ùê ™•‚_*'¶q§gAkÖJ\ê™Xx’—¬­cãF€K[ã±%.bKÜX߯L7g%A¨p-È:#Ÿ/†¼ftÒX ô@SFúúÖ†FÛ¶¹à‚óùÚ×¾Jwww¿÷ýàƒòÃþ .¸ !ãZÔjóì?ÃÈ.ø\À /¼gbZÿ5㪿ºÒÑÔÁ´S€@)¥ÒðÔ&wUØÍl0H¡+zÊ>år}[$ìKÔ:æ›qĤn¤”bcGÀ5+;ñ#Ó=«ØFÕÞ[Ê$a-c \GКä\‹¼#ȹ‚œ­ãäyGò\»Ïúv7¿&ÇkæÙÇ×…0‰mUJWãPHz<®ýWtMY"ì-**¡¢0Šoг?b4eô|é.k‡LÓsöìÙ\rÉ%\vÙeýÞ3ÆÅž={øÉO~™gžÉ!‡R÷1-n³xhC…²¯È:Ã_ð¯}ík¬\¹’pb²ý%¨×`øö¢31¦`YVH’rŽÀó«€´¨o-!ÈÙ‚{êÛË\A¡0˜ÈÐÂÅÕV¯zóääι‚“–dÈ»Z€çbÝ„èÅ"‰‰[qŒª<‰‡£?SôÏîôÉ9‚Yùý•t#Ktë÷­„ @²«'ÂK•JK_×¼#è,E‘ö5Žãð‘|„oÜx#»vîì÷¾Z÷ß??øÁøâ¿X÷1ÐbQô#:ËYgè‹òÇ?þ‘o|ãtwwOhá_…Nüû}Ú™J˜ví€RVò®ö¯x:rN'{¹ÂgËÆ—ãqÔo ³gÏä}Lۂ挬ÒÞÆc #íïõt·3o‚' Î-Hþ|y–“—d9~‘Ë8:Çfq›Å‚f‹9yI[NÒ’•\­dí*½«+¦WUÆÒW¨”œ·¢OòȨRIF–èÖï[ñg[b®“¨™–ÌBçì­DQzc™={6—^ú…AßB†!wß}7=TÖÚY9‰”$”Úƒa÷îÝ|îsŸcÓ¦MuÓþ¬IŽãø…BáG)gÊaÚy|ßï´,+B¤RÚ‚Ù„TÛ¤A ­º¨ÜÍËÏ<©GQ§UÔ²,æÍŸ——éÄ5?Tø‘Âó¡××Â}go@wEqç=tWâ$·@Q‰“áü6ìöë2Æñ€™SöAióÞàInµÈØÚKPLZ%ïó©:%º „Ö¬E‘*1‘Áì¼Åæ>m?Çqø‡sþžëo¼í¯ôïªiî§5kÖðƒü€ã?~OØ8ŒÇ´e%ÃT|ùË_æ‘Gt݉ný›±Íž=Û;ÿüóÿûŠ+®HyDS ÓNˆ¢¨Ó¶í0-áÚ “» iãÇb\ÀAq/®~¸®Ç •`m÷<®ûug\;ó³£]P–¥ÜL›ä=®%hÍJ¸‚&Wsµ;ýÁV›Wê:Ú±ctëèàInµÈÄÞ^ßXþéÍÛÖœ Rª¦R#…±Äwv^òÜMó¿‘Âx³fÍâ¯Ï»”[>ÿ ¿@5¯ï¾ûnN9åÎ=w$ cIœw0¿Y²³;Š·õ_Z¾ÿýïóãÿÏó&¼ð7ãs]—·½ím=]t‘7£Œ/¦àºn7)òðÿ³÷åaRTWûï½UÕëlÌ Ã"û"#¨È¢²"‹ *ŠKbL~σhLÔ/FE#QP£’E£á‹KŒ¢AÐq#²…%È"ûÃì½VÕ=¿?nUOÏÊÌôôôôL¿ÏSôÐ]Ë©[uï9÷ÜsÞ`Tá#o¨Šç éÐMàèþ(>y0¦óœ ç¸èü~ÞÛƒÃëàp;*ׯ%ðõÁ ¶Õqç˜t0+;:° „'­ñ°ãìüz˜`š€’"ÖnÎ*B 4F¬Fîàá–w¨X›. EÁå®ÄªQS±kíŠ{D¾òÊ+¸øâ‹1hРæ—Äj—.é Ž”ØU5«î³eË,X°§OŸnõʨœýgeeáp§¥¥e#Uþ·YÑî ÆXP!¬Ó,£Xc™Ùœ³Š“ØÇ×Ý«ÿBd‘¿]ZTΤu³’Ƨ[¬Vž¸_'T„ä:º$‡‘\ì¥E§±üõ×›tÏ ƒ$Eq:TÌ™q1²ë)jo B·Cè0LÉ€WyÓ!ti[pª23 h¥ºX'!Í)ùôýa+ø.¶Xš“Ã0¿NµV lIôìÜ—\ÿÙö|>_ åjÿýÕW_áÏþ3üñ¸-tÉT±éh¦ (QKQÅÅŘ7o¶mÛ—ë67ì6TcÆŒA~~~¦a½‰h7c,yS…ZÚPVVFö Ñ,£†Mè"ûyTÇÚÇlžsSÈõí ›!¤b7L‚ß øC_HI©Âæf)q¿^Y ÅN9cÚͅn×wk2w;/ÃíPáÑvîž 5g-ÍhرcGdwÈŽ´ImÎ £ÌíênÎèšóíTùòù¹U†b¿Œ¾—<‰€¤øuYÞä³Ä:ÄéNÎdÿ$S"…¯‚޽ãwü/-x²VƒÞVh¯¾ú*† †ï~÷»q‘%ÏËQ"” <•ò /`ÅŠUdiͰåóx<¸ÿþûªªž·gÏžO!ùRh´; ##ÄÙt¿­Ìm^%›*?m˜V­ñU%lVV: è_ˆd”À© Š0ðæÆ UMDÖÀ‰Æ£ùÔíúá.‹z5Û£Âã`ð8X$Õ,¯®ÉýœÑÅP8­F‹ŠŠðûwÿÐlíZ8W0bĈ³®uƒÉØðÖÁÝz]ý- M‘˺ HÀ[BV»­T@ƒ#`ap%Ì‘å‰]GiP’&)H\„D‡ÓãÁ¨k¿‡¯W¯Ä¦M›jõ0ÆPZZŠçž{ƒ Â\Ðì²d{eKœñ›èà‘}héÒ¥øóŸÿ ¿ßŸÊßç—\r FŽIDĈ¨OÿþýU¤ €fC»3JJJLoZFLÎØå:‹… "'§9ëp<† 'ÇŸ@¿\`×®]X°`>œTÊŒ‹¿øÅ/Hg-u;sæL£`ÚÚ°³¼ÿûóؽ{w³³¥@Dàœãñǯñc ªªž·}ûöv9qÚ¥ „ šåie=›;Óç󡸸'OžÄ±cÇpüøqœ8q§NBYY ãìZA.%´äÌeáÂ…øÍo~Ã0ZDùFŒ4øÅ x«° –x}—PØï¢S•ï‹_'ð–@x5qX$ÜBKwp*Â&]\;Ç«@Pì—ï®ÇãÁwÜ«®ºªÖý£ûߊ+ðÐC!Ä,‡ßïÇòw^þ H.׿m$Íœ9£Fªñ³õyÁ AƒR€Í„viI1ÆŒ1"¢TgΜÁîÝ»qøða=zÇÇéÓ§QZZŠ`0]×aš& Èt¬¼ªBÓ4¨ª —Ë…ììläää 77]»vÅ9眃nݺ¡[·îp(’Ü¥%r—ž~úi<ùä“(++k‘Á¾ÆwÞÙ ýíudÎdZc¤"`{Mþ¯‡*3C‚:AˆTLìâEå!™–èP÷Ò]’E²,H„fXÎk:²Ü’$©°Â´Ê6½zõÂÏ~ö3ìß¿»víª7àµ×^Ã9眃G}4&R£•+WâÏx¡Ê5’6íïYè~‡¶K½´Ë†dŒ• !çœ8pë֭Æ °sçN¢¬¬ ðù|ðûý‡ÃM¾–Óé„Ëå‚Çã×ë…×ëEZZJ(ëû÷þQqþùƒ0xð`dff6ã]JÜÿýxå•WPRRÒb³"Â9眃믿¾AûÛ㳸 Ê£YRV€Æ‡"³Tt“ý± IDAT"©¤‰Bš“£"$nx4†4'G±ßª¬ÉWEÚ£1¸5ŽSÕ*ñ?÷Üsxàzã„xúé§Ñ¹sgÌ™3§I2lß¾sçÎEYYòÉÛír×]waàÀuî'„蟛››@ж…vi|þùçX³f ¾øâ 9rÅÅÅ(..F0¬÷¸†*ÐèýB¡B¡JKKkì·{£_-OGFF222йsg\pÁ9r$.¹ätêÔ©i7 ¢¢³gÏÆ?þñ%‰žý{-¡õ‡‚ö/MnçXq¼T§ÇVÓö¡„É`ãP‘N-+¢oO…ÉL°p´D§_|x†¶Ÿ¬ÿù¾õÖ[Ôµk×:ûiôw¹¹¹uz***è'?ùIÂú|ssæÌ!¿ß߀$„ °n–‘)ÄŒ¶ð2€›¤G}GHÒ¨2ŠZ+´×ËìàÂ5kÖ`íÚµÐu½Æ>-ûzÓ§OÇÔ©Sc:—SePPj9ù›v!#£´´o¼ñþþ÷¿#;;cÇŽÅÍ7ߌI“&Áé¬{2cŸË¥Êô¿Ê€Ä½Ê^·¸ì±ƒJ&U„L ê‚tC44˜óÏD”¢Žm¥ÀLßà|Á€6<óO4¢×¸{öì‰gžyééég9ªa*¬Â7¬  Z<8dÍúÊËËñÞ{ïá†n@§Nð¯Ã¦O—àLI á³»˜ã)s–›£"L‘ª€ ‘„ä{˜ãUP0XØFÇ4¾05¨p“íX´hn½õV8γzñt]ǦM›"ÿ?Ûþ­Ï?÷†€.¯ƒÃ©2¨ «ÇkBÑEŸ†~öÙg©1>F´…%€twèný?õR´4MÃ믿Ž=zÄ~2ÀdA ƒÁ²={íïqRµ%¿ß>øøàpEÅòÉSñýïÞŒ©S§"-- Š¢€ó–±å+É€8º\Hl=ÑÁ«À¯K–Ä4Š ˜`/!X/d#e霡À0ò€×É!ˆ`˜²|rÐ „ )gȺü.  ̼ïy,2ñùò· ‡êg$Mv|ï{ßÃôiÓ jMå¯dz$¢¾—_~¹@MŠÕŒ¶`ü€áÖßëµ)4Ñë”úÓŸj«ÚÕ$“Ž3ÉzWäkáZÉ­ÕgxÂ4ðÉGâ“>c Ó§OÇõ×_©S§"##š¦AQâçµà4GP—A[¶œ±±‰™.YXË&äx+‡IÇÛHE^õ€)&ÉOCȈô€ exȲĄÓAƒðÞ6?œ “‘ë  i$ëËP‘ï< 0†Iw=‹ P°nÅÐCm3À½c—îxðÁ‘“›멲Âáp/[c—ªý"Ù €4“d!¥üãŽhåÿë_ÿ7Þxc³QßÚŽ3YX%` Sr¬§Pö³øðÃñᇦM›†ë®»S¦LAff&œN'´Fϲ†4‡TnvZb¼•}Ê<Ë­ øõªF«¦È [ ‚)Ý$tBÀ°>uBH·RÏt `uD¼nJEnZç €ˆ2Pá ‚€Â . œ*Cºp© ܃ÛÁà¶Úfz²‚Üàÿ½þ<ñhþüÇE¨ª<=nÜp÷“È?ï¼XOI˜¢(ƒ‘2bB²ãœ›h!Ú¢;ñí·ßŽûÑÅ~ηƒ!lt‘2êBmk¿Ë—/ÇòåË“'OÆÌ™31qâDäääÀívÃápÔ8¦©HsJwlE˜U¯)³r ª27ÉšU›ò „ cØQF@–2‚º@Ђ!¨›é@HÈcíÙ¼I€•±ŒT^™âPœ*G–‡Á©…Ã¥.í2¸5‡*³TE÷Ɔ tÊà¸a¨òæ}ˆsûï¨*˜¨j@=ûôSèÞ%O<ñŠŠŠ’:ÍQ²Ïúáÿ¢çãá Ò±õkÆEé×"¶g$»0 €½ÒqBôtÓM7aÞ¼yÈÊÊŠÓµ* …MÀbün0¢ŸÓÇŒ?þ0qâD\{íµ?~<òòòžž^/ùP]ˆ^÷:9œ CyPÀ$‚Ú@ Z‘É Â°I€nÂBθýa‚/$à Ë™yÐrµ ë8À0¥2/ Ö aóÑ0@–[ËT2§&SËÜ¥)pi .•éX¿irVîÒ¬™9cP¬¼óè¿™“Î*8·nGÞ‘4Š:¦søÃ¯³)q"†ûî»ݺuÜ9s’6Ý/ú}œpŘõ½ÛqÀHCy0抖 ˆ¨Ÿõw’ZG‰G²} ï!åþ¢;ñõ×_… "///Ž×“l€D !WÜ.ÕæP=xÐþnÕªUXµjYŸþšk®ÅرcÐ¥KdeeÁår¢!Ý'Ú£îPdY`_ØŽm!Ëe6!S*r¿."‘ñþ0!`„u a}£ˆ[^PÕëI+'\‘DnC®Æávpx é†AQ€‰ýÝÒ8QåÌ\aRaskö-gáöú»œ}Wþßj¼˜“Ži ¶ÃrY q¨ t»ñÆñÎ;ïàÝwßAšÄ£gÏž˜ûè\döé;(˜èš©4ÊsTc‰ÈÉkÛQ“qD2d'Zˆ¶ [ù+Š‚Y³faÁ‚èÚµk|¯ 9+cÖšn MC]ÆÀêÕ«±zõj0Æ0vìX\}õÕ¸ôÒKÑõœnÈÉÉÃåFØ Ëm^¹´ÖÉý!‚O'u‚ 'Ê ì8†!ÃÐ#nuDfÆΙt“sM\ CšS*p¥È½àf‘Á¸"Ä0RùsK™Ú3o[i« é ‡ŠLôÉÕ,¯‹I¹Dµ$ªžýˆ/G@|aB†«éB¼ùæ›x÷Ýw“r À–Ùãñà±ÇÃèÑ—á`‘M‘ñrŸØæmBˆÞáp¸3€ƒÍ"t;D2yÿ@jöØø»ßý.æÍ›×™¿ ›XQ*B)’¯æ@mʃˆðùçŸãóÏ?ô< FNÆ9ùÃáÉ>žÌ<(NwdFnÏ”U.×»ªt½ !ã2\M…×ÉáÑÜéb×T§5sw¨rMÝf´;môì;ÚËÝ©Ïd˜ãU°ý„.¹´hå_SÉ4næY=¨ðìÈñp‚PÈp5-=sûöí¸ûî»›tl¢a+Æî½÷^ÜpÃõ¯ƒÁëà(ôÙ<± ÛœóL—Ë5) ÉHf@b‚Š3Î=÷\üèG?jåoC³Ö\S@Ëaÿ¶µØ¿m- èHŒw%.6½{õD÷îÝ•žfÕi³ò4'ÚAü÷¸Žë†x‘—Æ#©m6jÞ«Gæ7T™/Šªª=Û#y ü!½ªéP‡ ñC†‹ƒp¦ÂDbËËË«Pý&Óì?Ú[qóÍ7ãÎ;ï„Û-)­]ª4‹ý2î£è¬€|Çz¢öŠd6ÂRÉâqÆ–-[°páB<úè£8÷Ü–I¸Ø)@¢°kë:ìÚºÿ`äÈ‘˜0aFމ>}ú gÏžHw§ƒ1†l‚@8 !¬¨ìg4•3€UÑçÑgÈt+Ð…¬"Ù)­ §nFxNá´¯iïïc=†¯¾ú ’Êý-ëe—]†|°Ê’¡CeÈt1œ*7á 8ÜMŸ¿ !ˆË5¡>±ÊÝž‘Ì@ € ëïT``wè·Þz ååå˜?>÷ëÊ€/ÀŽû¥R¨ö³_·nÖ­[1bÆŽ‹#F _¿~pf÷DÈäðéqÆÅƒ3 Ã)ƒýJü&(GIà`@p;82\§#®î†OK–,ÁK/½ y•ÿ€0wî\ 2¤Ê>· µ0|aB–»±Ë1•à<]3©@{F2Å ­¿SÊ?°gjD„eË–Á4M<óÌ3M6j2¬Ö>0*ŠÌ½¤‚†êA„D„õë×cýúõ€‹/¾Æ_‚Ï@ôFöèÈîÐ!QâÂëdðXe9 ’ ¹Ž"_ã謿ýö[<øàƒ’‹0Ú ëÒ¥ yä\qÅ5öãœ!ÓÍ ÃŸÀ9™±øÍ7ß8Î?ÿüÔt¡ Hföˆ-«4…:m¬X±œs,|öYœÛ¯¿‹†vàšË¿ö*‹|0+Ë¡~] ¦ ™èK€H’Q[BmÆÀƱqãFÀöCñåe#1lØE8ÿüó1pà@thQc€ÀC–›£È/šnëÂÜ4‡K .—ðÀ`ß¾}Öy’göÈw$++ ¿øÅ/pË-·Ô¶Àdæ‡Ê3ÍHDûöí{€1¨"Ù €õ>©e€¸!ÚX¾|9\.žþyœsÎ9ˆVâ@å e+lŠú•¬ÿ k’&¬â & „ dB:¡,$J‚kQ‘ò£%‰¬„—BmJiÏŽ­Ø³c+^~¢æi™¢ªj>R@“ìÀW¶C)åGDHK–,AZzžzz!ÒÒ3"tªÂ*˜² ¥H>uŠÃt Nðé@0,9ØCVE9ƒÓ¤¿zØ”3Ÿì @U*‰`’d\l·Ø¶m¶mÛ†¿üå/4h† ‚¡C‡bذa6lX\Œ{ÖãUpÄšu«\²ö% Yn&Å<õ§.[¶ /½ôÂápR*‡Ã¡¯‹nÚ~.Mf”†€C©Š%³ä¸ÀŠXNÔ^‘ì@À‡ÆB¥¼-„Åy Å<“n»©²¼©QÉèXÃfac€Ê94Å.~¤»:z9\ «Û!ÓËœ Ç·§ÂØsÚÀ÷†§!ÃÅ"™«²UìLè§P?*™Y·oߎíÛ·ã­·ÞB~~>ˆ!C†`Ĉ5jT³Ù^_Hòÿ'šB:Ý))„‹|}rêÞoÿþý˜7o ZN¸f@4IØ­·ÞŠ_ÿú×ÈÈÈ8ëq.•¡ƒ‡cïiaBvŒÈ’adlgi¿HvÞ0À ¨}RF@ `ÅëÏ#眾7ífIü¢Ââ\çpk ošTîšÊ 1U©Ló«/ú7hvŸ2îäÈr·L­ûšµ3îÚµ »víÂûï¿~ýú¡ÿþ:t(F…1cÆ4‹1íQ2¾°@‡RÌš^«êß)k­»¶hwÓ4ñøãGb)’eöMô3kÖ,<ñÄÈÉ©Çʉ‚Ceèàæ™„Ò€@¶'¶çdÉ2äì{¦PÚ‚°ÀRÕ¡Zz8ˆ•¯<‚»®¹Ã.Ö„3Pdý6‚NE~úuHɈºèˆ÷ìÙƒ={ö`åÊ•èÕ«z÷î¡C‡â²Ë.Ãøñã›l d¹@i@ [fb —Ê‘éæ8Síí‹/¾ˆ÷Þ{¦i&ò€ë®»Ï<ó :wîÜÀ£ed¸8„ z#^ˆˆL]ˆˆ1ÙÈ)4mÁ€µæCHyZŒ1œ8q÷Þ{/–.ý™™™Ó[»€Az¹¬lH–Á¼%Q›1 „Àþýû±ÿ~|öÙgX²d ºu놡C‡bܸq˜8q"²³^î#Ý*T0$n @º¥‚‚ŠÚ£Ý?ýôS,Z´eee-/`ý^Ϙ1¿ûÝï¬@à†Á6ö=š¤“.ñÛÆQLõ ‡Ã}ìmò‰Ú)ÚŠ¯Èð0dZ`e‘ïâŠ/¿üóçÿO>ù$𣹓KœË¥€dC²Er·4j3LÓÄ¡C‡pèÐ!¬]»K—.E—.]0xð`\qŘ4irssë=¯f²#Ìc­6×TØÏ¾cÇÞBàÖ*9~ü8,X€Ý»wWÙ¿5#ZÆk¯½/½ôR£ ƒÙÏ®âXˆ=€sΈ.—k8R@£Ñ– Ò Ì`‡£¦¼qB´¢{öÙg1uêTŒ;¶YέqY—ÝnÝc4c5j>ŒcÇŽ%ÅÀžhToÆLÓÄÑ£GqôèQlÚ´ +V¬@^^ „É“'cÊ”)5jSØïb¶G¦;ÉL“Ád{„L‚/$àÖ*—$ž}öY|òÉ'r¿$xGª—_´hQLµA<C¦‹£,$2(âí‹A>àRoÅt¢vˆ¶¶¸ð,€(µ¾« Kn#¨ÏešÕú`¼¡P÷Üs‚ÁXKsËG¥) jÖèÝ»7Þÿ}ôìÙ3æµÍöˆêÞÓ4qâÄ lݺo¿ý6~ö³ŸáòË/Ç 7Ü€W_}'OžŒì ¹^Ž’€L!M´ÝŸîd+ßáÅ‹cñâÅ0 #é”ÿm·Ý†?ýéO1si YŽŠ ¡,Ø,ý›hJR»G[3i¼`€uÖwÑl5I ÆX•@*èÛ·/æÎ‹>úãÆ«ò[K*ûš›7oÆ¢E‹b<›”ÛÎð…’ë‘qÎ1|øp¼÷Þ{8ï¼óRF@ ¨Í8}ú4vî܉÷ß÷ß?F«¯¾/¿ü2Ž?ޝ™Y&iNÉ_qÆŠX¿a^zé%œ>}:Á’5 ÑÊÿî»ïÆ‹/¾Ø¨˜Œº ) YnAƒšeÀB*<…Èp/¤7À⃈ú»UoVTk•­S§N4{ölZµj;vŒü~? !¨¤¤„žþyr¹\õoY³²²èÔ©SÔdùqÆgТ/Kéï›*ªü;v 8uêJKKá÷ûá÷ûaù­ª*ÒÓÓ#[nn.ºté‚.]º k×®èÓ§<OäÚvdxá|8ã7¡(*¤#¢ù"Æc¸úê«ñé§ŸâÊ+¯D0Œ{ê‘} ¼ú꫸瞦yå8܃aæLþHz‡Ã[o½Ý»wÇwÜ]»vÕÈìH¡yA¨lWûÝBFž›¦‰õë×cýúõøùÏŽ‹/¾×_=nºé&ôêÕ+æk¿·d Þ|å…JYZá3ŽfÏž ÀëõÆýºªÂáæ„Ò @§t%&â&Î9Гˆrc…Í*l mD”ØPa"Z²¥‚¬.¡°Ñ|3ÿÚðùçŸWÉh‰-??¿Éò¦ ¯èÉ–ЩòÊB2{¢±{÷nš6mZã}íq«-8ó¢‹.¢'UTÑí IDATŸ|’öíÛ×$ÏÜ×_Mçž{nÂï­!›¢(´hÑ" ‡ÃºÇXñßã!zæÓÊL€fˆ( ‡Ã—!…£-ò4B¢epi a£²„n¼0vìX¼óÎ;‘ÿÇ;71†={ö`Æ M:ž3Ù6 J*6À†¢ÿþxë­·ðÀDj¨“Åâ hYQþ Æ6mÚ„_þò—èÛ·/.ºè"Ì›7ß~û-t]‡išõžïرcxá…"T¿­={öÄgŸ}†9sæ@ÓZ¨~‚ÕÖN‡ÂP´ûwÓÞ{ûÙ !4MÓú7‡ˆííÚàœ—Û˜ ¸5†°´„W]u^xAº$)Î5ö úÆo4éxÆœVÉ`¿ž\l€ Ezz:žzê)¼üòËèÑ£€ÊvK‰AmÆÀÖ­[ñðÃ#??^x!æÍ›‡mÛ¶! B×õ*®ýP(„¿ýíoxóÍ7u u¢ú;5}út¬Y³£GnQ9È’#ÍÉàq0”LfÃŒüª«(‘çDÀ9çDÔ£Y…mãh×€¢D—ô8Â&ÁhõAÎ9n¿ývÜvÛmZÆXºti“wØô¶çˆÆm·Ý†¥K—bâĉà\vÉ”xD6¶oߎG}C† Á…^ˆÇ›6m‚ÏçC8ÆêÕ«ñðÃhyZîºP=ÎÄáòâîçaÉ’%ªæ×lòXŸnÁ­1”‡¨ÁE¿ª6)«òGؼ"dæ7—œíí:@ Q";ªGã0â¾`Ãétâé§ŸÆÚµkãî¢$";v ß|ó Î?ÿüF¯)² PÀ2Za U³aèСøàƒ0wî\¼úê«(,,¬2­®ˆRHìç±k×.<þøãxüñÇ‘ŸŸqãÆaóæÍðûýZÇ3‹~wEAþÀó1éö'1õÊñp8ÍR1‘0ë߯ÀãàÈö(8TdX¾òl†)«€úÃ_˜à×ai$të;k è’öY7 ºIJÈ@>fý]Á;7Ö¿N“€”PÊ9O¨Ù¡2˜D0DË ¹¹¹xî¹çpÕUWŽt-áŸÿüg# 9˜¨\ò…mE[ <æÏŸÑ£Gã±ÇÖ-[`Fª¼p+Côsˆ6víÚUå»D¢ú¬?-- ·Þz+~þÐ\üû¤§}¦µ_UÅ- ‚Æ)sõ/ —3L Aê@EHÀð…¤ØÆÀ© YWr,4 dÉÙ÷åx8—å=Èö*ð¨Ö÷*cnuýá§wëóÅÐ|ííÚBø9ç u·j\vR£ÍÎ9FïÿûX¼xq\¯%„À_|{ï½·GÉg¡)€CAT`ûP€W_}5Fމ‡~ÿøÇ?PPPò´RÔö,ý|¢ßMÓ0pà@<ôÐC˜5kÂ!³4€ÃEö€Ãª[ù)ÈòNÊOݔʻ",P´gç„ .¿÷W›­B7ÉžËp(œA³¹.ä2‹KcèÙA…C•F¿S‘AÀ‡ÇRö —ÁÁr“˃œ “±B ¹D? e4íÚàœ›H°VQ8#ÖâÕËÒÓÓñãÿo¾ù&t]Ûu„Ø´iSã²& *gpª ¾PíƒU[F^^þð‡?`âĉX°`6oÞŒP(å Ú‹A”BÃ`+~[ùçææbæÌ™øÕ¯~…¼.ÝP$M…ÅÛO„¡›@YP ",à·Ýìa9;—3uBØ „ˆ&g–òÕ¸\¦ÓT°ëÖ€l7‡7“Ã딳t•K/§Kåpk€G“}šsÇÊL|¼3€¾¹*&ôwC±¢ÒìY?³”}`L%bƒü+.ÜÆÐ® @*¨DÆ8T€qJH [Ÿ>}ðï|‹/ŽËÌÒ>gQQNž<‰Î;7è8²¬y•Nµ2 =â†nÀå—_Ž'Ÿ||ðöïߟðf ­‘ ?§ ½Ãøæà¼Ë®Æ›ß‚ß”"dZkåBî»xC8cÐ8ƒC•ŠÚ©2¸T†,Ã9Žt'ƒ×ÁàTyD™;U©Ü]Ö1¶²æ°ŒKqÛ΄ˆ2GÍÀÈŽ^‚Gcð‡ ŒIƒ¢ž;«k)2Àà›²Ý ½D À©2p–%—o¼‹/Ž‹R±ÏIDرcGƒ ûi(p« ÅSÞ~<ÑÈÍÍÅÂ… 1mÚ4<ÿüóX³æ+'Z¬Z!r»õÇà±3pÅw¢cÇŽpª ÞLŽ4Cš‹!ÃÅqÆ'°îP÷p`p¸T&½‘ˆVÖ•Ÿ@U…Ô©ˆÛ“åÒÜi„ ‚S­ï¤ º¦Ê9?¯é’µ/´w %2À©2(œ'l–;`ÀäççG˜âÓ4±wï^L˜0¡QÇ)œÁå`Ð ¹©´ó¤Õ+®¸ãÇÇïÿ{¼õÖ[X»nL‹Ž:оÑ1¯ÆO¸?ºc.»ô’*}%2‡ìSÇK ì*ÐÁ³(xcÿšr¼½¿K•FÉ‘¾°@†‹793Á’ƒhùÜÆ$E»RMÓ,E‚R]*ƒ’@²›:4Z17B=z´ÑÇq&… è-#ÑZÁ9ÇwÞ…7Þxß½ýté+³+¢ƒSh?HKKôiÓðܳ ñÖ‹1aì%piL®Í[›ÊåìÞö ¹5ƒ¡8’ `Œ¨Iƒa,ïc YnŽ N(ÚïpÓû:c BgЍah×EQJ… ]P¬`˜D‘Ýddd`èСq½¡   ÑÇqf§IA“Ù’ŒI ×~ý$¼ù“Q¸ñl]÷vïÞÊh£¨þ<5MØ1c0cÆ Üzë­ÈÉɉڻ޵r89ñ( V ®e,!a¶™n“€Ò@lÁ¾Œ1‹Ö…9\àpsÉØVÑ® ~$x /!éÉmFlPUµY*ŸÕ"BIII£ã pjrà „ ˆ‘²¤Bš‹¡ÇÀ‹ñ½«Ç x×j¼ÿÞ¬Zµ ¬â–MÉèg8fÌ\uÕU˜5kúöí[ËÞõ¯•;T†tCA¹ ¬?ð.þÈt2h ( ¢†Fý×fJN!Äp4£˜mí݈@AVIɇCB†åŽki ÒO‘ÅŽÖ80ÆàRä¬Än›õb×!ãGüºÀÄI“1eò$,[¶ Ë–-Ã'Ÿ|‚C‡*S¡SäCõg6fÌL™2W_}5nz »Æ,7‡nJ¹iJsˆÛd¤»8܆²@Ø\±k%€ b—¬í£½¦Í½ÎèpjQY BQ¸Ýn¸]£©\UdñµÁŠ€MAt€”SeÐBH'AàÇŒ30eÊ|üñÇX¹r%>þøcìÛ·/µ4D¨žÏ?aÂL™2“'OÆ!CšãÈtq0ÆPèK¼æäHs*( ÊthW½™õÃj3…sÞ§ÙlÃh×€®ëEQÌD³Úy°oñE‹‰Ðˆ€H‘›†C¶ƒC‘yÅm­$0Áöö4’v5jW;'Û§W2I "(ª†©Ó¦ãò 1ýêk°zõ§X¶ìCìܱ#¥ü[)¢—kˆ‡“'OÆÔ©S1nÜ8 8°y.dYi.‡úL-T¸h C–›aÿ¾°@–;¦Lâœ3"r‘‹1l~‰ÛÚµ iZ¹ÂLt €ÇÁQì7$»[äeM¸^Ãív7òÙPTjf¹Võv±£Êû$‹ ]DýM ’Å£ !ÙKÇJM¸TÉæV¨‘ä]ït^;¼ïDœ»y-þ»flûwKßn u úl¿S§N˜6m®¼òJŒ1}ú4ïD–¬@?& ŠüÒrLÔh_7ÓÅËwh|=ö2®8@#iHÛÚµ@DÅD¢S§¼VI`A%²œ83…ØQ]ñ_xá…¸æškp饗â /Dnnn|®k}:U‡ÆPne$j ´¯›ábT„ì¾›‹ë58ç®ÆÖwªÌŠ‘I¡„:¥+¸f°iN9×,†CåR¡+,†·¬&Á‹Ç2+BõåP×}A·Û`À€;v,~üãcóæÍX¹r%–/_Žâââ*íž2êGuîûó‚ .À„ÉÓQ–;ã.ìY£û´Øl¿v9,ƒ„"Ÿ™p ÍÉ‘îâ(ñËrÂîãc u?qâ„·K—.¾æ‘²í¡ÝBÃÊHX& Ce·° ÀçóaåÊ•">9ö¶²àœã¼óγ¾l…DDÖšxå¹Iq›BR$ë¡, °³@¬Y¶F0‹[}XÇYö¬Ÿ©­ž+Ô8&ÍÉ0u²‚H{ÎJäää ''ùùù˜4izè!lÙ²ü1>þøcœ8q"e Ô‚èvˆn‘#G⪫®Â¸qcÑ«Wo(îø`7àðò„*;À&ÝÅÁC¡_ ±¡†¾òr”£¸ô OÁÉÓ…¦ Ã4ašÒ•oš& Ãc Š¢@UUhšªª S—.èÒµò:æ!//™.ŽÓ:ü:!»RÌFÞÌ1Ʋ;wîÜÀ–övopÎËä%’À­1’kÂ-‰Ó§Oã•W^ŸÁÜ>Ÿ¦9àÉ닃gt˜$£×zT0›gJ#(hÕ!·k‘—åÚù;[ü((7›UÆÄ ¶JjÑp;dšd@—ÆTsdtÛ1;vDÿþý1iÒ$<òÈ#سgþõ¯aõêÕX¿~}÷¥½ÕïÓþ;++ &LÀĉqÉ%— //™™™ðx¼`L’Ye8ý(öËxŸFgÆ6ìL¯C–.©‘ püð!ìÞú_ì|8FŒ‘#GbÀ€p¹\p:p¹\gí¯ ²<!ƒà׼Ζeàa?Ö®YƒµëÖcËÖø÷ú-(,öA‡À •|8®÷qvB@‡ ‡C€’âbÀÁƒ°yÝ¿áp8át:Û c&LÃø±ã0uÚDtðV °=j+–‚…vopÎK¬Rq»ÆÙ”¹×)i9EµõU¶â¶Ý䂬ô2ƒ6€)SÍ S*ü°Iè²€Ž;n˜Öúº*ÊÊñæ‚GPZR·{¶¡* æÜ<“zš|™’F¨¶N¥‘H8TX0­ðˆ¦®6ªªF ‚ÜÜ\ôêÕ 3fÌ@—IgÐÉ-pA‡blÙ¼[¶lÁŽ;ðÍ7ßàøñãgU ñT2g;·Í—ŸŸbðàÁ¸à‚ 0dȤ¥¥Uº­5­ÑºÂ%ï½’¿¡cœ)xIbíšâ_Ÿ®ÆêÕ_cÛ®=†ÂÐu=⶯ uµSKnÑ| Á`Á $ö;}ú4öïýoýåE¸½é8è0\}ÓwpíŒéèÓ1#º,ð¹-*p’¡ÝBˆ ÎyƒÞꦦ FcXÊZ·Ý„eî…L©°-2˜ Eü°ÖÅuCcËÙ³|;ˆH–ŽJ'Ó¸t«+صi96ÿëÝFßGSàv»1aÂëM ~sX *™ÜšÁCšƒ£ÈoÂöZkbdQEqáœÜ,øÃçŸß ç„[n¹B!àóùpðàAìÙ³{÷îÅÁƒqøða9rGŽA P»× ¹`Ÿ»cÇŽèÑ£ºwïŽ=z oß¾èׯÎ=÷\äååAÓ4pÎÁ9‡¢(M ²® ÆdÐ&ã@qÀ^woÞçurÿ.,ûà|øÉ |½~3Êýa˜VP^c‚}[‹‡¦>’½,áóùðÅ¿Vàë/Vá÷yqÑÅ—àÿýðG¸~ÆžíѺQWÆØñˆßêÑî Îyƒ¹¢«ÌÊ…EàbJÛÕ2*•vØ „«}o¿…ÍJÅ-L¹ÏÆ#aì(Ða3Ë5rI÷êTŠ úÒ•Ëÿ»,JOû³qŒ&ÿV­5öÿþwþ牟Fî'žsŽñãÇCUí׬iÁoE ùS@5H—š‹áhie=€–/*m]Õ2îr¼ÇJåìRQ(JåL×ãñ cÇŽ6lXdf( qúôi ¨¨%%%(**BEEü~?ü~?‚Á È(¶ªæÜn7<¼^/ÒÓ3°á” s:àæËz sçNÈÌÌ‚¢(5‚Òì-^``ðh…ãŒßfà‹õY¾Ýôo¼ùæb¬Xù6íÚoÏ~kUø­yù¥¡¨-EP(„BXÿÙ lø|%~ž™‹K']Û¯ÿˆ+¦øSâ$n½h÷€BR±Z3o{f¡\5AÖ~–2è² [Èt! “Ô®‚"ô¯ –"g¨Áê–é²³ÜNUèÞAÁEÝœp¨r?M© ŠsªLĨr¼)8vìf̘ת6ìÁô¦›nŠá,rpt¨Ì tk½)€‰€­p3\’I²24Q´®ò3ËÅPªÿYÕ5£v8ÈÈȨQ義JK¹Å‡3>¡d$ñN¾Ë.•Áë@„ƒ¿)ÏŠH`ϦµXüÇWð¥Ë±£àT þu0¶Ôv¿¶áSV| +ßþ“gÅßþøG¸²oGÏq‹0üº¿ãõÛR¼Ú½ðú|F0\9›7ET!TWâÒå­ÈÓ] NUÚekŠTÔöÌÛi)q•Ëc*‹(x…öðßã!tÍTqQ÷³å×)i}îÄââb\{íµ8tèP òx€ˆàõzqýõ×ÇpéÑɘZ¨ ûY§;9LB:!Q³ÿh¤[…]ÂàÒš‡a³©ç` tô*Ø_h dÄVj6ØÆš¦.ŽÒ€€!j­y! ïÂâW^Ä›¯½‡mÇ "¿Õ7«ok ÿl¨ÍØaŒ‚EãÛ÷_EÁ†ß¢Ë¸EèuùKøzîi´úbMB»7+w;@Ù‡ËRÎ*#YP…4•‰0ü¥gPzæ|¾r˜á ôp$ 誦*ª ¯× gz:ÒÓÓ‘››‹:X3aD}¢†«Q™ÎUq–YSÝçªkŒ,))Á´iÓ°qãÆqÚ׸å–[ iM§ô²ô¿Œeà’ì&…šð:di› q ­.&ÊC.-±Y @n‡_—u\jËFÞGä°ž‰Ê²¬TÀ N‘Sí0M!)Vþí ¼öæÿaÙg£ÎW;ùP 5Õ>„’£¹(9ú0Îüç~t»è÷è2êil8}x§-Œ4íÞ¸f+×TFœÅE§±é?±uëV|ûí·Ø»w/öíÛ‡²²²&Ÿ?7'»vA¿¾}ѧOôíÛçž{. „¬¬,i pNE ¨7ÿÈ}òäI\sÍ5X¿~}‹­ÿEÁwÞÓyìÖ°=+-M””,HsÊe¡ŠPk1T&yÝ;¦%>m3Û­@7 eAlOb *²Üaƒà ÒªÚLzG¾ÝŒýo¿õœ,•¿¥”~̰{!\áÆÑM÷áô¾;ѽÿ3t÷ï°2»˜ßºè­ íÕÐ sDóîÿéçõ«¯¾BAAA00P#¼Evg-½ü{|°zccSJ¿ÙPi„J]8²ñW8uü.tû\#cïºr€µ‹Æno@ät-€›Œxýõ×#?ÖH QÊ¿®sD_‡ˆpêÔ)¬Zµ «V­Šüö§^½1~ü8\qÅDŒ1;v„Óé„ÛínðµÃá0>ýôSÜrË-())iÑÈ_;Uò—¿üe³S岂^I 9 µ4<š¬í^¤„T”¬U‘nîB_⽪ŒYY2*G‘%OKñ$Ô™¶i$¡@¥EXºäu<³ðE|{¨akû)4 ¢ ãpôo¿C· ~гoÇ‘éëpb™?¡ÒµÚ‹ `€9nCÕ9R$jª%•d]8xð^{í^{í/d±éÓ§còäÉèÛ·/ÒÓÓ‘––Vçñ%%%x饗ð«_ý @Ë"öµF+®¸¢ÙΫpT®HLÉäÖɬÈQnULh ¥]³=\zÛåœ!ÝÉP@ ©¼Ð}Øûín|ù‡7ñìK/àd…ˆP9·Dn UPiÝÒG÷}Šî翌³æaô'ð§‹õzNb´uÀ ©øïð½¨ï£G€¯˜Ö{زe ¶lÙ‚yóæ¡W¯^¸æšk0cÆ ôïßÙÙÙðz½€P(„o¿ý÷ÜsV¯^9OK+Î9ž|²y)†Ë`˜2`2…šð8ʃ•l€‰‚]h&ûÿ³wæarTõúÿœSU]½ÎžLdƒ„„‚@}qaqEø]…‹ *\܏РB\DEYE6DEð"rDAö-„„l3™µ·ZÎïSÕÝ“u2ÓÝÕ3™÷yfëîªs¦êÔùîï7iðz—§Feq‡==IO6Ú2I¥¹Á–¼ðOÜòSýò&úÜ@&¤OþÈÜ„~Á’GO!Ñ~$™ô7xÏgÓ?ízrµ@ô:µC'ð%à† hP¡_‰µÉ.Þ|óM~ðƒpðÁóÁ~E‹ñØc±xñb®ºê*öÝwß’ðª¹á1ÇÃ>ûìSÕsB÷Kð”B—<Jôé˜&J ­È¨„H¸êZ“’Þ¼Bwtɉzsa¿„ú#7ÐÇ ÿ|ŒEçÃAìÏ·ÞXþ0!ôeM,×5…¿ÿìz_û);>¥^nl.Æ«`gà€C+^‹¾@z„XóÕóÏ?ÏóÏ?ÏE]ÄÖ[o]êêWù™z!¯µµµêÖx~ÛÔ<!€¡-î´­3Ë]¯\û%Z’’Á‚&ÓJÆ¢‹&¥ þùv‘¬£ÈÔ± _17ÈkÏ?Ë]wÜÊ¥W\˪þÚ“pM`Ô(‡”/xñþcHu.`§O…CÏþ_îûŸqC$4€ýk€9õ÷™ IDATÁß%>ŸÈfTE¬­ ¸®[þQÄ+•óÎ;Y³fÕdÛÄD`m„‹:cK\¿qÈ’šãÇÓ\ÉX´¥wB@[Ê àÂ@Á'S‡Ž’Ê+òê‹Ïrï¿æŠË¯â•®|&ûÆBo€`pŶ¼ðûÛÉíp .ý Oü×’¨'W Œ7àà:`zð÷˜µú‡ƒ µ-‡r§žzjÍίûP“ž÷ãMq-X²E(#ö4Ç%B -u‹ ’ð•¢'ç³USmÇ[úÚ‹Ü÷§»¹öª+xê…7É9Gf"±o,¢ì ðט,~úëd=Øñýgóï?=é̪€ñ¤ìüˆ-Dø7Bk¦³³“K/½”x<^ƒQôm´LDLälMq‰šƒ?êBÐ9 K—nF !© ‰Öšlíæ3ؽœ?ß{?»þzþðÀßp¼rrß„àóÐ7ÒË –ÿõ`rSoa÷Ï|“î¿‹óŘ%/ @'ð=`^ðwlã•YÿßûÞ÷ªFú³ž‘í0 y–{£"e Š:0Z› C‰Kº³Q >½RWJÔ¤ ¯ïðè}ÿËí¿¼…[nû]A˜ÂÝ?îP ¬Ü‘¥‡‹ó~#çxLrŒàKÀ¾ÁïÂ¿Æ¨ÜØN;í4Ž?þøÚ%w3´@ö&6Ôõ"“Ä A^E& ëï[ã’ž\´d@a %.Y“­.ÀÛ/=Ã/u;7^}Ͼ½"8wãÔñ×›t €^4ž«x«Âš‹øY÷$>ñËËùÕ1c®Tp<({G6¿æ¨ô‡vßüæ7±m{#GŒaC ˜!ˆ"ráÖ¨°MÍx§CÑ>áiKIVD˾Ž)…žO×`Ðîs´“q¹ã¶ùùÏnãÞ‡þFÞ‰^ð¯O‡k!‘LÑ9¹“L&E:ÝJû¤6Zš›H&ض…aš¼´ÒEÉœI&¦ÔÇz®‡ë) dóyûúèéêbÍ`–B.K_o/«V®ÂWŠèyë í pú›XúìW±¯Ä9¿½K>º,ê‰mƃp<°}Ô“Ø’ ”b÷ÝwgáÂ…tvvÖt¬RC C3ÞMT¬z“OÆ¿BIŠVhKI^Zéàûš?JÈ€ à.¼«ˆ[#¿./?ó7\ónºí—,ë.ÑXÀk©”i’ií`ö¬éL›>ƒÓ¦1©£©[oMçäÉ4eÒ¤Ò-tLê ¥9C2‘À4%B~÷ì +û}ŽÞ%E[J–óm æò¬ÈÑÝÕÊ•«XÕ›epp€žÞ^V._ÉŠåËéî]ê·³ú·éYõ6ýŒóþ]0˜àí'>ÏŸnhç´;¿ÂO>6f*ƺ0Xü>aý×á†3wî\-ZÄÎ;ï\·±-C—6² ²©n’´-y§×­È“ˆöqhO |ònp=Ÿ¬S`С rÜ|Õ¹î¦Ûyü‰§É¹õ·ú×í(°“íì²ÛNÌ›¿#;ÌÃŒ™³˜>u+¦LÊ6S§jk>üä]EÎQô˺}òއ¯ÝYŸwú<~÷œ.s(øä(8>Ž®'ðü|šñ•@$ÁH½`Ž)°DwÍrr=ËÉ÷® wÅ[¬^òKßx™W_z–þÁ|tÏHí •€ÁnÁ+=_Yœñó/ñ£O½õĆƒ±®ì lü>!ükˆpã™9s&‹-âÀ¬ëø¦Ä ÙÐHT„wa˜$c ^wO‘‰f*CО”\‚ @ ÝØõ}Yöäæ¹$^ÿ÷ãüè.á¶;þÀоBdÙý¡ÐOMÝ–½÷Ø=ìδs˜¼ÍtZ§Î i'p<Ýjø™5>[9È`A—‡æ…ã)<_7Ž §/¦×Ód[[·mIAÜ2HZ‚dL’²uEEÒÒïÛ¦À’ºJÇ’M˜²Cî‚”š j {5‹—¼Åëo¼Á+/½Àß}ŒÇÿú0ou÷ê©ã @/†l·àÕ‡Ž&fÁ7îú"¹4ê‰m c]Øh‹z[”RL›6E‹ñá¸îãK¡= ½OD¤„šoSÜ èiö½0/J4'$èË7€dâ`MÞgÎKЯ—Š¿½f!—]÷ žxâir^t˰'3û½û3{—÷Ñ2mÍ“¦á¶Oá5^íÑëƒR+Ì–!°-ˆ›’´-™”$Lݪ9¤b²Ôº9,ëõyà•<{ÍŒ±çL_éóŒ úú¥Û:رµƒù»ì†Àçí7Þ`ñë¯ñìsOs÷Ý÷ð׿>Ho~]¦Ó1­äz/>p4ùb/'ÿò®;¦;ê‰m cYˆSƒß'Üÿ5ÆŒ3X´hÿøÇ#,Rbf£oQ“ï<¥{4‘²1)èˆ @¢BÊÇLAò¡¨§BÜœ¸ÍCÊH!ÈýÈ¥ÐÚlI–n(¿Gž*ÌרeÁ¾î+…ïSú»à*ÝPÀ›k\z-G®¨È{-ú䊊¬£cåÏÝrýóí¼¹äê]áÂNñÉÿ8‘ÿß'™7w.³¶ÙP•ÍZÞ°,ó ò„%hŠK‹:ŒTVj‹¶ÉSÙkòTv˜ÿ.>~Üñ\ÿã…ÜüËÿcL2ëhh%ÀÍÙ¼ò¯oqɶý¼÷­xlzÃu‚Ë @Ô{Ü®eoòæâ¨«Zôf›P6Џ©Ý¾ƒUÊ•¨µ#`S¼-%éZËå^ùy5Dh—¹§tã'OiöÇð}Ç×Â)Ø9ǧè*ŠäÝ@!çúŸ¢§Û|¥P\_Qt¡7›×.ò€_Â6mýoòàOÿ›ÿ»ÿÏtÖy¯¶’sÂg8õÓŸbþ¼9LéØTj“XçÏjÜçÖ¤dq·Ë`Q‘©³÷FÐÒÑÉžûÊìíçqô1÷sî9góÄ Bßêàî$‰eG’¾î·À„PEd|Ô“ï(dûøî·¾J&æóÙÏ~6¢€ÞÚì:Y$c1C“õ…ýò‡qÙFš4(Ö¶Ê}EÖgb‚%Ý݃®_Î>÷ƒr´| Èó®OÞ¢§(ºŠ\ð^ÎÑe„WÇSÒjdðeHMõkIÿ¶MA{R’° â–$né¬uÛ¼µÆå_KNÜ#E{Êæ`ñSâ _?—ý'N0÷Zº¡K玥Ø~Ÿ£øæÙ§ñÁ½æÓÑÚ\“ñ6…ðþ·%%/¯R |¢"”nŸ2÷ìxæî²/ü7_w+}@™‰wL@¯Òæ 4MºŠû¾½q~ÔsZcYX „Ô‹ó4nÑ×ÛÃÙgŸçyœz꩘f}—Mè:Ž™bâ&o–!HÙ’þ‚î“ü`C…¿¶º½À÷+¬q×× ÞWZ ;¾®Ï:hí( .¸¾âí^Uƒ·=5HÞñ)¸ÚŠ÷üòV.„NR3„À”C­ò渤ӒÄcZ¹‰›°$‰°-HzÓTÑúX#P Ö‡L\ðÏ·‹$m©«€{¯]Ä×]Á?_}»âZԦį’7`΂ùÏ/Kor{vÞ¥“ŽÖXdY)d“¸ Ë\‘T“H“³çóÅo]†9õ]Üté×èÉ©±” ˆg sêÙ|ö¦{¢!)ÌÆ²àaå„\¨1²Ù,gu–eqòÉ'cõ³ÂýÇ’lQwzír´MAhIV ”÷_…Â|¨[Ýõ´€v*º«´õw4QLÞÑ–¸íBð^ÞU۽잇¡¹cx¾Â”‚­[,â&Ú*7u‰ZÂÁ—~-f bFÙª7„%kïÐë—ŽIT@z3%£¸äÛ_å²^Ãò5ýÁ5¬½Õoƶâ«ßù.§œðò2ÃÿÊÑWÂ$Qq&ÈÄ%ž¯+Â9G‰)“'±õ>Ÿáâ¹s¸èÌx£{1à P˜ÁŽ]Ãqßü§ 'ê mcYøÚ09ê‰l (‹œqƤÓiŽ=öغ‡,C·ndlh[Ú\aår´®_!Ì Üõ5±‹ë©R²Ûš¬ÏÓK‹‚@Vy@Sô´0/±sÇóq¼P „Pek<(#ÓDLºf¼5i`›”¬ï¸©Iaâ¦æ!ALÌd Š ÿÜÃûç%˜Õ>Úíf4åh'~L`‚·ßäë_ý2?¾ýnú áõ®ð/YýVšý>ôQ.>ÿì¶ãöX¦ä­5.1S0Pc6Ñ®ïtLç‘ôåýÈú7T"¤“q’ÛÂïï¹›3?z,ïndO€^hí;ü‘ɇ_Ê-Xõ„6†±®< ¼‚V&Â5DøÀ‹EN9åZ[[ùЇê[`ÑoH›Â†¦W)Ì}¥Jñp·B ;^(‡2¶=-ÈCa^pޝp=QæÅà˜‚Ï@AqÏóYÌÀ‚6¤Vž ©ó,C“Ã4Ç) ë¸%°²ðN„îõ@‡Ê€”Ú:îmHZZ™èÂ0T#†ûð޼-ì h A|Íó|ó¯ðÀÚfµþ±Ö©ü÷÷.æÌ?As2Vz?n ’ôç+’"D2¦ “zr>9Ç'‹¶‰ƒ)Iƒƒ[/Ø—ë﹋Sû0^ÞÕˆJ€¾3w_¶û_Â?ûrÔÚƺð*ðwtGÀ c:¨-Ùl6Ë 'œÀ½÷ÞËn»íV·9X†ˆ¼©ÌÆ ”¢àú,ï÷p¡ºÊ] ®æWÏ»Š‚ãSðÊîø¢«­s-ܵ«^)„îpíV· m•Ç ™‰Kâ$b"°þöši³M‹AÂ’µ.±L­2Œ“°£zt6,҄̕2©˜\±Î¯µ~xCÅñ'ËÅ?ž[¼^.ÿòy-vÝëƒüðÊ‹Ùw×¹ë|.n š‚¼œ£HŒ¢IQ5`HA[Ò kÐ#[TTè*@¯¤Î&É«]٢ό]÷⪻~ÃIG|”‡V¬i$%@OÖÚ.?ç\þï’¢žÐp0Ö€›€]izC»õ·zõjN<ñDî¹ç¦M›V—ñ­ Á«‘±¸Ûå×O–,xí¶W% 4Œ‘›R pËAö¾¤É.g±Û¦a2\øš|~ˆUs,îvxa¥Ëví&s;7w÷=ã[å+aü¸).K€(ÝÊýê¾ðÅsxörÛöZZý†çSŸ?‡‹.ø&S2Öz?k›ºö¾«Ûe  H¬ÿcuBà½NJ–¬Ñ¥€QÎ&xf&§ Š®¢/¯Øª ¶[°?øõ-ý‘Oðz÷`£(‚D l=í"^¹å6Ä­QÏgX ÀÓÀÀ ¼6¡Ôáƒ&„à¹çžãk_ûW^y%ÍÍ£/_ÚÛ›mŠQ° Õ¦LJÄB¸ÒC¡­…½®h° eêòµ0áMŽŠéMŸ¥èÍkÅÃÃö¯³¶0¯Ö•nKJVênñ››Q(‡[¯ù!_8û¿Y3P»ÊáJoBzÒvœsÁå|ësGlô˜˜M IÁUôç}&¥£ë™ ܶ”žOÖ •¶h*Â![’!Êy ØuŸrãÍ×ñ‰cO`E_1J% ˜Q&-¸óî»!¢àŽƃ°ÝøÈ¨'²¥ Ün½õVöÞ{oN9åb±Øz?3\hotùó¾*'­¹AŒÜ^Óß(f´™µK²”?úsó¬ò„©C… —{Ä:Ó¤´ÁK+Ã=±¾“ñò=Üðã…œ}î"újDƺvaÎN ¸ü§?ã°½æëØŒ-q}E_!,½‹ÆKR¸ ‰§ ß •™¸®Y“õð•f'PJ°ï‡Žæº/㳟?‹e}‘”–Îö©e—÷]ħDô‘#ÇxQŠÀ¡›½‡¡u"m2ŽœqÆì¹çž,X°`Èë•$1¡ 3Ö ¹-,9+¸>GQ’à nø:]¿äNï/4® „ޝo˜Bµ$ž{6×*·ƒ,üÞ|™ (êlîIiÉßëäE»ŽlŽù5ïðÓÿ9—ó¿ýEQ¢!®&†Óf·>Æ Wÿ”wm;œ6%z=$c!ÊJ[$^’ 4ÙS}ò©\uÛ=X©æŒã+ Ž"ïRJx+V”¬ùР޼L]+‚x¶.; \å¦ÎL3Ô›¾öå y­þ ÛÔ9}y¿TŸuÔ¤#eu|²EÛ¬‹»gùb®8ïë\øÓÛÈ×8à Oqøq'sÍ5? }˜ÿbèrOX:\T*Œx»JÇ%© iRÁÕm¸£„‚Ž”Á’‚&J×(ÞÊ'Oý2Ï¿þ?¼éî’×±û –+ö¤,©é—ò×óî¨õ€µÀxR@Wœ\ ì„Ô1ãJ ¨\à• ½Ž‹üû_Oñí‹Ä>Ç| Ó0A;Q+ÈZ· m6ÅE)‘Í2*ÛÂ8yP¦fšLÆ2Ë­MmSpi¼ËRÒ¶ ¿ Êl€/ÿÖ¤çë$®ÖdíÇ[±äU.úÖqſïƒðO¤š9öäS¹þ‹6óúgÂ$-IÞÇ÷r,†õ‚: Гӽ"Uº÷Õ¤´ÁóË‹>Íq1$,Ñ2e[Î<ý‹¼òÔÓüñ¹¥õþ‰6˜¹Û-<ÿÇË#ײGˆñ¦<…θØ8æ½ëú‰D‚ææfR©+V¬``` ÒlØ~~§~êãÌÛa~IÀ›%V8+ k­dxÛÜX¹1!ÿ7‚€~<.YÞïâz eŠˆáêÐH5Úo ï¼ù"|ý‹\uûŸj^ÛJwò©SÏå'—ž1âóÅ-Ý6¹¿¨KSv”÷K¯¡¶¤ä•U.YǧÙÆ©„朘œ‘¥àúæ²Ýž‡òùsÏå©SÏdEŸ[KC(Þcæ=ÌûãA­ŽÂ+N:}ᨄ?hÏVÆ–d ŠbÔ÷+ÈiKÉR#&ªs"@ø¸w¤ )èôØÐTÿØ'8ã”ã‘¢f• ð—Ð<õ>pÜÜ)ß®ö õÄxôTâ|àà›À{­ÚâjLxÌXœD¦•DSÓæ-`Ç}ŽdÞ—JË,)8æ¤/sС‡qËþ›?ù0¹ÁºÏSÁþp=ô‡z(£îYü©Ie(y &°~„û]S\ê¶¹^èº{TS\²&«õðZ$%.yåY¾yögùÙ]ÕEø'ÓS8éóòÃ…Ÿõy-)ÈØ‚|À䨙‰®0¼/)ϧa(Š[’„%XÙ_®XvŸùÌ)<õäSüæ/ÿªÅÐ!½ÍJæŸ|%wœóxµ¨7Æ»ððIt8àt•ÀT ™ iÓ d@PÔÜFº¹…ŽÉSØq—¼oÿCØ{ßH%íRœ<$”1„vµ»¼›Ïyßûη¹ñ†ëyûíP9­¯ããÜsÏe¿ýööíµþ±‘k[áþÓè<}Ö}:&ðU¹£[”W^kBÒ5f¹WwŒ%/?ÃùTnºçñš>ÇáyãÉV>}úUþ ¯GÆ–ø7².|ÚS)¡7ï㌎QÂ2thkå€WJn]ßs6uǽ9ñäSxü™¯²tM¶šëA[3±–mÛ_É£ßúi5N5¶ ÄCÁ×\à(à `t¶(…¿mÛ´´´ÒÒÚŠŠ·Ð2e'¹ï}ïÞ¼k—w!ÁZ¿›Ú¾sÁù¼g·wsþùçóôÓOõI 7­üãÜwß}qÄÆIPF‚±àˆZGIÙ‰æ—oWGZ²¸;ŒÄUoVo¿ò/Îýò©ü¼ÆÂ‚2O+Áñ§ý?^tJ•Ϊ¯EÚH¨(Œ:oC×Þ÷æt n”•á¾Òž’¼¶ÚÁõÁfÃå’þØq<þà#\rÝm8ÕþÒVLYð;ß÷ÝÈò*aKRB¼\|íŽî#ðîɳvþ°òœÖü@¹þ5¸NõYCb±étšL&Css3­­­´··3gÎvÚi'æÏŸÏËþ,Þîœ~`3›n¹²a’˜~ô£Ì›7/|á Üÿýu¯¸ð 9üð뾑ç.Z±›ŽiPoÎz* ß‘6ø×2× ÛË^ޝù³Ü\'á¯ìÇœôy®¾ôU;oX ˜ŠIb–Ú7ÀMC+}yŸbùÖAðÐOÎHž}G1XðIZrÃ{KªÏöYžüçüé©W€Q­ }3„€Ì´¿²Ï}_Co“Gl‰ @%þ|ñû{þø›¥o¾þÑ¥o½.ÞzãU–¿³Œî®Õ ô“ÏfÉåsäs9ÇÁó<\×â¦3 ˲J_ñxœD"A2™$™LÒÚÚÊÔ©S™2e Ó¦McæÌ™Ìš5‹¦¦¦Òd|¥XþBgMßNÆûÆIbæÍ›Ç-·ÜÂé§ŸÎo~ó›º(á>ú(?þ8ï}ï{«zþè·Åá ÚY&b:7¤7ç7LÆë¤”Á`Qw˜ËT¡”cå[/rîÙŸçæ»ë$ü•ÅÞG}†«~´°ª™Ó¥RÀ˜îÀ8PÐdYVti¥g¸%!XÙ¯ œ2DÈPüœÒ¤óº}:Òo >m·8á„cøç˳²ßé 41ém_çƒgŸÇ­bñˆþ‰Å–®”°ûö[õí¾ýV±ïE¾jÕ*º»»ééé¡··—\.G±X¤X,âyRjMÔ0Œ@èÇI$’455ÑÚÒJK[+ÍB~S°M‰ãk‚œj”¼uvvrà 7‹Å¸ýöÛëê ¸üò˹ýöÛ«zÎF÷4B‰m ¦.»‹~6­I‰ãiv¹L|tçê}ç5¾~Î™ÜøÛ‡ê$üïÞûhnüÑedjT7•0ɘd  È»j#l’µGhÔt¤ ÞèrÉ…•3v¤ , +<¶Ÿlnr*Çø9þ|ÿcüü÷÷ãŽlèì–¶ýØÅüâ´¿Œä$Œ  €”r-·Ž^ì“&MbRǤ͠n,C3å¹>T«gSSW^y%žçñ«_ý ¨mÒcxÞ{5kÖÐÚÚZµs7¸üoèºò¾H ‘±51TÁg9ܳúm¾wΗ¹þ—÷ÕMøOßy/~rÝåÌi«Ýv3é,ÍiÆÄŒ}…öä´AÁm†Âæ¸$i Vô{ÃRlEó6œþŸÿÇŸ|šç—vmîz ´&Åܽ¯á™K¯ùÌѯ²ï¯MR²q÷z­7¾Ž[Ý­µµ•ïÿû|ðÁu±R… pçwVý¼ŒÈEnpo›‚ºòu–uB‡$¤²£°’…ßø?ºå®º «iÿð'ì9orÍÆ­ø§mÍß0PÑ(JLÊ€¢7ç5D.C Z&«Ê\›Z Ž<ŽcŽ8˜„‰ð&íñ[žùÃ÷F<éÇ„@J9õšÌ«Q ÷Ö[oÍe—]ÆìÙ³k^f>l·Þ:6úbW Qï“*¸§™¸$ïj2 FK€æ˜ï©Päû|•Kn¼ƒB*Z°|ó¢ïóÉv©éXºß…«`°PérmI‰e Öd}ܨÓÞ‚ûÝ™‘ôæ}Šžæ–à´3¿Ànó§k^øMïyeá¿õ{žåЯ!zG9û†Å„PFOÔ­øŠ5"qy×»ÞÅÂ… 1M³.µÆO<ñ½½ãöùYQ‹Úðn6Å \ÏgЉzFBh.€ÕƒaùÍ;þªEçqÞ¥7ÒïÔ>ÏB?qŽýâ·ø¯S¯éX•h² ¤ô–Z9GïíJÇ$ýݽ3J„ŠmgÆ _Tôç‡?ŸÉó÷å„c?HSÊÚÔžWþöôUôÙ³¸õàq•ô·6&€2BJ%Lmݪ¨ÄGÁ™gžY³ó‡PJ‘ÍfyðÁk>V£ ²o”h‰ <ƒ…ˆ wÕ¶”¤;§MÉÍÑ;}åB¾yáè/Öfn•]ÿ >šóÏ9ƒD²ñÃ¥’¶5Á×@ÞÜkŽÞ’ • ]’k¸\&§ ЕÝ 71 IDAT<—ĉ§ŸÍ{wš)6ú?0Àj^Ŷ‡|ŸŸúçQLyL`" 0€çyk #ÂÚ›qK 5UlÛæsŸû÷Üs/¾øbÍxà>üáWád£?E­QÙÖ8J4Å5Poù÷‡ Îâ~y…ÃæÔ¹?qÇùÚù‹XÝ—Óç©áZA½¸Õù-úo¶ŸœªÉ8뎫‘ŒéVÎÝ6;JòJþçû ¯Dô98- ‰)ae¿ÏÃ÷‘Ø­s8óÓ'°´÷g¸Ò¢­µ™D¢…iӶ°Ì×üëÿz套_Ã÷ˆ5­æùëîG\_Óÿ¥0¡0 £/ê9Ä @Qtk;ζÛnËW¾òN:餚jõžçñðÃWå\*zè&QN–жd*¨\G“tWMM/;PôÉ;·6}È›OßÇϽˆ×Vêè\Í9,P`g¸èâ ÙïÝój6Ά7qK0èø\ÛŒÞ ™œ1ùÇâ"ƒÅÑUoT )[‰KV„‰€›ñˆ|ìrý{AIIÒŽcÅâ´´4‘H&°â©{–x€Á%Ñkðu„PF(r#ݹ…SRShâ¢<]wÝ•§Ÿ~ºf›«RŠ7ÞxÇq°¬aìúÁXx$Ë¡Òhg›Œ-Ëd@Q_;¶Þ²EŸø&˜nòKŸç´3¿Æ#/-ÕÇ×)ëÿ¨OÉÝ3‚à¨ehÀò~Ÿ¬£hŠGßWbrZàøŠ¾üp“îj‹˜¡½«û=\¤Xߜֿâc-,ؽc}§Lªþl9eˆµ~F6 Ó Ô†³–jÀÔ©S9餓jvþðÁ, ¼øâ‹5§‘uì?„m lK“AcÌ+mkrë¾M%p©•œsÚÜ÷×§€ú4êRJѾÝÁ|õŒOÓÑdoú€À2tè¦èB¶Ø•-ICšœWcg’*}[çÕ ¶j2è øÖ¯”_SJ{å<_áú ×S8žÎ±Ê9ŠÁ¢O_Á·Öd½õjã€2 J)_©ŸKÈÙÛµ$ߊÅbì½÷Þd2úûû«~þpÓö}Ÿ—^z‰wÞ¹êc4"N–ÊT®©˜ˆw¢gqB»¸mC°&ç1s#[Ï…_û?ûßñ¨c—Îd+ßùÞרm§iµkƒ4Å%®ªÌrÖ⎛‚tLÒ›óq}mœ CVœb“›™`}oW s½®'¥ r®bMÖ'“(ž¯ðxJ }Oia_ð ï(òŽOÞU\(Â?ë(²Oå\DÁõ§~â—ÏÅ~uÌNuH5mL(”RƒJ)/: h8%´õ*µ~þ§L™Â~ûíÇÝwß]³1<Ïcñâq]MS‚§¢w•†c§ã’å}¾2BjÙðzh²ÁêÁ gpßuÙw¸úš_Ó¤×+ëüýGΑí‰ë_C?ÿaòf#Toñ‡¶”¤'çãxJ')«á)”b?† s?Ö J¿{J“Wy*|M[îEW{E‹žbÕ€KÑUüý­"Í«òŽ"[TäÈ:ºwAÑÕÇyA?¬PÿB·—R‡Z-)DÌ$,cúa3f¶ý –Wû262&€Bˆ^!D„O§îsë3•––öÜsÏš*J)–-[V³ó7„]3qeúòZ€™5ì­…âFkØ…/mðò*×W/‹àJ qUâ~àv÷•~¼ŠßÝÀý®­qEÞÑVz1x-WôɹZ˜çEÁõuo¯<€ëÓKŠdâ3æ†$fj¾ ÛÄ-ˆ›’„%t…EL´ô{1C`™ÛÐÕR0Ó÷dûg&€-=J)u’‹!À¶*“këºM¥Rì°Ã@í6\ß÷Y½zuÕÏÛˆp}½6BrMK\Rô ç(ÒÑ„µ‡@ݨ;»nXÂ_ög}ÿxqqð^í…¿#ÎÞG‰íçÍ"ìxŒ ¨Á¢¶¸7GØ\Ï“¨˜¡V¹XæRhORo^±jÀÇWàzà*me0÷µwƒŸž§•NÏ/»Ò‹^puÖ{ÑÓ1ôœ£}ø^ØyÔ/¥àëJ0iH%õûEW1)eБÖÚ6À¶$ –$né6Ô1¬À…?Ñ’…×Qÿœœ1xe•K_Þ§-¹¡´-±ÎŸ™A˜¥”Š !¶˜DÀ   åûº¬$Ò0€Ë„¢ž¿a ¸ªC a5Uª·©7@šýFàzªT.±1IÚ–‚ÍâM¯%„€¦¸îs‘-*Ò¶à…¿ý‚ŸÜtËò@}’þB%cŸ÷Á!ûìÉ¿»½ù+I#敱r}Žõ[å®§­ð0i­à)Öä|þ½Üá>Á¢¸ÖÑÂÜUäܲ€ê^×ã¨àÿ ©L)0+;i Z’X)®=qKÜí1“’ð¾ö±AvÙ:ÆþÛÙ$c£Ù”Ös 7`™¯u5‡üìÌH žOo^Ñ–Åt(+&†al 4«FwƱƒ `( BˆÑ±ÕŒp<íª3ê A\×%ŸÏ×tŒÑ’•ÑÙu¸Wȧš°dPu+7 VJš¡0±úU¾óÝŸðȳoë÷ëèú'5Ow,»Ìêä­Á,ýù¡^‰uæ>D˜Wò éÓU ÏÇ×¼ùޝp=-à‹\¿$¬ ®v­;ABœfG,™ë½9Ÿ‚âþWrÄ B ©­rS–t:&Ë–¶ qS{–À¶$¶YvÅW õ²‹}Ó µ3#éÉzÈ„úf ò¡/mî£2)m tzÌjµ µ’©@† `Ë„”²HG=„%pŠX²·kÁP !Éä(ÕôaÌn^°ékDOÖuÜ•d@‘:·„ “Ä AwÖå¶«~Ä]ÿ÷`éýz6š9ü£Ç²ÿÞ{c›Ú+ñF—O_^ÇÜ‹ž¶Ê‹%â××B½Rˆ‡±òÐÅ^™Ý^tµUÖ§—zDR–cåaÒ›mBsB í¶¤Ïë].Ó[MæL2µenÙë&Ĥ\ì嘹)AV¥b`ma¸ÜÓov»]Ö“— J?êµ¼ZqK°¼?,ÕÚœDW &€¡Xlõ$âPJ@Çqxíµ×€ÚY`BÚÚÚªr®Fïà+JÓ¢v˜R×ÝkרÜôØqS7½yôŽ+¹ñÚë(¢wîzR&f±ç‡°Æ5X¶¸Èò>ŸUz1‡!âZ/x 'Lz£bš¥šrm‘ ‚TLÒšÔnu+°ÔmSÇÍãÁWÌÔ±u3Hx -ò„%XÚëqÇ3Yf´šì·]|ƒ^‰M#ÈEÙ,á8T˜‡å‰“ÓO/-–J£æºHXД,ï«^¼Í÷ýBˆêlTc ÀPtG=!t"çëx_­ÑÓÓÃSOiÊÕZY`RJ¦L©N‚mƒË,åùèBÀ(g«7èŒ-éÊzÚ›dÖ~>e·µ7dý»eš»ÿÉí·ÝÊ¿—çêÇôWyûŒ5-»qï‹9Úr,*^\Q$eK ©²mêÆ3vP–f:¸SÛ„”%Y9àñ%EvŸcç©1A-º¡Ýíf+"PëªÍ¾±õ¡“ð$Ù‚ ¨†0 š:ñ¯7çÑ™‘ ÁtÙ™1xi¥Ã@QÑ’¨Î|”RÓ}ß·¥”[DÙÒ„0‘« À4uäÍ­CîÖ‹/¾È«¯¾Z“s‡Ö”’Ù³g×dŒFƒR‚¬£ã¾’ï•’±Z’|1žÙ 2 òþ>ôŸÐÔ­:[½èiŠÖüÅñN@Û6[ ãâNàJÿ÷½×ó§ßÜF_D…V8òp>ìAÌî´ë\°¸ÛáùÍqƒmš7wKT%7ùð°iA3uèfe¿§)ÁÑ+”Í I2&Y9è³Ýfö¨¦4¸ž¢kУ%1êr© pBl4±…$N(C‘‹z c·½ÁÖ+W®äæ›ojÿÏgšf‰mp¼C,ú5ÉU*6n™‡ï´'å†ÃI*$… „¶W&€ ËÍòá—&¾ùCÞ/T|ÞõËÙñª¢Y» båþò§¸ïΛx»/^+³G|èCÌÝ*6ôõ ߉ƽ9ÂxB÷XÜí’ ›‚5AQkR÷–ØÜ¦@µÂ䔂ýÛuŒºÊ(¼¸;­L([$"ÇÜI%pmðâ‹/rÇwµsņ €[F·Mn庱®€ë ‘ÃÕ>TЬýÙ S}-¡Ü“÷q}Å3Ë–ôh‹2´ÌC¶G q¼2—{ج%Q'½¼ëÄ-³Ž[:“Ý’“›’ÅInª—Ûþ|;Ï?ýÌp.cU¡•[Ø÷ÐC8øàýÖyß65O|Þºp£„æ¸Äõa P?FÐ #¬¬ð‚*—艮Z‚ª‰wúªR æÌC+[&€¡p7ý‘ÚÃ4t©P¾† ÀêÕ«ùáÔ¶þZJÉž{îY“s7BNóÁ¢ÚhRûZ!òÊW5ýÐÂÖI…Ž;´Ô,ò¼Sæ_×V¼¯Ýò!Qøþ#¯ç1 QÚ¶…ÔñìÐú™±5«[Ü’å³ {]g°CÌÔ5è† ˆe*~Ay[˜ºØþöû{øùu×ÑW;®© B)MÓÙçàC˜;5¾Îû¶)tµDΧà)ì:$Kna‚[S\»´ò~ä÷aˆ£3#ye•K¸-m´‘P3uo‰•afbUT’ ¼^˜P†b ê €¶¢LQn \mM[)Åý÷ß_së´°ÿþû×ìüSBÎñK Žž êÄ+ëÆý0F® `rŽO®¨ª”¬xŠ¢ÆÕCîõ2ƒ\h— ¡ë¿MI‰C=´D0RÀc‹3ÚLvžÓV»Ç”‰eB6d‘r¨ y)t½ù7\}5/vÕßõ*·ïÞm7>tè¾ëýŒV´{;ëøØú·CAv¹(jÏŽ¡Ë=¼õƒÁ¢¯û”ĉTø‡JÑä´Á««O¨ ÐZçTB߀-¦)ЄP¥TOÔÝA?ì¦äÂø_•5€^xo|ãúÜ5.Ã2M“ƒ>¸fço$(¥­ô×V9ü⟃ø*èaîê¸bEœÜ+Q¶j¦·0»Ü¨äqKД$‚ßmS`ä>¶!±­r}¹Xß%¦¸ÀU_p/¬phKJvŸÛì’´ ýŸÃ>‡›ãwý’_ÞÿH$%J)Íì³×þ¼wNçz?cJÈÄE²Ek¢®S\/21­ÀõçuS Ñ ·j #eàùЗ÷™”nŒJ€)ƒ-sèÏ+ÚR£›”¥DÂm•R !DCä„Õ @„k`º†Ø ä¨¦ðïêêâ‚ .àõ×_¯ù†,„`æÌ™Ì™3§fc4Šž¢;§pW9ئÄ6´ÀnŠ â1ƒ¤Yv¹ÇM¡?ô.‰c¤,[á†]ëk¹×!è[±ñùÄ EÚ–ôüµ>¿¹ÙëelÎÆÿÒSñ“˯ ¿&²Õáúž6ö?ìý\:.ñ”¢¿ÝD›uŸˆ ’1IA÷HÅ6}L­Ñ’ÔTÂ]ƒ>³Ú£­r 19£+Vz´¥F] ‚ýp§l6ÛLƒ$…× @<Ïë‘2JÍV›úº•¦¨z@±XäŠ+®à¿øE]„¿‚£Ž:jƒŸ‰ž®úhMHÚ’’£ß•¢-%´H5ô¦)ÅÐŽkB€m6¹R¨à¼•0¤ ×l€CÉ€ªŸ½¾6r=Ëøåu?æ‘××Dgýc±Ë®{°ÿÞªBÑë/„KÂΉQ¯KËÐy ïôù¥dਕS šâ+<< P@kB{½–÷{l?Ùõ5 öþLÓl–Wiš ‹  J©FH¶ ‰HÊUÕÙŒ®½öZ¾ýíoú<ÃR Ó49î¸ã6ø™Ê+¾Z‚æ½ÈsŽ"ë(²EŸÁ¢bEc4¶Y„¤b”fNëÌŒd‹¬¸×eZöMßýõÿ °9.YÞçP¬ Úã‰ÿÌ×ߥÿ¬³ðoÆ^ïû0ÃgN'>ÊRß„FPJ›â’×W»ä‚ÄÉ(•¬´§$+û}|0¢WJR¶$m Vôëüíj\#ß÷·•Rfª0½†Ç„PÓ47(]ŠÅ"Ùl–B¡€ã88Žƒï‡Ö‚@JI,ömb±‰DÓܼË>HBèî]Å’0ú'ìºë®ãœsÎ)Í·òN;ïBçŒy¼Óç‘w|rަ\,*²Ž_â\/q¯;”eJ=Î×*EëÍESC>\X†Àñ!ï©õÆÊ‡Qì·Î¯#¾ûPKBêŠW‘Þ 2 Ñ kÙ\yù¥¬të·Þ*Ž9wÞ<>pøº¥åÏéŸqS`[Ò:Y¯] ¨,6€R¬¥­2Ͼö‘{J⦠#m°jÀßh7Çá" .Ëø¾¿EPO(èëëÝÝÝ,[¶Luuu‰®®.º»»éíí¥¯¯þþ~r¹Åb‘B¡€çy%W·aضM"‘À¶mÒé4ÍÍÍ455ÑÔÔD[[ííí¥šøÎÎõ'$…ˆZŽ¡‹ýê«Ê9çœC6›­ëf¼ÝÁ'qåÃ}ZìÂ\ ¥³×X¦,u®KÇ%qS—£Ù¦¶Ì–NˆJÅ´¼^—Ù –¡½¹¢Z¯°¯çV²6%$ŽW®*©5<'ÏwßÂï~6áÇ!ÖÄŽ öà=Ó6]Õ·tŽ¢ç+ŒªtÖB¯DSB{u oU\„COm6xä í™KÅFŸP::èû4%cðÌ2‡lQ‘¶G?Ÿ@qßV)BÔ¶OzĘP`>0˜³ûoîܹ,]ºT¬\¹’Õ«W“ÏþþÇb1ÚÛÛéèè ½½É“'3uêÔÒ×´iÓ˜5kV‰/_ ;vúøJljGð}K/½”ï~÷» è ÇzmÆÍíS8胡µÅÒ¥i–þJÉMIK`2(?«¨)š¨@¹^^Tü°F{80¥öÙç]­qT:eI”RäjL,bÅâç¹ô{—‘s£u·o5}:lXŸµMI*&éÔdI©*’‘"¼fMq‰e zó>®¯‚¨±U“AÁóéÉùt¤¢mxUâ'Hd‹úò>i{t‰€"pi†±]ooo˜PÆ!Þ ìì lllóòË/óòË/¯óá‘Z1áqÅb‘wÞy‡wÞygÏ´··3uêT¦OŸ^Ræl?—>k[ŠÉé.6Ý!ÐSšàÅóõOLJ‚ã“­p±çÅÊ+¹õêK¹çö«ñÜú³¯œù…ÓøÏý·*å4„(…96pܦ,ŠF(ÓÜ Bj6ÀFp&ƒn¿ Š:¸·‹ù,wÝð#žx«/2ë_+˜5u6‡´û°Ž‰Š ÞîÑ9'©:…J6†Œ-‰ €ã*b vß‘60¥ kÐcÛv3ÒJ€p+hMj·/ï3µyô§ <ÓMÓ\—5jœaKR,ààýh`GÖe|Z¯Í6ÒMlÃÇ Â¨vWW]]]<ûì³ú!˜ºÍ 2“¦a·Oçåÿ݉m翇m¶ßÏŒ—ØßBÒ×Wi’ŒùÎ+Oòø¯ÀËÝ=¢yœþ¹SGX»<òò´F€”º‹ÜÀ&Øë‰„©«Jzƒ·š9&”ϲæÛ—ß„Du”RÈXš]öÚ“éMÃ;FWKH >“ÒFô n–&(êËk†ÂTtS)A ­PöäjÓïb$ÈÄ%–!YÑï1¯sô‰‰â:Ó4Íqϸ¥(Ÿ>,fV¼¾v–]½R¤7üŽR,]ò&,y€?˜ u«™´tÎ`ÊÌyl»ó{ÙaÁ~4¥SØ)ÍÁž°$©˜¶`îþŵà€l¤I\-0¸øC›:ŒYʹÊÍ4|Øòù<¯½ö¯½ö¦iâºîÏÔsÇ;âˆ#8òÈ#ë6nãAß›&[²zÀÃó‡¾J%e¶dõ€‹ãÁ(¥×Ã÷yóÁ»øé=OcFkAwLšÂlžû´`›hE)â²»-qݼ?})`ˆ©MYúòŠ–ˆû&¡½%iƒœ«è/ø¥NŠ£@Øh6ºíÑàègÚ˜¨òV9ÀuÀç( ÿê±é4”R¥ 6TBáþ…ðO¥R\tÑE¤Rª ÂËÞ×Ä;N$„ò¢9.5ÙÒ(¹%ÖO¸ìÛß%ëF[¥¡Ç–Lj›ÁûÙõòi‹ §\îM Ëô伆™SGÚÝY¯a;Ò¥`õ@U.’Bàûþ\´0n1ž ü8ŽòM³Vÿp°¶ Òòºì²ËØa‡ÍßtÇBÙ—‰ Šž"’ΩÚd@J)Þ¸ïNn|ôߥ¿£‚R ì³öÙ—©#(ã‹|Ù¢_êÄõíkŠë9õä4Cf# a R¶dMÖþhIØ,ïÓ Àh×a8'ŸÏ7@oÈÚa<)磅Ø7k\ ÿF€@[ÿÇwŸøÄ'0Œ`*i¤lë‡TαCfâ_éòÄjBáré%PPÁÑÐÜÜÆ~û ügmĤ cK .d‹"ÓùÚýZ kGR²j 1JÃé¸dE™ž}´çB´†1zfÆxQ>¥RÙ á_c¡ûØÏž=› .¸€ÖÖÖ¨§Ô0ˆ›BÓ»±A‚&•E_•{),yø®ÿËK@´Ö¸á··&9âC Fxí)ñ|UV”¢Ö4Ù‚B¹ ®sgÆ`e¿×0.) =%éÊVÍí¦”RX–5K)5n-›ñ 4§P®ïŸþu@ðppÍ5×0{ö쨧ÓPHY¡4@£lɘÀ”e.€jaÑ…çãúÑ[ÿJ)I:fÂ-#: +80Ð]CA_Ê)ñ†æþD‰)M«}À)QBgÚ`  ªåå óv^¾|ù¸Í À§Ñ´¾0!üëŠk¯½–÷½ï}QO£áˆ LC[m²?†l€=l€£ÅÊg~ÍÕ÷¾¨ÏךN"g߃öѱ*ª©˜îEÑ\¡ oNèðÍ`Ì)Ää´d è3XðâÞ ¡½W±z°zJ®”ò=S¦L™PiàP`$:ÿF .¸€£Ž: ˲¢žJÃ!ié²‹4ê=2n ’–(õ»¯†g{áÂïã7Hì •ɰ`߃Gtlt¼› IDATø$¬Pykœºû–„DèÍ{x PYЖÔTÉk²qau¬ì¯j¹Ä.ÙlvBhPìÌ ~Ÿ°þë„Cù,§~î4ÒéqO•="˜†¶ý!€h»¦*=§€ HOht‚dpÉcÜpû#Áé£JZdÒ“9pï)£:W" M,*Üño7'$1C‡oÜÆ·4'$ɘdyƒLAsBb›‚åýÕ©α”rÜVŒu ’ÛBø×A6léï½>x,‡}úšZÛ7rÔ– ½é¤lÉ@ƒôP[Jƺ*íãríÂKé©ÊìF¥˜q&ïv£<—m ÝË¡èShþ}€Œ­K×äG)‰™‚ö”dYŸÛa.…Z…7Å%«Þ£ JA<ßjÔSlPŒu`;4›aôkpbmb¡ý þãÌóI6w6DIR#B)}ÍÒ¶®'/_¦3·ƒŸÍ¶$ï* £4#Uö-.ÿÙoÆõˆÛì»û{F}ž°oBÎQe.€ˆ—zÂÒMz²>Npë"S0øVM’å½µétô:”&¥%=YMy½þÏùkS§ú5O)5.ccYèÚ‚ßg'g…ÿ±ÇËÅ—ü[MÝÇkR’FC(Ó¶$ç‚뇉€Ñ/Ѧ¸AÑS Ž2Kú8½ë¿ñD’wï½ï¨Ïc\E—ÒuŠ^ÏÑ–í@Á¯¨ˆp©¢0´¶#kýLùþH“ÓEµÁ$Ρ÷rÝ«”æï(øtz,ïóx£ËÙù™åËcë|x`,÷h††h‘=nnð't .¤©µƒ^Êáùà6-i£"c ŽÒd@Q÷K Дx>ô|ÚS#-mÎsÅï¨ê¼FƒŠ:‘H°ï{¦Våœ[âúª"0ºô¢°okRòÒŠJ&Ç)—ƒŸíIƒþ€Ÿ nV>ú±Ùøµ¯|Ç‚©-ާiŠ›ÚãU ¾Oá]MíêPOÑÇÓ¯ç]E®¨È;>rŽ·Ó€SŒ1{ŒeÀB7þ™@ qÀpÖYg1iÒ$OaIðTcðÜ72šâÇSä$Ž º!BÑ›yàÕ?ÿŒûw5Œõ¯ëÿmRÓbÚ(m´PØfâºR¹ž<êþК(w ç5ZSOAwÖgjÓ†·âáòõAÿ‹A'T_QôEŠžÎ…(zZˆç]­å]Åò~¼£¸ÿå<ÍqÝ0ïèާðø¾ÎÍ)'è ¤)Á31S3 vX¶Ìí2ñxz!¬Ù•j\Œe È8nÓØ(øË_þÂÂ… ùÎw¾Ã6Óg`߇bpå'J/Ö¦¸Äó!WT s2q‰!½£ ºä'?Ã÷%ó[ò öÚ§QŸ'ªÉ˜À‚Á†,Ôy%50¸‡…JaÞ–”$LÁò^w£ @¥ mi]Uê—áúåíøä‚Ÿ…ÀJ×Jtðž£k]áûà)ðü AZÅ xuµË”ŒAÌ€¸)iJèFO¶)° °¤®öˆU¶)ˆ`úý˜¡_³Lˆ­€m€·gùfcYè¡ì’i”=v\!t¯Þ|óÍ ráE3gࣵpªÉ&®ü:hŠkF¹¬Ó8B$õäF¶‡V>Åî~ ß÷ëÞrzcˆÅlÞ½Ë~U;_Ò’X†Îh”¼MqIÌ„žœÂóÁeöV5¬ò„%iMJw»Ìj·J¹A¹À…žsÊÖy1°ØsN`‘;>… GÆW”,s¥Êq})À3ÈqKÐ’¥RMËËØ%a.€û_É#³kŠ˜©µLAÌñ}´À›ûÀüãÀWFçXVºÕÁïÑ?¡ã•®Æ;ï¼Ïóø3¿ƒbF¹Djâʯ[ …Òl€ ¢$Ù¦ n úËvsSn½òǬòªWc=Z„JH,g½v¬Úyã– fjw»ãÝ»dÊ–$LÉš¬‡ë+ìŠ5a¾¶Uîz:¬çzàú¡U®ÈÙ¢OÖ!ˆ§ûÛ ŽbMÎçée¯u¹x>øJá)¡…y8:>oHJÂ:aIÚSZ›å­­uAÜ”ØÁ=°dð¾ÔnùÐJ7¥XïÿìûŠWV9¼ÞíÒš”Ä6ê*©8^뽂J)%„0æÌœ9Ódœy`i ¯¢Cã2C³*B~ÿûß3P,8î<òs懟 !¤[ƒ!iiêÝFa”B`E2&èÏWf’÷Þ pûmÂsgÿÓJˆÄÎÌd—mªW¥e›šÈ)ÄmSÔe•oLÇMA&.éË«uÞ­æ -Ä=_çêxžöÖe]ý¶:Î;:žžw}²ÁßÚR¬rÜ0^îƒB …¸!µNX‚–„`Õ€Ï.SãR“`ŤV¢â¦ ؆ö<™, {m•›R[ú"¾›—Û°îg} =mðìr‡Þ¼Ï¤ôÆÒÄÄ_74r hΈÅbc¹jn½ë À?€7€¹LH¢š¡R ø¿ÿýkÜ8{n÷=ö˜¾—|Úº©ìõ@:&èÉo~rÛ›ÝÎÃowáCC¹ÿ…4Øj×=«Zd›‚´mГsÉ:ŠæÄHC]£³Ê•Òîq_i!™¶¯w¹¼¼ÒÕŠ‚v·7»æ.ðÉ9:9Îñ®¯è\/p³÷­Ò½n›Ú­žŠIÚ+,oËЂ®%qmIÆÒdm#¬3¶ ë)¶ì XºÔey¯E.#ÈX £øºŒ6 °ˆÈuo‚š@ FµF)…ïû¨HX×BÂP¡”G¹ì/DôšÒIÚ ‚  Rõøí¯G¹ê‹Á¼ <ÏÃ÷}|ß~÷ð¼*Åâ0Å¢GîyÎ0T‹U>ò¯ÿÉÿ< {ÞËADž’¼#Ø6ÖJàh½÷åóùUZëE’,L-ƾ®| 88³»&¿ËþàãÿëÖ­ã oxCÒSI%z2’çGBB­#k-Ùe)€Þ¨Aâ8ŠjuöŸýŽ9\§é ºÖsì Í’9GoN²s\µ„ƒKk­¥”Øpà 7üØohÐö`ø7àhà :JÀ‚Áó|.¸à:è Ž;®yöý =9IyG€bh«R€¸·üè’ÿý;ÿM¹\nã¬æ‡Ty"šD4¼ö³¥}§®a.¿YÄ^¥?ßYÓ3ÿλ±«ß–¦QѦ_“s›RÖrÿŽ;üðÃÿ“ýHØ_²ï>ÃÄøLºv‡ýÏ=÷ùÈGصkWÒSIús†SÞK`—kXÏFgÉnþ5÷Üÿ4Jû\û)2Kù»¿|}SJ]¼>MS ‹R ®´DV ¥Ô GqÄ~Å>»¿(_®ÆèÞ¤P´Bn½õV>÷¹Ï%=•Ô¡'—>:à¼+±-›¥pûMÿÅöjÉDSfqw°@k͆?~-'´¨%J¦%a°`B]»Š­3Ö¥”Gnß¾½£¤pðI BTVÊ~¬L¾Y’´Ð.¿ür~ö³Ÿ%6~ÑåJõ¶²É#Ê·$#•ÙÍé†ïÿ˜ññý®J)Ù³\ÎÿÛpdkÄ‘¦ BJØ>ÞRŽB.—˵ò„IcÈhDøW CàÇ1-ƒ÷»œ€8f6Ù"k,wY(k-³T*qÁpÛm·Q(tš4‚éã.0”²­^€õä¦ÙŸYÈ8PÈÔ Š*¾"Pâe”•±ªf¬¢PÛ~ÍÏ~/\Fì‡ÐZSXu$gŸò,«uöhÞ5} vד!›1”RZ!º»»ÂÈ—´hõMaSÊÀ€À?¯dbH`ŸT˯âÇc=–3Ï<“õë×óÍo~“[o½uB-ôB+÷Þ{/_ûÚ×xï{ß» ã¦YÇÔUÍp§™®:p/mPk+Z ¨w7SÚòJ`hˆÇ+ŠÑŠ©g/Ed1;ÆC6‡pÅOF Û] ñxÙ »&ûÀÿÏöÒxS× ƒ¦C¼GóÎóYÜ•iÉ9뉀З—ìŽ_5ë•RŠh?=Nký‹ý¥pTÀ$âþ7†*øÏóåìCÞ€É<þýCáÕ¯~5§œr ‡z(6l ›ÍòŠW¼‚ï|ç;\z饌ŒŒÔn„…ŽÛ^z饼þõ¯ç€XÐqÓˆŒm”€™€ äo‘ðT8”®ÃŒWcUmØß|E9¨?_¬jŠ~ÔÃø`V¯^Í¢E‹&¼÷Àäýï?ÇwûØÇ¸ûî»T ˆÇÚ¶mW]u—_~yÛÇLk®…8ÒЫŽUâö¦F`—Ùß|͸gû˜§¬õJt|Låj¾BÓŦM©iª"È»’Á‚¤«_Ò•1´­YGPpÝ3‡BÖ¸DpÇÓeî}¶Ê›Ž+ЗfcôžçžGŸ£¤‹ú·ƒý /=ý,Ž\µ¨éZýɰ¤`°Ëâw[|v[£D÷õKN=õT‹ý¤)Ðþ®€I¼x¸øc iÐiìÉí ¤Lµ©Æ¯X±‚“O>™ãNø#J=ðrð¯]Ï¢þ™iw]×å´ÓNcݺu\yå•|þóŸOÄð¥/}‰÷½ï}¬ZµjÁÆL ^ùúƒEã~¯j¶)^xèy Œ¸Ý ©±·¹Q—>#ÌË{- ®¡ŽyOVÒ1>ç˜æ*"b}¢ÎÁ¾7(¥éÊHüŠ5­ð›Ûïàùí#ÆÌéÿZ ³'eyÏßþ%]ùÖçÕYò¡Òì(†¬ì·›ÎˆÞ»è¶·hª‰âAˆ1ü Ó;à‡ÀJàLŽÀË€þ©ÞÔ¬ðœîý±ú£>š—¾ô¥sÌ1y䑬X±‚ÞÞ^ =ýütSÈÛºº{f=æºuë¸ä’K8üðÃùû¿ÿûSâqÆÇÇùìg?;k/À|ÚÒŠ]Å;ƒZs•®¬ÀóÇ®ÊÔ„xoFÒ•"An ÿnɸ;Ú\¯Aýºí•ù,âJWÀxuúõpï½w0:¼{Žóè ƒÙAkM߆cùÇ„cµþž—BГ1ÔÊ»J­ÉˆÐëûþz: À> ø}ôó0pF£[ µbÅŠWŽŽ.kZhÆïÏf³¬]»–µk×ràrØa‡q衇²bÅ òù<]]]tuu‘ÉÔ“a¼@ãÊ2RøZãÎA8ö÷÷óŽw¼ƒ8€7¿ùÍT*•S®¹æ+|ä#™U³ ú}9uƒŽþÓÔ»™¥‡/sù‡Óz¢x»à–ÇJ<ô‚ÇkÈï¥7y#4Z‹9¸Eëîí=ÓªXcÓ¦÷ûÜqÏ㌕ö /g)C¼½þ¯ßÍâþÞ6Œ`â¼k¼g-äЀR©µ¾oHüCTQŽ~¶`B?ò?øÁþ©¿¿ÿCãããlÞ¼™­[·²}ûvvîÜÉèè(Õj•r¹Lµ#¶m“Ïçéî«‹þþ~–.]ÊÒ¥KY²d …BL&ƒëº¸®K6› ì§‚à:‚@ ü€9Óɺ®Ëë^÷:n¾ùf^ûÚ×R*•D B0<<Âu×]g*t_Ñ¡LôƒIF#ôeš«ø&P?4ño/„²§«*vÓ{Ï !È8’\C¼±+#M×7_ãX³µBæ"üçŽlÔÖu¬ç›LTJOÝÃ3[¶F­Nü¿ƒCk Ýø«³N¦;×zŽìXyvlÁ¢¼ÅPI*5›ÙÌ09»BØü,Ó?t`2Ê@å˜cŽyÌæwä‘GÖše„a8¡¡Æäö£q·°¸™Gü3_ד¦–Ïþæï•éE m¼¢«*“üæiª¾¦˜ö§•¨ý©g³«ºƒÛ’P¤`.L …’‚þþ‰‘¤.WFÊLzÂnÔan¤»F'Îíîû`ÛnãþïÿÚ“Î8ƒƒV ¶åÜñvëHÁ¢¼ä‰í!ãUMo®5÷Ÿ”r-&ýfŸï ÐQ&!Úð†ã¿…8Žƒã,|7dmA¨õ´|òÆz›Y¸H)yÅ+^Á7ÞÈk^óšË xæ™g¸ð«w2¸þ˜ˆlÆxdÔ¿Ü–F9–a¨Ë;’Á‚ ++érÝIÎ5-O³Žéenߟ{øG‹éb§‹•¼£>zÂóYG ”ñ`~$!ÀµL NŽ0 Bíûþ°m/쥙JKa¥M_ñ©  É Œ®ÂÄîöPk”œpÊé\õ¹/ñÁ÷¾{aJUÈŽ‡þ‹7ýéÉäݨlÍêÌ]ijÏ]1'»øÏ^ó§|ý?®¥X,¦Ê µÆqÎ>ûì Ïç]Ó‰½è) iq³¾iBcUÒzRÒá¿Ø¸™ÑNø¿ƒ6@kÍàKNà\ƒÓf‡˜”õ„×]EŪþ½K³b°C6·O££LÛ¶›2fc•OF£ ‡º ·¤@k÷T­±LՆDŽ.ÆC%OSò]é_AÙW”ªš’¯[uÇþÉ[yèÖëšùˆ³Æ#?»‰Ó7ì­QФk¥A‹©¯ÞË^ö2Ž;î86oÞL†©ˆQÇs8ï¼ó˜ðZÁØƪqD‚€è¢J ÝYÉóC>Õð#¿}ˆ-;wÒ‰ÿwÐZÄÖÿ;ÿúïY¹DaR@OFàJØQKlþîÓZw‡a¸žŽ°ßb\k@LÇÓ:#&s­ #[£E®ŒÐBC¿ÿ­ø!”}M90±ñ­ã^¨yè÷wŒ•EÏór ñ…q¹Ç£ ¶)ðqlQ#Y·¼wðc\üÄ}¼øìS-»`SAkÍÖ­[ùÍo~ÑG5ƒëMìñçLWüª«®â‘GaãÆ‰1ƈÇ^³f ŸúÔ§öx=çJ\[0±¶À™7b¥Jb,£J€é—Þ`Š=ðÈclß5dŽïÿZ„Xø¿ï#ŸáÃo-ÝÙ…ð† I!#ÙY [¢}+¥´”RX–up[+f™$: ÀÔD­0}²ØÒ5aF TbAnXÛŒ0÷C¨†é­è(© |U§w-zŠ’½Yë1뛎Xßb…á©>]‰+M\¹7'XfK²ŽkÒ˜‚k\»װùØRÔi`¥ÉŽUê@VésœqÆm¿aòãÿ˜£Ž:ªeç\·n×_=ñÁ /¼˜¹|ùrn»í6z{÷,iÊÚ†•o´5J00ZD–ÑT­ŠŸxìFGv-üäšDÇ[‘nh]àü¼ŠÿoeQÏäSEÁþŒc:—ÌZÏ6wˆ{h­kÑLEG˜Û‡=°,B¥…§L=¾hªQvz\¢Võ/z†Ÿ½â›’µXPQ,>^Œ³ùZ\ËdbgÃòfÚ´ ²äI>#èÊŠUÍWâÌòÇë2Ì{m æ«ÎJ)9ñ„xë_ý×ýÇ´îÂM¥wÝuøÀZzÞ“N:‰Ÿÿüç¼ë]ïâŽ;~J{€v¶GŽxÁ9ûì³ùò—¿ÌâÅ‹§8ÊÄ× ®`¬š|…$] ÈgLnIÙoÌMxðW›)¦[ Æ•6ñ÷ÏÕqV¯;¥K`ÉâEôõöÑÝÕM.ŸÁ± ô÷/aùŠAzûºéîê¢Ï“Ëçȸn­DWMhÇFJ‰´,¾ùP‰ÉÙGw1P°ÒJL‘‹WÏÝ›*Üòh™wžÜͪ¾ÙU)¥jULñú5¿›]´&TŠ0 £*'Eš÷˜ ¨Ð$òjMø„Aˆ„A@¥Z¥Töøæý»Yš8f™¦Z*±{tŒ;w²|íñgg½ba„? £ýÖ•‚þ¼dë¨é uZãyR¾´%'J` Üø›¢ ´…ßPЦ¢R¶øŒ©WiyƆ®¬$e´Ç|ìy×0¾å\IÖ6ÍXâ¬÷Lô¾™ÂöñŒm\ù…)ø¬çKoÙ¿hï{ï{ùúõ×£”jÛ†¯”âhùyÖ¬Yí·Þʽ÷ÞË·¿ým~~ßý<ûâò¶"c‹¶(–e±xñbN<ñDÞúÖ·î‘õ߈¸¹+#¯`+Â_ÈÙ¨7*ÒÄГ¼8¶/~"¥Xzè‰|üƒä°ƒ—³lÅ ÐÓÝ…ÝÂv²èÑü†·¤Ÿáôå¯>—w¿ã/`$söå$Oï ¼%ɇý‰%»‹*ò,%<¡(¿dI—äçã’ä'f AoÖ$Rï.)Ö Ìßhj€Bä€e¹}` ¼ûåÝ­u9ú’çŒù,°=7[‹†XmënªÞô¦7qÝu×µÅúÏ©”âÑGm›#ëðj.¶++¨&l”]x:‰)‘q$Ž%­qhzþ÷lIýÿšƒÆû{pzs_™¼´ 'cEí*†¤eVèÏ[ŒUã|—¤µ£Øvg$¶ì,¶´'ÀKØÇ€6ùƒöy”„U¦ºµô”ÏN@+¾-®m £³·ìÜ|0‡vXKÏ9aòÌ3Ï´u 0¤B¶e®•JË®ôf%Õ(4 Âä›äÉh¹¾®¶=õ•±±Dç6tèÂ0±Æ·qOV‚6Õ9éø©u‰ÜUR5e7 J$ u+ù÷›€¹ ùÈs»»Ô²9‰È¸yY«N˜: ÀÐZ—”Rþ”7Ô^JÔZ7‡h8aYüyRï ýýýœzê©m9w ¥/¼ðB[Çs\KRöuªšõæ$~%ºæ; s]\‹(9Q™0ª<ùøVFKé°Ü¦‡`úöPÈN‡îŒDJ÷4a*4K3‡Þ¬d¸¬jÊnÂÑýy‰cÁ–‘ä­Í:vmÆ)› ¬VA)ubËN–: Àxî¹ç<)e¢+8Þƒ¥0%|Ó16‹ÞÞ^Ž9æ˜hÌölüZk¶mÛÖ–s7–&£ä)Â4ÈÚ=ÃFVL… 9- º³‚’gJTÚÈïÇwQ!íõÿËX¹ta9•sŽÀµ ur¼\« ¶EyÓhªìÇ}IÎyA ï¬äÅ(ñv–±yI±ªB^Íž[ „8¼%'K` ¬]»VÅ™ñIC`ªü°=nmÛ¶Y³f о_kÍÐÐP[ÎÝq$”<* +cJ’Æ«É Öø+–ÒX¶•À„&^xê †@IkBÈ®e0¿°ÛVÎµÞ qS®$u¤x[ì’ø¡n™Pk"ceQÞb˨QÒ L:–Q–ª¡f¨Ü:ÅD±Lk=Uýï>ƒŽ0=’Wa‰›¯c‘ IDAT·ˆ¨±=7Swww[ÎCk½`Í{r®‰Õ†)Øxbte$– Vr—$jž% ;#ðBM%€§~¿‹íCã‰ÎmoÐZ“Ù°”žÞµlËXµcÕzS®Ø ,Ð0TJ~]Å^ )`Y·dǸÙ>Ó`DYRЗ³•©€–(pp MŸ)At€)ð»ßý!D) Ú«q EpÐ&À²,²Ùl[Î#ÚÝ]&Nø‘”U£FNbއƚû¤!„¡)#fÊíÛŸeltwÒÓÚ+6¬^–Ȧ՛•”<ÕÈ™ü—¸(oaY°3•±œÀ²^‹á²JIÒ«™CÁ5,ÃåXkzn†*VëöfP·` qÄZ1’ô<À”µemõ h´Ö„a{m# ©Áì@yWàš8g2ia+‘9G0^ÑS’K'!ÒÆ=ÅæÏTÃTXl3aÅÒ¥ <¢ùþúr/4ý7 ’¿N=YÓßcçx˜ø:!,鲨šáròZxì™È:‚®Œd¤6§Ö|BˆŽ`„Rj( ›¡µMiצJ€J¥‚ïûm9wŒv{â 0ïü0¢6%ùÌèx 2‚¢§"Å$ùÝZ£,I¡¯Œ³ik‰åtÄlgÂÒþõ :^,@zs’@A9‰œ®%èr%»Jé™ÂÄÛ%uw{¢Ó‰£ž£EÉkݼ”R‡¶ìd  £LŸþô§NÃf(…Éb5M‡Ú3Ÿ8C¿] ‚žžž¶œ»>†yÌ:†ã¾î-I^‰SK^ôâòÄtÌ)k›Q•á­ì*Ñî M+Ë·7_e2âuÕ—3Bm¼ªÒQ ¨ëž‰ÑŠ"P:Ê›À„»ò®dûXœ˜ð¤0{hN2^U5öËÙBÏ ´K)ÖZïÙlAG˜¯|å+FRáÀÔl+ÚçÑGmý‰ ¥œ¦YNë‘wÌ’.éØc˜rû¼8s…‚ŒmúS o~žÒоѰ°4™¤ë®ŒÀ–0VMG…‰Žö¦‚¤ì«T°Æ÷›”‚¾¼dÛXœ˜üÜ\ËxqLhbnic{w?Ô”<Åp%dÇXÀ–Qé“Û½µ-Ÿð¡C<n¸á}î¹ç[ÀÝ<X–é Ðá144Ä=÷Ü´Ïý+¥dùòåm9÷dä\Pòt¢ÍH&£7'©úàPp“žñBdl“øâ3»Ù¹k4éIÍ V&.å¼+É8ukÛM¼æÞ`°ËÂa¤¢é›qyëï•RÀÒ.«¦´ÃãeîíÙ{Ó¤,î’I-7Á´`7Ý]üӪÝ7B¾äŽ…J ©F¦½»Â Á µòE?<øuË?ä £L¥T˜¸ðÇ,oÓ¸­=ÖãÖ­[¹ë®»Z~ÞFH)Y·n][Lj‘³–„¢gÒÒââêËYTCÕÐÓ!IÔûLt¹‚'v°{,Ý%€1Ú¬:\Ë´ç­¨š'. æ@Á¬ðÝ¥5ý­iuÛ,¤€z,žÜáS 4Y{ú‹T¿†s Õ­rã‘ µ& ¡6ÕR•@Sö4%_QöÌß›GCŠUÍÝ›ª<½3 ä /ʯòC̹”á\idcµ…¡w,“O³½YIÖ2ëØGß™÷K` œ{aXmæúì`I¼(HÛª(r¹\æöÛoÇó¼¶´ŽÏ)¥dÆ…I–Í:Ç5 -èÍš’»²w”Kñ¦+…j¥‘m”ÆÓß gñÂæL;+Ø2R/o›‹Ú.ôå õîÎñdiK•!)`i)›-+²ÝÓ¯÷ºe¼œJkTt¾@+=¶Ê˾¢õÔ¨DÖyÍJýPã…(ÃÚjÓÊ]kãá4V~ÈxUãXF±ËئB k›ªŠ¼kú,ä]IÞ1íÞ-iŽu£vî®eBB˜m^Ü6¢£L)e*L"!¶%*‘ UûÎÖ­[¹æškš?Ñ4ˆŠl6Ë¡‡.L²¬kCÆ”üt%Üå3fã)ˆÕ6nÔ]·{+ae_H„‹Û›L:5Ì:êÍJ6î ÛÖ˜k>(¸qWÀ:ÇD;¼{s¹7Ž)…`I·…F0\V,鶨4¸Ð+2®ôª¾é²XŠòJž¢ì›î§^¨ñc7}dÇÊÀ°YJ¶4BÙ‘FX\AεÈG¥y×Pk4½àQö5g–cQÞ‰º”†­SDŸ¥ñ1þÈºŠ˜ðûl%@G˜Z)5lYép©9R` A5ndÑ‚Üó<¾ÿýï³qãF ½ñÿC9dÁr)\ËtO¬xéê˜sRˆ”ô0‘]EJ%Úâj5rbá½rq[àþœ…z) ãd"Wôî’)1µåÌJï\cç1b—{  b5Ôx‘÷":éb;/zš‘²"ÔŠÿúM‰œ#Œ«=j‰(ã¶×:έ×Harw, !jäY]…ºE^p%yG’sÌk®-È:&—%cK2–Ù+…¬ºXˆKa”Šm£Šgvtg%ƒ]ÍøS£ê¬|àœã?¾½µÔm@G˜B­µNOÔ±–lPZ€M›6qÙe—íÝø¥”œrÊ)m9÷”ãEÙí•€T)F11|òк0N3º²v”K iHO³Ûé‘Ä cݵ¿ ÑÚ”*m„V²0«h  yfW€hlwf)äZƒÆÉlà&·Á •^ô4ãUc•}MÅW”¨ú / Š›«TCó»B˼¦8kF[ÂôDÈÚÆâîÉJ²‘5ÿdº`w-ÉŸ,ã+Í;OêÆ5V”w"…±È÷~O6HúYßú汙 )=9‰¦±‚¹æóÜçµÖZH)-à8: ÀþÈ8°ŽôY+ŠsÕ«æ/9´Ö|ýë_çúë¯oÉg‚‚|>ó*,ÌÍœw;ÆÍ&hæ±@ÃO %Œs,î˜ @ U|QIwÀ¤Pû†¢_º]AÆ‚‘Š"P`O£LÔ§g§\k ¡„JG?Qf»2 ›LlÜÄË‹^£E®Ù2f’Ú®À¤-™¸y3×q9¬@cÐØBàØQœ%X”3Â;¶¾sQò[Á2F¸gó>[š²d[ l©±-1¥Õ퇚•½6¿Ú\’ç1tNŠù¬o•©…ImÌnS ðøMýmrq ÁPY±cæœsÎáÉ'Ÿlà ÷„ÖšžžÎ9眨m^WÔb iH·‹¿®Þœ¤ì)üY­˜Ó‹å1vy¥DçÒ  aeù”‚¼!'Dc_¼(n2ÙMLÜê5æÅªÉj/úæ˜-#!%ß\ Z£(máZ˜”àÆåi‰PΖQŒ\RÈ{Î3ÙÍO,ð3¶yßlnõJ èÎH†¹yäùÇÿZÅÛ]K°m,du:DMÖôå,¶ŒùŒU}¹¦“øRwi­— !67?Ë…C:¾•ô"yéA½!ÐhÅ”úÌUÃãŒ3Îà—¿ü%Ðþr¯øüoxÃÐý_ÿ¢ ®ÉÖ®:_`„Y‚iA¨4)šÐ^j㯗Õ3ѽÐé˜Õ-#F¸(«½èÕcé• >ÖdÁ›¸( .Z5s¯YÒ¸Í3¶q•ãk»$‹òV,&%Âeìúïõ,w㪯e³ÏIÒNZÁš=¬ôŒe:Ýí.)¥p-™ìš\^yGЛlMÏú²-A_NàŠ‘Šbó«h@cÀa@GØO ”RcRÊ$˜G&ÀFsÝmRÎ4€íÛ·sÆgð«_ý XØZïóÏ?AÆ™Œœk®O5ˆ¬Â”hYGj#’æmá£JûF€gvúÜñTÅP¼Fqòª¯©„Ïg‚ð£ÒÆ8MMJ“{aKSYãJAÁ…»!‹=J„« ñÈbÏE¤2¿ÛêqÓoËü 96,vóò·×åÞCTb?'>c„×`AòØ6ŸŠ§q^[Z˜ëmKXTl»¦£ªª;+QŠZWÀVÌIkm !~ÜôÉ`”J¥ ŸÏ‰+¦¶]D³þÖüqÎ:ë,6mÚ´ I1´Öœ~úéuÔQmk*dmÜX ÒUÙžwŒýW¬&?«x=ÔÒ\÷Üúð‹øVŸ©`&+ݶ®4e–ý¶$k›„½¬ YÛ0Á墄¸\$Ì(é͉Þo[3×ÇXÖmÈcÆ*ªá²Í5«½~P³²'Îå,Hãéð5=I7Š-)èÏY<½Óðã$R¯UÞ•8¶`¤Ò:ÏD¤Þ².: À4Èçó> :`)LЏ¾w6øîw¿ËÛßþvFFFTøÇã\xá…mk:dmS²Tó¤† ƪ­%š_"œ9vt×sˆ°Ü‚Y, V2ιÇŒUîšd9§!ÖîXMVXh]³`§BoNbKÁHEGÕDV{ŒxÌ‚E  yOZ tg ûe¨tâ•/ñµêrÝÃÉQ 4™šÍþÜÂnúD ŒŽ0 †††¼¾¾¾2$¯¹ aúY×X·f€Öš .¸€«¯¾߯kÞ )ü_þò—/8ùO# [Pª¦‹8ï˜ò«ÑÈò˜,³›¥iQ/‹› ÄMQtTNVïxV,+RЮ}Öè­ óÒ³Ë+™—‚5ƒðSa’u#å0Š/¥!ÊÔ5d6Ñ[; Õ/–€¼Ä4»Š¦'@w=YÉHÅ(L™é怨`µÖz™bkó³\t€iÐßßï^¸Ñãz_¥™1ìÉ'Ÿä/ÿò/yà&Xý õâq>õ©O-ÈxÓÁ¶L wÜSÑœv'Ô4 ÷úø1ÕéH%&šø¾É‚Ü”ŸéiyL£¢ßcNöjÌÕÕWZ£–|jY¼@³e˾E_¾y÷ÃÀ›fulë¿õ:ÑTì)¶W’±D­+`:JaØ- ÛÆÂÔ(9Ç$Mnõ«j Í+LZk!„Xäûþ: £ìÐ@˜´õæ6¶$÷žÂÜó<®¾új>ñ‰OP,Í{jìrîëÏ夓NZðqaKC„Rl`¢0Ÿðì´ï™(Çëǹ¶)Q­(”?f}ÓuÖ¶PQëOîF¨ûÊ$µUCMÅklJ½ÉŠ2Ùñ¦§¹9g\'ÇËmã2wmcf’_ßsÁðXr¤Eq ¹;+ÙU ñãÅ•‚="ïšRÃãªÆü—8„ ‘\É–Ñ£–§Ä3!}QENÜ›£I…IG¥ÇqîmÍLÛŽ0 žþyV®\©Sq#A-óß‹úh@+ÅwÞɇ?üazè! ~ã'!üs¹—]~Y*6Ÿœ+.©i#Ø÷¾M2ÊŸêB»Ñ­‡j|e6?*ýó£ç_ øù¦ ¥¥«©A÷£6S‹½W™óµ2²8ù͉:ÚÂø6µZrC#jýÎ3 Ïe£Nj¶„ïßïÌó 'ƒÍ›“cè®5ÊI^Ls®”Ts¸¶`Q^²»⇠×N–x'ö@flAoN²}¼%‚¶3 G0Zi %0€RÊ–RÒì `¬Zµ  šô<Àl<޹v='Ÿx’KÿåR¾õ­oÕ„}Òí\/¹äV¯^½àãÖ­ôúæ’w[ü颌`ŸxÓ7 óø÷ æ¡ÈAÔ›Ü-r_×\ê5B™¨Ujô}EÝÓÂо" á¶'ʆW]ÔËÒâÇ®Œ “—µ6§11LƦÆ×?fœ˜—ZF¼=‡d«¤³æ!Ï=ù% Ÿà< /€’Ÿ†Ò6ˆ{M ,^ )û7á=¾&¶„þ¼dëXKmÓ¨SÊäáŠ1Zt8@GØðì³Ïêµkצ¢@Zb,6¯Zâ·¿ÙÈçÿë«|õ«_Åó<€õO…cN8‰óÏ?žuѳµÊ'CLü0.Ñj`âݶ¥ B]³¨ƒ°nqì<ª%¯ú±Ð6$1Õá^ ênö8ÑÌõ—Âd9׬siZšöd$Ù.Ót%c ž Ø2òª Yº\YkÂ’±ëüì\íÍ èt¨Ö@k [à¹á€Ãú’Ûº ¡6 dZ[‰»´c¡6ÐeQñãô¦Ä3áX‚¼ä©~¨qR€ٕ1^³±Š¹·sNó÷™”Òj~– ‡Ž0 Ö¬Y£á¤ç†!cccüöÁG¸åK×pùO¾çÇD’îþx|­5™|7ùä¿M`ý›(Çgçö›Ê*‡º°ÝëñîX˜ÊXÚÕÀtjÛ<Rô?}¦‚%ˆ”†žæ¡ÀUCûÓ:k`ܲ4f€‹»™ Œ víúsÆ -s‰k™Š ÛŠ7Ç;Q󻞮°}¼Ì «³sØt¢™M|˜öá_Ç(?¾ÿY{Urû좼aÚ‰­ÇÄfbP MDÜûc½éH¸³"@5ÐŒTƒ…tÌ+‰±ªi‘œs¬¦òâûL)5¨µîB µpºmCG˜>ú¨>ì°Ã†¤LæöcçÎ<øàƒüû¿ÿ;7ß|síµ¤¿™C}ü?ýÛfÕúC÷x½á¯ ¯éš{=ŽGnõˆçÀ‹,ñ8S½ÅÃcÞöºËÝ|“øÖü5×ü¯_ôp­8fnâäyGÒŸ—¸–…c*U·ÆÃYÇWë˜ |ÛXõ–Œº±MÛztzä3¦«ãXÅl:æ‚ìIï:éjOõð‹;¿ÿÎOPè8îGÊÓç˜$ÞŒ@ ÁîRˆñF')LÀîbz€Œ-èÎ ¶‡Œ{¦ ™ü¥”–R )e8¸»•óm: À4¨T*YHêèè(»wïfÓ¦MüèG?â†nà™gžÙ㸤Ks ÎyÓßð’Óß@%”=…!î‡Ôv£ WõRµÆr4/Ðx‘{>&< cW{4®a3ù±K½;#'g×6ÓvCî}¶Ê©ë³,ïµjmO3ÑqN”'…¨5o™O“¥‰Ð5wìtèÎ:àqO±„h3œQø·RîKD€Üqß-hÞ•Ø5³¥ çJFʪ΂ìöBưî,FDS‰‡̵)¸&ŸeÇxÈ!KœÌ+®°ð‚€Ñ²‚~hæ.”õØg8–ްoã¸ãŽÓÀx»…íîݻټy3Ï>û,wß}7·Ýv>øà„c’Nx.GŸp §¿íc¼Puyðù*›v¦$-J’‹ a¨ µñ_ ¡£ÄµF ÛGG×y¦!Ù-Îbw¢Ø¸k7XåQòœñ¼[¸í7íòyð…*kúm^2Wkhï‚|jìý=]Q[ÔñиùÞY³K¦Bv=øS~³+àè…ß¾báÕ•ŒVU ñìv¢~1@òB6¾‡ ºÝÆJ€tø°âN€ÃåÖÜÑÚÈ*¥ŽiÉ `f´mkܹs'÷ß?7ß|3·Þz+O?ýô„×…~š„ŒÁU8ù¼ËØìõQñ5;‹Š 4‚Ù¶Lže°gS——Ÿ9ÒXàq=c›¿Õ« °¬èQÎG›˜¼%CåPÙsL¦›ß˜³AÁ5JJ\œ´ØÈzq²y`ßh l6Ùa~pÛÃýÆ|üXxõå$Ïíö©†š.óÊ‚Ïe2\‹zWÀZ@p×â{ȵýYSL’¿Vf½9ꩨV&(ºBˆ ­8ÑB £Ì­µBÔâ;sz/“ dêüâ¿àšk®ák_ûJÕuŒ´ ýK–¯âÂO~–“N9–±ªâÏUYÙgsòºL$àê¹w`³ 5hsÚÃÝKB\ΑØƽ´õ0!‹¸@Ò†cš×ÙLøÑß㣠(1ò’Ç·™\“4¸´ã9 ,~?Pò5= gÜÇ0 ´’ßlñ©øšl“÷Í¢^ h:=ŽU^ €xÿB bîêÔß\`!*0!¾Ì޳}OóÇ÷¾÷=.¼ðB{ì±=Þ³/lÆË—/ç3Ÿ¹šÿyΫ°¤`ÇxÈcÛ| ®`UŸ=Æs‰¡Š=~î-qˆ èéö¹qæ cïÄØ4tÀ L.G&“e_ñ€¹OîÿÉÍì/eqBVî`AâšbU§Â¦‚Ä ÁMO6éúÇ‚Á.‹¢We¬¢É&œŸï3yGF•†*»à6}êx)dµÖ !öLàJ: ÀôÐLÓ p"g{=é-ÎT÷ø$MSLßòŠwÜò>ýÑ÷06²{¡>CÓh¬8X±b—]vçœsv­Þ߉º±U¢Þì{®ÍQD4NkçíJ“GPòTj<Z£ ç Æ½xRÉŠÁîEôz€}gMø£¿å?~œ·¿úнÜ tYh`´­¯¤5€‰RšÝ%Åʾ¤gc …áÞ×Ú(&‹SÒ Ñao (zšAš¦*‘Ç8+¥< è(û*.ºè"}þ?:¢¤0A¨q[Ћ¼tèêÛ÷¥÷ßy#ÏŒ_Ìú®…¿±8—ë¦4¬¯î¨ßC½0á9‰º§0ï vãVØIO,JÌš2ØõˆžŒRjŸ`ì(ÓCKéŒ,ÊCÎÖä\IÞ•äÓT%&‰‰²ÄíŽeHb~të-Üw×’þ<³Fc2âK_úR.½ôRÎ<óÌ)µ¢2Ÿ°B­$*y˜›;ï‹£Þ´- vôfe-d’´Pè$ÛÓŸèæŠx}zCOrÍ·Â'Ï;-‘yt¹’Ც‘O%-üÁ„½ ®¬YÚI¯ùxä¬c”vŽ×ê&›Ô{r¦2i¤ÜÚJ)å:­µ+„ðZqÂv¡£Ì€7e²®ä²Nwe‹×°ù}ú…óé+/7Ç¥¬ž*4Îñ´ÓNã’K.áä“Ožöxu¥kìZ—¸rm;WÔô˜ŸìИ°@%Ðt'=™¾AººS,ž%âõ†!ßù·Oó¿Î;mA›ÅníÞ¬dw9Äc.ùÄK:‘[{çx@¨ÒÓìɵý9É‹Ã!J™}#IÄûSOƇí.+*~Ë*„ÖúÏóV‘ò<€t¤‰¦Ëú²å¶dŒÆŽš¾…@LþËζmÛÆ}÷Ýg^I±ðÑ爚ZðÖ·¾•/|á 3 0Ûk Bešç˜sµ¾³AWFÖò2Òtí{s‚ „’—‚9‰>–f»“WDæˆx­þþÑŸsýYð±$EÏ(˜fy%lÕFóì’}Ã6™¸–`Q΢èiŠ)šWWFÒ›5¬Ž%¿u÷£”²×¶íµ-;a›ÐQfFsÜIdî½÷^<ÏK¼Nx&4vìëëãâ‹/æŠ+®`ƽóY!ÈZ‚Pê_ƒ„[4|—+ ”±´Ó„îŒD¡*’„`ùŠEôìciñ=éy£|ñª+™Ã`ARõ4e_“øš§®~ ,ü†Ké´¶%èÉIüP3”¢y9–!šAÓIÃ:Úë³BˆµÍίÝè(3`ll ¥”nFx?úè£@z­ÿÉñþkA‹Ëd IDAT¯½–}èC,Y²dÖçÈØ¥4~MÐ&m ™Ç®ŒñLT<‚í¹Ž.W €ñj:6ÂÕ+q»÷1 €xí*žúõm|ãî'|ü.‹@iƪ*Uëk0/QZ³«˜ŽJ€½YC¶³”¶yî„’oþ6yóF¼ùå,ËZ×äÔÚŽŽ0º»»‘RŽ6sŽ]»vµj:-Ec}¿‚óÎ;o|ãœ}öÙärsÇÔþ@ò[aítM†o9UAÖ‘Ø"= ÀªEËXܽ(éi̱âZÙÁ§¯¸jÁÇ_”“)®¤‡k //±­z%@ò0'ç rNC"`ˆ×OoN"ŒVZJUœÖ·âDíDG˜‘`¤™s$ÕNx:4ÆúÖ¬Yõ×^Ë•W^É¡‡Î•TÅœ#k›¬Új˜žš{0ý$1]kÒ³1l ®#j ’žÛÚuËYºlߪˆ!„@«€'î½eÁ½ÝÙ¨-p©¡pAg05º¢RÀ]¥–¸´›†Ž\rY[PÈv׿•|WS0€Œ-.·f…S¥RjõÇ?þñt €IHõä’Fww·†šY¨K—.mÝ„šDc¬à]ïz?úÑxË[ÞB_ßÜ3ÁãÛµBhü0]–PÆX–lM¤R@ÁièpzHßÚut/]–ì$æ‰x-îØÂÕ—]± c»– —šFÏ5ç=nB[ЕµX{“.íÌÉ<º¶¹^£µuŸŽ¼¨ž¬ ïÂP9¤Ú¢½B”²÷¢‹.ZÝ’¶ `f¨fCG}4ìbot÷ƒ‰õß|óÍ\qÅrÈ!ØöüªAol)L)`:œ{nÄÕPL‘az·§# D~ë»ö¹J€BP>OÜw_¾éá3^O½9£qX;2MýyÉX5$Péà¾s?vg$ŪÂK‘Ržw%ÝÉh%Nè„f|9 †VO‡·f–íAG˜;wî •RÅf„÷Ë_þr²Ùl¢î®xì¾ð…/pûí·sÆgÐÝÝš-ߎZöú!5Ò4À¶ÛqªÄë{dûf¾ü©ËhJcŸ%â-aQÞ¢XÑ)*5À@Þ¢âQó2¥vÔ®¸k;-p,A_΢è)Š5¥|î{¾®ý‡ZueYGµjží@G˜ƒƒƒJJYnæ¹\Ž×¼æ5ÀÂzÇr]—üÇä‘Gáïx-ÍMpm×®ú • f`GäãÕtU€I<ª¦qT°æ ÃééHzó†Yï>¿ûí]\ü¹,ظyIÑWTÒCƒ ÂpT•f¸”Žõ†”¨/ošíXD@‹>üwüïïÜÂô•‡æú,ÊKüÆ*jÏW%û ˜ÜVkÑ%„Ø{-u‚è({GÓ+õ‚ .hÅÂ_ñjþõÊ/ò•¯|—ç¿cÒ5˜héä(©¨£iíÕÚ¦Êɸ÷ÍÜUô*óDa«¾¦ìcUÕʶ|À¡C<¶nÝʲeËT\*7_{ì±¼ímoãÚk¯mpc‚_¡Pà=ïyïÿûYºti[„~#K`[†p'=†‰}܉ [R’wDOFà‡šª)JGìBðdê¼%³E|<ùèC|ò“ÿÄw¿ÚþÒÀþÈ¢­êZY¢î½Y‰mÁ®b:zÄÜûyÇxåê Šó›“&J¸ž࿯ÿþ_—ðس;xðç7óë§ÞƆµ‹Î &¼¯/'ÉØF0mÍM8Sc”'¥ Õy¨ãn¯¦ý»iù®){š’§)y¦clÑWº ª¾êþÐl)\ùWçõAÛŒŽ0–-[¦•Rã­p—_}õÕÜyçlܸ±eJ@£µ¯µfÅŠ¼ÿýïçío;½½½XÖÂ4)umÓ±è”Ä´¡±@ÙSÑõNÇö,0‰G¡&bKA3Y9È1kVp‹;ü¤'3?Ôî©°ÊOnú!—íÏø‡óNmë˜=‰-Ã¥­“S2È»‚œS/LzB±œÏ:¦Ba¤ÁÕ>“0Ÿö|L>DPÚöü~ü˧¦œÏ-׋ïœ~®?ÐX꾦ì)ʱäƒPSô5a¨Ù´;@bö) {¡m™kšµýyAÖqjíÞs® +#èr%ÝÓ…4cÇýbt¯…>äï; À¾­µB ·*yïàƒæž{îáu¯{]"8Æd…`réÞäãÖ­[ǹçžË»Þõ.Ö¯O–pÊŽ:z!©ñÄ_YÞ5w]+¹V!㘦Rq–v:(žxØ0°„û°Ðx¿<ò«ûøäeã›_¾¼m-}YÓMN)¢¬ªä\±«] S¡°q—OÅ×äÝææ3Q–ÏÅBŸxœkÅä™CeÅ`AFÕC&|¨,ó Ôø!xÊ4\2½ ìk*¦èi*ãCüâûŸçÚÏ]ÁXy×Õ诸á·8Õ^A—kZ»– ÛdÓæ}ëhÈPYqâ—Õýv-\aG9NÇx: ïɬ/]·Ö:µŒ€`8n¥àX¿~=÷ß?ýèGù⿈ïû(¥öôñßBˆš+ÉÒ¥zâ«9öÕoæ’·ŸFÖIK§ÀµÁWõ€äšAÞ(mØÓk‘±Eg'}­´†þãNbåʕؿ}Š¢% !Ú/qÓ ßá’£Oáâóÿ¬åcÄû¢‚dËhH ÀÑIs~Ô$n5‚2ïFsfîîv˜,Ë,tâ¤ÞJƒRÚòè'ˆ,lÓ2ÜtÁ¯*ø}•Þ¬d¬ª({Q,Ý×TE50Ôâ~  ”‰¹‡*NÝ3 µûq¼ö£üì§?a6)Ÿ›î¼ŽOw*G­_IÖ‘ä-ëŸçþßW¹ý‰2–¸lX²÷¼©½íqÑúÈk­×Îbz‰ £Ì †áX«céù|ž«®ºŠ|à|æ3Ÿá{ßû[·n5*U£ë•R²~ýzÎ<óLÎ>ûlŽxéñü÷£%¶Ž†5¾´Àµ*ºI!ù¤£9Gšx^j\í®9G0Zi$IZptqÊqëùÉ]w°£”ØTZ‚X8W‡7ñŸ×|ŠßÀY/›+Õṏý@AòÔŽ/ÔäXÈïq /{47S *­*w™=l&w;Ä™í Â<þ[A s_A(|^^`,òŠoxÙWT“ W L¢k5ÐT#î…æ¸?Y!cMt³;–ñ&Æ,‹ÙÈ:Ϲ¢f‘;ºÌS÷|‹þñ½<¹ev¹uBvþú^ž~öN9j-î¶“éÒ ;ÇC´±ä^¼{ùš#o­¬ÑZ÷ !RçZë({eYåv¹ŽW¯^Í•W^É•W^ɦM›xì±Çؽ{7¶m³téRŽ:ê(kÇ—}…%E¤Y§CÀƂ˵¡Öøµ@æf<–Œy*éÇhm±VÒ‘¤ãøã_NwßÙQÚ–ôTšF|ß>ýëùä'.çÀÿó9[œoù8ýy+JÓôf›ÿ'Z–3¯Ú)¼ìÑó¦Í-v+0‚:Ž™›¸·qµûQˆÌ¯ mSÑ3Aˆ7øøy?Ê­Q‘"‘0×XÒ¬q[šxxoNµ-òhžÚ°´ÛâøÕ.YÛÄÍó®4Þ"ŠŸ×cì|á9®ýÌ%\þ•¯²cdÏÐéô×T%¾òùopæÉÊe{RŸ÷ç‹wYen/ À°X t€} P‘ðo«üX·nëÖ­›ñ‰·‡¡aÝKÌ%ÉØ­IM]{ŒØÍ7VÑIṲ̀€îŒ`¤¬Ò/Žù“ÓY¶r%7ïû Ä¿ÏÝ?þ&—]º’ÏþëÅtgZ;F_ÖXÚãUÝM˹ób ]Óàjâä¡2¡·Ziš2äR^ Ù>„ðÈfbT¢V b+½nµ{&ˆbðºá6‘BÔšWY‘0wmÃaaà01qG³ÏG–zÎ8±ÅÐÝÈÚ«(nüU‰®¬à¸U³û2B¯Ì£ÝÃGÞó·üðWÏDÙìØ•„ü9[GǦTz³’®ŒIèô"oNSРXü®é3¶`Üpà œsÎ9ZJ‰HAö˜æ¦ •Æ kG©@Ö6—§¤+Ù.¶(ÒB ) +[Û)¨°2Ëyåá‡òØÃ1ä§áŠ5!Ú+ñ>ÿ%–p¿à­¸ó8Ïtñ󞜔ÃeµÇºŸN˜CÝÝÖbܦŒ6ŽyA^¨ðBsoy‘ }‚ „¹èH0Â<ÐÆ’t›ÇóCYwRàDU;®-Œ0wŒpvmãbÏ;¦„0çš8y&vÍÛÆš7÷ÔüïoÇ‚®Œ`Ǹ¢ì+¦›»·?Ï-ßþ ïþÐ?3æé9UPÕŽ˯áã—^Èá«—LylÖ‘ôd%;ÆÃ¨µ9Íîe@)Õ-¥L%!PG˜çž{.€—ôrÚÏmÚíS êIØÍBÑ£”JeWÀŽ034P†¦5Á–@ sc+M­›Vâ^íh™¨# îä´ø&œ¨v·è¥¯@Îø‘e×wcK …`ý)g²ä€Ï²eË6Ô>.ücÄ÷o°í1®úç²jqñª—51ñ.RQf{#aŒ¡y„y`bçæw#ôßî£5k<øÕ°n¹nècuTgn p¤À±#ËÜ2xOV’±ÙˆÔ'k›R4WŠÈZ§–ÍÞ;,Q÷*<¹#àˆev ZÌœ…0·mÑœ»;#Mí½§œâ¨][Ÿç®[näï»]c•=Z™ï ññ™\ž—½êÍ|þ3ŸäˆµSÍ*Rbús’ „ñR; !rZë5-;a ÑQf€Bk­K@ „HüZI!j±öØE•´ÝoF0›]J¨sÍò® ìéf:|¶Ó§ TfìKU‰b§ð~ÿÄoØUÜGi§@,<6?v?ý§ ¹šSŽ?ª&˜«aœµ>1ù-v¹›x9T"ׯŒ{šñ*ŒWtd™‹ÚcÆ2Œ™˜8Æ©[íî$‹<=g5ÄÝM ~îwºšÞœ¤äk†Ëše³V2Å„_[¹ÇÄ‚6ç˜J§ÑÊD íóë‡æËW]Ê5ߺŸùYýZZtw/âoÞ{ÿÓ{éß‹†]ëîXX†J¦S§Ýd"`a.NΕl Ò$ÿA^t¨[‰{s¢dmÁ†S_ÏÀÍ·²«¸y¿LÆSÞÅ?|øB^ówŸdõkk”°5,2¶ÐJÔ2¶ ;g™¹-ÈØ†Þö‰í>Ï …œyxŽî(IÎtÉ5¢¬¸iVsÛÈÜ\î½9I¨4£UŲPNÇó.¸†«Þ@³õ¹§¸õ‡_ç‚ÿuÛ†KÆã:«+6¼” .ügÞó¦?‰jýg‡Ey£¨í*¦ÂfQ¯‡Ö¿mê„-FGØ *•ʸëº*yá•ÛYf‘×r’žVGš¸dÝ*JÃÄÌ ® ìëè†N–¨%†òŽDB-?!yꄸ¢ü•§pÔºõ<÷âfªû™ðñâ#?âÖ¯ôð7ÿp/9lµÒ“âã™ÈµîÈz"\œ@ç4¬%Ç<7TfÇîìl$ÎÜcç³ÏÿmïÌãäªÊ¼ÿ;çnµfí„ „a‘MÙÆ@„yqDDaœW•E4 ÎD¨ˆ .ƒ¸Ì ЬY ˆŒ(ˆHa“&†²tHzï®åVÕ]Î9óÇ9÷Võ’tuwuê&¹ßϧé¦S]uêÖ½÷yγüB€ŒEAA_‰0"SŸ“±(Ð[âðò}xîùgpÇnÁ/{Àèvýo¦pÊégãë7Ý€ù'î(ß¿c&%(2¦œ¡à1٠ЈB@!Ä ‡"vv/‰DXÐL‚›…F䤢°oäI£r PTædL ‡A µ4ÿX$M¹# Å€š´´ÁÕí–.Û¸NÿÈñLëËèè-ì‘Q€cÓšåxôvón½ óŽ?(Ô-™…ë ôW8² ÒàÜùè!³0L 趃¢¶hÜ/2AÆ¢XÿÚjÜzïrÜú㟡»(ë­ÇòéÌtœ÷™Ëð•k¿ŒÃ÷<¦uIÍŠ®"GŘ”ÿ†A9-Þ9®'š¢R«e˜ ÐÜ‹&xyJå ÊcµÁÊæ#¼Ç‹Î@  ž›µ|&s¸Q ¨ ÈUÛÒ1ôÞ¹ó÷=¸º=iP¤MŠI'}G´/4Ò|x¢ „cÍŸ–âš«®ÅW·cüëKie•´\.=ÝàÜùX D¶ô¥M‚^;Z!ÃR÷&¼ñ›ŸâÞ¯_Œ¯|û¶q˜}àøoü·ßrý˜Àô´†’ËÕDÁ†÷i‘ëˆ#u@‰Œ4ºFd®=¬ˆ:•¡Q'B‚XÆ’B-åÈÈK ah@R§5ÇwgCû·>f8†úªÕ_°@(FU³n²NÎL(8Ûr =ö>8íÔùxþµM(V"Ó ÛPäîŒaÍ3âKWvã·|çÌOÍ#êÛ©OJÈ”@Í¡R×Mµ ² Wæáô½fÂìž|òwXºøn,»ÿä‚à׫ü¡%qÜûÎÂW^sÏ8u|‹SZKZƒÏ¥xÀxk6;nCh±0Åb‘§Óé2€l³£€¬6¨4´QÂPB"ýåj ÙÁÆàµÓ¦,œ,59P5ère%H›µÀ ™¡¿ªùE ‡pjZÐ;^+Yqå€Ççp¼j%{PÏ‚>s!{Í]¥,7çäOc¿å`ýÖíˆJ`§Ñ9Þמ W}ñ l[t3.;ïý£zŽ´I‘¶(zlãÐûÕ)ÁÔ$EgÑCÙk®ðÊs+±ì¾%¸{Érléìðo£ù Æ\ðÙKqåW⽇Ï÷ú‘£‰§§å÷|EÞËèøk'ƒ[áT!Ä,BHû¸Ÿ±AÄÀd2 /„^>j Íp#“P"#¬(…¢6IÒ”-Šå ˆšToö£’14‚l‚`{žq©Sè³»Ê@Kã­æ—×(¿9>WR®®¸Œ‡™ê¯}Ç "¡I ›¨ZIÒ± ZÒ6özXßåã¸£ŽÆç.8×Ýv?*^ÄNº8oþu®½êJ´o¸_ùò…°êL’Z:ÁäE-5´&ŸüAô‹ªÞvÇ““''ÕU ØX¶®{‹/ÁÒîÇK¯o„?FO²6äßrÀa¸âª…¸üßÎCˤÆôП֤…©ô•9—NÓ8ºà/gxžw€ØØàœó|vÿ@jWŠ{J,*X:‘#?£•nDÂ"E#Í)Ÿnû`!950ä5`EîÊ¥&{Éh/0tî[c‡;÷`î¹Çx( ŒXªT§2âb)јlB[± K“ï9eHmö¤A‘0e?ºF¤lÐ[¤”(% ZßäûÚÔë#› ¸ôšÇÏx ÝÒ ì‘Å€’À ÈonÅ×ÿóËhïXo\ˆ}2#5ÐË¿›žÖÐÖïÃçbL}û$xuJ€)) Œ ô—9ö*?aôw¼…‡–Þ‡åËÁϬF€KAi­ªßQó>„›¾º8ãïÑà±dwNÆ"è)1x H)žäœ·†±?€U Yhˆ€‘árQq4ÕSì)ƒY²}ÌWÓÆšMmþ<Ð2/¹;ßz ¯Û.+ŒY`Ì•r_8)Í«îÒËG)Ü­«™æjºšÇx8°… ¡Ü‹ªdì›Ý^unH}ù„N‘2© /Ëb®¤zL(£Éܳ^3A-è_¯ýy´§oÊ”®e¡,8äH,øÔy¸ø›wÂ÷ý=´#@8ÌïÀÏ~x Þܼ 7ÝpN>jgRîòà¶d(ÖvÈIr– “ ›ŸÐs?ѱ‰r®.¹Ë~O=ý,úm£Ïócðß,>½àK¸ü³ãøÃçLØúÁÔ”†ŽÀàØ˜*WV­O¨÷˜>ÈÂ>®†­°`è «Î-/¹Ò˜•!om÷+Ãj÷²_•tõ9g› ¼/n¯ÑgÏšé, ‹¾z5/Ãîòq–N i2¬^kÈkCì2šó—Ò&ÅÌÌX½9uüÄÎtÛë5þJ Ðï¹äÉãjL>_[p þqÁÍ`ŒíÑQ Z”Fx}ñÜpõçð׿œ›n¹û 2îÁqÍ&)8rŽ™Ùxæäg)#Iý%es|/óËy,½ïXòÀÃX½æUttõ†;~2ÆÒÚóë˜ùŸÀ­7_…y'· îwòüoIkð™@¾Ò¸áfʱ|ÇùçŸ?©ˆ‚ýˆ:BQÆ/ѨÊÙF/2‰v {:>åE#ÈkÆ£z5úë%+ƒÁAíÔ9J^Õ໾šÎ“ƒ\ä=DÀ@É*®€¥TÞ2A*#‡©F;i*ãnÖ„Ü5YC@:0¬N€ê÷ðçZá!Tÿ8Ð 8z…8~÷Ù <K ž©xòxÁ—\ƒÜs7[½y6þµÑ€Þ­pÇíßÃ+/¶âگ݀Ì;nÈc³!RÝ.¨‹Ð À$‹ P Ñ·pЏ÷ç?Å’Ç+­CWO_ ƒþmb®¸ú|á3áÐ÷iÈšG"¸ö¦¥¥°Y_‰ £!‚9ê}íC™‰ØØ=èììDKKKd&¢P"eIe?wcŸ;t'Fj¯%eȰv(,¤!¦¦yóЇ0wn+ÁRrweÎ<(žó”£ÃT‹ˆ!q ƺ’nœ †­dLYÈ“µäŒïß­« Waø×÷f`j$ÌŸëDŠ+ƒúÐÐèŽèÎŒ9!ÒáШ@!¨O“ôklض½*ÔŒ-Ï?ù÷SgŽü÷í8çô1%›×zGõêêÐLKjHè]6à:µ¢qa*©æ»bcl_¯NÔ{ ±0œs ÒìuhTÞñÕ.¹^êiW® ]@†õ™*î {ιÇ¢•ëoöø(»ÞXÁkí®ì7÷eÅ»ë.ð™|®ªV€FªEmÒ i‹`F†Ê¼y‚"kIƒžP;rƒÊ]ª©²˜: "rJ^Þæ¢Çö1EÍnFÑ©9n; µ<¢#½DBåÚ‹M–^^§rŒrÞáº'ÞyʸæâŸcáÿ<±Ç§j©Þ;µ¿øÉ·ðÜŸƒÏ_w3.þèédkeÆÒÐ]mlb^^£ÓÏAIDATÒ*íreŽ)ɱíg×>÷8þçÎûðèïžAG{ìR)Ô†¿á8åcŸÇn\€£?¸iE΋"“ è)Ö蚈  FTo•¯Rkðß_!%!„ 2³?c`<Ïã”R;*7:ÙoOÃ|w½ç¢L ì÷¹¬lclOÀvd½VLFæÍ9¯ZæÍ…¼I2!ûí; †&Cí)“`zJV²g,¹;¯¶’4ƒÜ9…epzWpùÔnÂwt?ɘgL¹›e¼ö±Ò¨×w³&~¨]¾(…4´Å°C!i]u#¸L¶/Á’ Ü|~þȱx«£ÔäUîZjwr®[Ä+/ü×]~!ºÿLüçõÿS>ÓRzK²žDˆF À˜@o‰á€i£¸í³–ÞõÜq׃hýÛôôö¡âÊ€hPÜ4H*:3‹}ÿëÙ˜=câú9ç‚R úpj ½ ¦$)¶ôùa¤Uµ!„ —RÚ GÑK)ÍqÎmBHžÒ`›ïûÛc–euwvv–8çbÖ¬YœRYÍØJ¥Âc9uÂ4œju{}7 JÃÉk&zL„ÆÜåAˆ]æÇù2âAÞ¼¤Âí%[»3ç*ÔŒC•Ú– ¯OÎÔô—«ßMJPxLàë+x×LóI cÉÀzm8Žh<Ç" {†¿RG5e’0rQûZ@svjÁ:)‘QÛ ÷R»~1àQÙ à3y®Õã”j9wßr=N½èº½* Ôª÷ÝÛù6V,Y¼6w X*Áq«›Õ‰0üÀdœ~ÑüùŸÄ‰G€TBàd…obçxœs_í¬½Úÿ'„ôsÎß°U±UӴ턜ïûŽ®ë%×uóœóœçy¹l6›'„ Ù/jÜ›±0Çh9 ðþ vt> TbçB†Ø}Ä ÌÛž@É¡/y¼Úsî#Üâs©ÕÎUaëð¹ä²ç˜¤vçY‹†FW¥$€º3NÊ=ø…ÈL”P"Ó'oõø¨xbY#‘ZÊ”­P%W ¥döy–ÿâVœ|Îçáî…Q€€ÁŽ€àúº¶`Ù]?į–ÝãOz?®øâ—pîÙó`îb)þà#Ó5í+:^|ê÷xâÉ•x葇±vC׃ëMK7:²SA8êƒÿ–ÿñ-׿pâa¼½ºÍ±ßèrKù ï°Ý÷ýmœóm¦ivȯY³† qúé§3MÓöΓl‚ˆ€ äF±ôÅ«K#¡°LY _¨WÝëzëLCj°g-ŠÙªPLP´«e,Y$giò¦æËU¾–¤Aðê6‹ î1–òÆåÀ)•S]_ÊÝÊ'oÌsK³ÂNB Í€9|Äõ¥¶A3†µ Aåg¤41Pòd%´>(:AÁÑg}ß¹ö)\ù­¥{e* –Áï1†r1‡gŸüž}òW˜6çœý¡óð™ ÿ§¼ç¨°Øu"–‚àÊã>Ö¯}+V>‰‡ó(^\ýòyY¼É9²æ‰ØñkBʉ½uöÉÿüÃ÷uÐöÚ\ÛÈW‹©‹ØñÂfϳLB˜:% `JBU°D…Ù‰jU£HY2´®yÓ45Õº6Žp{mµzðå g7·‡\W­yýe^‘ªö„J‘*Ñ2PD¥|.š>®8 ¨Ï]eO¦ ôaÎ_Í0qñÂÛñì#«±xíÆ½Þ ¨EFL8—NgÏ–7p÷í·à®}“÷›‹ùóNÃÎú æŸv*ÞßÕìð•q2ÚßÞ‚5«ž'«ž[…W^~ «_x=¥ú»5&à³ ÖO9â¯x×—÷ÿé‡^Q óÇ4‘بƒËçe‰eP$uB‚ÜùØ»Ò[ð7Á·j`4Œ¬Fe#ÿ‘4]Â4I>‚€Œ%k:l'÷Äà³4ËÊŽ;x|"Ó‚ýö¬9ùd¬ß^ŒÅàcP›*Ƚ½ ß¿ ßÿK€•ÎâÄ“NÁa‡¾Sg¿Çñ.ÌÙg6¦LL’–‰ŠãÀqÊ¢P(ˆBo¯hÛÚ†õon¶'ÛÞ~ëÖµ’Í[Ûhe˜Ìw>Ú•ñ1ý¤Û°ß'¿ÕŸêù¯]¹–˜;upÀ4c«1¶p{#vé:‘UÚn¸Ëކ‘d« ÇF'R´+Š N´€@  aµ}DdÀÐeD§èÈZX;^Ûôýÿ¿þÕ½8󌣭 b'`' vwìžþý <ýû;ûS‚_ìÃîšhüôÁ¯cîYW¡õöضrW®#¦"pÜ-ð ª’i^¸]WR¶Qii“ȵ$uNÚ‹ªÝ.:ȵHib{P¿}³Ñ)AB#pUW °“µŠCŽ;÷ÿø‡È`hx:fÇ4Ð@7ó€‡#]D˼ÛpØ’ÓÐzûN½š˜æ;uຮ+„ˆŒ ®Ší¤‘Æš Ô1-ƒ€ ™3ŽÊñd}Ê («@Ö(Šêªs `ó ZÇ\&PeNv¼6¢é8ñŸ/Åí·]/;{ µ»~ŽIs^Æ{?{ºŸ¾kNènæÂbvNœ¨!„#„(B¢ ì¶ º,:áâ pÌÒ¥ÐèAEãC ”EQîó#c˜‚%P"U«5Í_¨JÙé²[ŸR¡nXøÿ—\Ç.âÒë¾7@0'f£Zà" [˜uô½¸vÕ͸‚ô4{q1#GêÀ²¬ €JŒ ‹ít*‹íxDî«Á‘15é”xLDd‹pÓš1¥ÓäøÍ]Î`¨ÚiKÁÈ5ZUêD7“¸èK7áöo|š¦EÆáŠi=U’¨ }ÐÓ˜wÙùØúüÕ±ñß}ˆ#õábH @óB ‚ȈÇ¡ ‘Ëä HÈ¡«5¤MO =JQX˜D#rúX®,«íH¸års—6¥¶…íŠzÂMa(X3S¸äËß„f$±`á÷PqÝH¹61c¦î'ƒ•}Ÿt^ûí7AH´*lcF$·š¨cÛ¶ ”Fæä¦ª Àçò+JXºlQt<¨D}ƒed,*§#mÛL¤0AÙðš\ØÉ9R­MÞ㓦œQr¥úå`iÇÞ!Ä×Ìdé’7äïùîÂÒ“R"œèGvGîúÍlZ]‚#o>­#6þ»'q Òé´™\£²­Ív9| €€À({R؈@x"8:i“B`øá6Í„R)" {J™öRN–Á¶„PJ‰üY>&Ù\ñ8|&„N‰ ,„( ! ”Ò"€"äÆ9/QJóúô ÍÊŸsù5•|eË ‹¾½øƒ[º‹ûHṎˆWÄŒDMž€‘*«ñwû ^ºc º.oêâbÆGìÔÏàqMCNæ#အ(aéšFPöy(R¦Œ`G«PFä¸béÔÉ€Ù`c¾ƒŸÉ Ñ¨>ç¼H)Bl!D™â!BH @A×7©ÈW+2.\.c¬¨iZc¬—RÚ ¿\.W’Éd0‘ͬ™pÍüËAø{Tð­íœäø ƒßCL$Qá~A˼Šýßý6üñ[ ¤ÜäuÅ4€Ø¨ƒB¡À²Ùl±ÙëШì÷˜ˆXµ½tt*§îE¥@1 ePPB†n×DHÒ à5b@#Î 0üÓÊBˆ WáB*„ç3º‰©¿Ãþ×ÿ­¯DÛQLCˆ€:Èf³ò& ¨ÒÜgdûh4þ±Ðª¹~3Ý2íO8ðÝK±ö×Kо®Ùk‹™ b zzzøôéÓóÍ^G-¦.G)€¨Ü55J`R ïV#QY›NSƒ(:²Ä]$~eµÂ5ƒóç»òdñ›Md>Ô`sÎó”Ò^}„>ÆX€«išíû~QQ4 £è8Nɲ,—â§}Ï-ô‹Ê/¼U9õ ##Ór:‘üW+V‹ ñú‰+ð‡Me|¼âᬂ *â´À®¤Öð÷ƒšÀä}ÅêÖÅØ?ÎóïéÄ@0Ƹº±7{)!†&Ç{ÊÊîÄ–íRd¨ÝãAy™¹Â¾ãáÂí2 .¤<0çÜ¡”::žÂUƽ‡RÚÍ9ï&„ô©¢8OQáœä…!DÁ0 Çu]Ï0 ×uÝr"‘(°-ZT¾ñÆ#Up5È=°Ü}í©xje>Þщóº+8±‚8-0ÁÔþlzâId¦>†O<ø ¾d/öùÞ@ìÔÁÌ™3""6Ê+8,ŒÐõj©@~ž½ñ«Ã‡ÑkÒÎVû8UÉÞ @€ÑoR¸%—;>CC?¥´Ï÷ý>]× žç¹†apß÷]×KlÛ¶K¶m—gÍšå.[¶Œ·¶¶ŠØ¨7žoý[|ûÂXñ‚Žs:|œÛWÁqˆFS5üz²Fj’-OàŒëDz‹Úñý#›½¾˜]HìÔ‡àœ BÈÎâÆ»€ÀÀéD*´Ek" $¡ËE5®¸®ã5¸]-øY}/ !ú„ý”Òd¨½  ¨Âí=œónMÓzä8ªˆ®âºnYQ¶,^)•’Žg€õw ÖßKý3Ö{À!ža 7î9¦ÜÓ…W¼rÌ;ðx"3™ƒ—œXŒÿx¨^ƒF‚€f;AñŒÄïpìÂ'ñÔ¥ÝXvQsWÓb N(¥A‘U$nDš&»ªE€ê—ÔùäòaI5ÐõÅ€Ü9çÜUƼ RzïBthçœwjšÖ#„°cžªZ/ù¾o†aC¶»¹”RfÛ¶—N§Ý®®.·­­Í9á„êÖj¸q´G f—òòV¬°ú´øm{ ï+[øHOóíê'GF¦ºÛ' ÀʼŽLö×À̧p̧ÿŒ•—æðÔ¥Í^cL‰€:Ø´iŸ;wnˆÎˆSP¸¡0®5 ¨pû ¡˜àçZ‰×ð8çœRÊ8ç>!¤@éОÐE‡¢£âò~ιK)­pÎóBˆ¼®ë}¾ïç8çE˲¤Â¢ÈlÛ¶Íyã7Üùóç3Dk2NLxª /xùÜC±ò•·p„nâ¬îÎè«`nÍÃbg Jí±  †‡ÉûþFö7 Æ³8ææWñøÙV®jæc"BìÔÁܹs¹R?köRBt*‹Ú† oÃ9+µ­kµ^¥7YÍÞMéæœwSJû!%ÎyŽÒËëBtëºÞ  àyž/yÅ.cÌ-ànïîó§.fÏžÍ5Mã!$bÒE1»¿„µÖÞðxú—Ïá@ƒâhÎñÌë«`zÍC÷Fg` Ñ'`MÝ,¡ÀìãÖᵇ6‚ŽÇÏnæ:c"ÆÞv¡Œ !„à÷î¢À°7±Ú<ù–>¼bãÐþéˆTøïƒZÕòPÕê”R›sî°)¥ÝÚ…Û9çÛ5MëPò<Ï3 ÃuDZ,Ë)•JN*•rs¹œÏ9çS§Nemmm¬³³Ó?þøã‰€Ä4‘#¦bNÑÇ~Ãaš3rNeÀöÀæµ=Õ!ú¾´D/ôä£HÍ|BoEË1±áÞHµ/ÇD‹8PÜ÷ý|";¼ Ú™~Œ ÀS…m¾ÂÑ©è7)¶Û¾ ÀÛùó<GQÑu½ ïºnÞ²¬€ŠmÛ‚sÎ'OžÌø›7of›6mòãp{ÌîHkÚ´ UgdðÛV-) ºÀ{*>æ—Ž-ùÈ ó§»«S0(¼OtK/ÜÒcÈì¿å®×@²ÛÑ·®ÐßÚ´…ÆìÄ@B¸ëºùÚá*ŠaÃí;³‡†=x!„nï$„´ !:Uè½(„°•N{ïûÝœónÓ4û …B9›Í‚¡Äm—3Âd¦iš –-[&T»š@lØcöpÐZO›?n-à5 S¦$q \œTfx¯KpŒãcº/†5þQt ¯‰) ~ O‚NZ‰´¿ Úƒ/´öàFÂeÇkLL}Dí„,Bˆ¬.À9çjØJ€~ÎyŽRjCæÓû9çBˆmš¦mРGMOc¶m3ιŸÍfýöövoÖ¬Y|ýúõüC Œ9?ÿüóEn‰§LGv}Ò®…TÆÄ ‹âðžŽwÞiê8Ìö1—5÷êÚ±óA¦0ì/HN{ÔxŽ÷:„ßd2Þ qx?f\Ä@!æpÎo¥”®cŒ½-„èPav²5ÍV_E%!„¿aÆ_´hQ¼+‰i2—Ær á&KÁLùÈP -¾ýÌ2ï%˜+¦Q‚™à˜ÃæLø ݬÚ:pôÄVèéç‘ÐÿÛë„cÛ˜|°‡Ü¹EàÆÝfæCLô‰€Q ŠÅ¢E‹Ä¢E‹‚ 0@lÐcbö´c³LR=  É~i-©¤‚)ÄÀ4´”|Ì$@VÔ<^ý-U³|ÈVW¦¾Ê0Íè™íði4Ñî÷ÂñJ@É•ÙÇÞákêÖµˆ‰ ±S?ÒÀ߃Ÿkÿ}8j»ø ¯˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜Fñv ¯‹Btˆ!IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_math_32x32.png0000644000175000017500000000066613561570220020227 0ustar otfriedotfried‰PNG  IHDR szzôbKGDÿÿÿ ½§“kIDATX…íÖ½KÝ`Çñ/ÜÅJ® º´C­‚“_º ….Ú¢ ˆ(Ž"¥‘»ˆÿ‚» ¥s¡­AiéÐ¥qqhT|rÅpIs“ Bó…ÀyNÎÉïäÉs¡à§©fý C ò®±«¼ zŠ¿Xˆ¸×ŽGx}Lä-~Ë"þàI¸ùF;øŠRLLíçË•‡ø…­FŠÔcçx‘"§SØ ùfñ&kïpˆÖ„ñ¯0Œß!ß{¼¬ÚÒ0Šåñ%T°Y]·àmi…¡ kò~vFð%‹x ëâ·þ_]pŠU»‚·(cLÐY‰XtB½˜(6°„qc˜Æ§$â3xáï@?&ñ+1í!»?ÝíÔ>æÐ'þ‚Yw]¢;"ÿcÈÞswúájòžf“8¼ýwà½$õ)È‹Ô$-±=)è’œ4ª€$$ YIòÐ24à´  n6Y9ù™GÛÇIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_graph_32x32@2x.png0000644000175000017500000000073513561570220020746 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞbKGDÿÿÿ ½§“’IDATxœí˜»JA…?oA+É––’ÚÂW°Ô"…OðÔÂWÐÂÂÆ,ÅÎ^A´´rQ¬Ô¨±HŠ%Ž›Ý8óÿ= ³Ãœ³‡™ !„Bˆz2¨Û4Ôÿ.'CÍ‘|=ÃrmóYa¦=Å,{ŠÏêVŒ´w#­? ð`¤ýb¤SÈ$LW€·o€·o€·oBû€X¬ëï[ƒgè´Ë€ãHžLéç¬p“Òdí§€Qo@·bÙ2q–òcf ©ÐUE|4¼ xSûBs8°5ºI)šÀ~¤¾Î(q—àN°Ûƒ^Ųâþ±=ü±¡ðLœÐæ#ôó¼Fèà=R?¥Èíÿ5´L‰ð6àMí0: ´©¾°\¥0ò £NldÆ ep[ð¾ ,Ñ_çï ÚÝÇ45IÐ_ç3Oµÿ *oÞÔ>£e°EàÂHë8ÏWxð1xÎFš§Ãž«À‚¡æ£¡–B!„B1©ü« ¾W{˜2õIEND®B`‚ipe-7.2.13/src/ipe/icons/paste_32x32@2x.png0000644000175000017500000000602313561570220017751 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ð IDATxÚÕ›Ûo#WÇ?g.ž‰c'ŽCÚfwY.UÛ]Ø'ªJ¨R‹hU©ê€Z¶PñÀü!¼UBE¨-Zxë—ªOHhO¨ÛvWHPª–½°;qì8sŸÃƒ=ãÏx|ì8)=Ò$ñ™ñ™ß÷{¾¿Ëœ9œr{ùå—ßB\´¿o_»v퇧iŸqÚ!®®­YÚÖÖÆBß;8èkŽã]¾ØÚã?Ê•+ß@J©ô!7nÜäÆ[úiwÐívøðÃ÷ _ézÓ¬Ñíž…iˆUöÊ+¯¼ ëâõ(’_ËŽ½»»Íæ¦ç¹JãX–Íá¡Ë½{Ýl·B|"¥üéµk×Þ=u~þâ#ÏJ!Z*…²7Ÿ~ñÒåGõ6BL†‚ Àu%£l{ Ó4™ö˜½½.·n~mõÿò{]zJr’±Ü×à7¿øÃƒ¿*ð³—z^À»íZq³nÌõC tü7Ž¿ÅK/}( ‰ã8CÀè6Aàçú³ç’¦i¦YKÍKNkš†®ë¼óÎ{\®½ÏŽu8ºq™=™þÃã º½$O—‘P¼úØyK^ùj]9郺§Ólnà8Q2…Z­–r.fj¯ü¼®ë¬­­£ë:Û›5o×Pi–~=:Šîî?ÔÐ_j­Útï-ã»òpéõ!Bth460Mƒ(Š  Êç;òç't]Ƕ×BðOñzF;=—‚å? Ý}H)ùúÃ&› ]¿{n—Ù­œzb‡N|Ž×~ô4­XÓ|ôÑG¼õÖÛH!QŽŒ“Ó&Rš‹}2'eÃ0Òñžyöyžzê©’1à×o¾W;GÍ»JÒU& Æ ÝÞ& Â/[–”’^ï~ßr`&d,Ò79i567C¤”Ôjõúzîþš¦a𦠙Œ3‡…¥êß÷ 9Ý÷=@Òï÷èt:…”§6볕`Yö8`J‚ÀÇqŽó@ s¢Eð  %•UC½¾NF ‡GX–M­f©Y Ø„Ðð<—0Œ¨×ëóm•jwW"@JsJ¦‹¿L»ÝææÍ±³³Uå—kRƒ´Ûm.\¸0ç⌠€ª |.R•IÃàµ×~Ìõë×ét:ÄñêfFõÂåËßäÉ'¿ÍÚÚZÁÆb ]R7š#ÿ¤íîîòÜsÏáy>«”ÿ„õõzŽ€ò8’WÀÒ$,È7šn𦱵µµrà¥fUØ“€?™dv097œU›)÷)Bääâ% H—”Üós_.÷!ã'R@2n*§ÏQ³f}öÓÐT X. Lª2 îܹs àË7›MΟ??±1sÙt ¨2}¾ $Œž±Tä^V2'WŸæ\fš&ÍfsÀ‹€Êúl{m¦U©VA€*“¶m§’\ü|àe³.‹P²Y€ä´*àÕàg—…?ÓRx²D*0àº.Ýn—EšªÜ§g}{{˲s}¬¬ƒŸ7X ƒÀ//÷fs˲J®ËƒW©^‚ ZA±,ðjðÕrŸåiõª`² ̬ÙlréÒ¥*ç‚̃šîŠ^?‡^Œ€ìÍO—Íéó#þ ÿÿXÉ‚ˆªF/>T–Áò€ªÉ˜ô†‰mW¾ìWVP OŸÃ€ëºi)¼J¹'}“ÒW–-'„gížWÄ)—ªítå.+}_fÿ™—–esîܹJàÕdLúg¹@uà#UÁJbÀ"Y@J‰i˜fsðYàgR.÷r’w³ž‘" kЬՕ“Ë}Ò¯Ò7 ø´-2{î$P^TLƒï÷ܹs»’Œ2BÔÒk|³Ù`wwärB4MËÇ€“B“R¸¬¨˜žM‰ú¬Ï~ŠSžÚ4î×4-% 9'Æ6/³oýÒ€RjÈP²°lS16«ºz½Ž®ë)øì Û•BeàËVaGYส_ !0 !ÛímÎíž'Â0Äó<×áèèÇqèìá‡>½nÍÖ‹ì±WË™B(Iƒ«,a«ò»aH)‰¢ˆN§Œ¶é9Žƒëºì÷º¸žÃáþ!Anoâ £…™»â$%lx)ct]'Š#gà\×Åu]Ç¡{°‡xô{}â(¦Õj­€p1V_´„-ëÃÑvÛ(Œƒáp˜ÎúàhÀÁa—0 9èö0t­­Fƒ£ã£0]öŽ I”ÌÚÑ™_|…„a˜F!Žã ãñûǃƒaŸÀ9<è±^¯Óh4ØØhÒh4:Ã) ÃEn¹IJ„íÝŸ5ëÓÏèU/¹K|ßÍzEGÃ!RJ‚0d8ì°ßëF!ÃÁßõÙÜØHÁ7›Munß]l—Ê,¤…Tº®O>뺎®ë¹µø,øyG–€‘ª¢ü¬ðáÜ»‡8ŽqAo@­fÐjmŽg½ÉÆÆè¨××ÓýÄH²|Ë4&`G1fÎÓ%˜Á’_¾ñúB /ÛäØéÇCÍ4ØÞÙJ‰;:rt<äþÞýt g¯0^I hîø(`kÀZ,eڟĹlÿ÷wxæCYV ËOÙÏÙg†lA•[`™º6[te§L øŸ—Î} ÝqŒ4ǘ5ÀR P,ÀŽ%šŒGÿ½±nk#Ÿž:øÖ3ŠÍìI|J"–ã³1¯4øaüÙöÜ'}Ä2v[§þ¿‹§ÚŽ}ÉÝ®úa|{ÌGöH] ‚ñáß¼íþj}­þÂ;;ØBij?ÑLU“R“’ÞûŸ ß<ÀÏ…Çf;9.]¨í\¹XF×´v,Ñ“Ì#—[z9£&@ „D 5AD²ó÷ÿüñ}L€ËÈÿã2’–Ä“IÐÐÆ×|"dìúã¿CF3î‘í¡¼p’ /ðÿ*=õaûüm}»¥tEXtAuthorAndreas Nilsson+ïä£XtEXtCopyrightCC0 Public Domain Dedication http://creativecommons.org/publicdomain/zero/1.0/Æã½ùtEXtCreation Time2005-10-10}þóØ%tEXtdate:create2016-01-21T14:13:06+01:00 ]9=%tEXtdate:modify2016-01-21T14:13:06+01:00xtEXtSoftwarewww.inkscape.org›î<tEXtTitleEdit Paste¤bEiIEND®B`‚ipe-7.2.13/src/ipe/icons/mode_splines.png0000644000175000017500000000064013561570220020102 0ustar otfriedotfried‰PNG  IHDRY ËgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTEßBÿÿÿÐj©0tRNS :±)ÈK¤M+rbKGD†Þ•z pHYs  ÒÝ~ü]IDATÓc` °—Éòr§Ä©hsÄ‘9êÈÊLô³@iK («„ãÉàéÀà UaÀÀ2…e TUƒód¨*f„ ªÁ`//Cât” Ü qŠËÉ&kÊcW%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/snapgrid.png0000644000175000017500000000053213561570220017230 0ustar otfriedotfried‰PNG  IHDRÕkgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ< PLTEÿ€€ÿÿÿÿvn÷³tRNS@æØfbKGD Lò pHYs  ÒÝ~ü/IDAT×c`@Œ ,è”h(`—ƒSZ À”þ°†ü§` `\·v¼6€ˆa^ é™r%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/grid_visible.png0000644000175000017500000000056513561570220020071 0ustar otfriedotfried‰PNG  IHDRÕkgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ< PLTEÍÿÿÿ˜!îtRNS@æØfbKGD Lò pHYs  ÒÝ~üJIDAT×c`@Œ ,è”h( Ë9­Z¢2˜–0005p5p10p1p7040ˆy @r @ƒÓ†U }\«XH²JK¦iÈ;|1%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_graph@2x.png0000644000175000017500000000061713561570220020104 0ustar otfriedotfried‰PNG  IHDR,,„ZbKGDÿÿÿ ½§“DIDATX…혱NA†?!ÎD sZØX[XhB‡ …ÏÀÐú4¶>†V44„ÎÒ†XXSÞZ܉8Xöv.aÍ|Éä6w³3ÿMnwîEQþ5kÜž…âà˜ Å[ӰƧÀ“`ì/*\·Æ²Š‡Ú¥´È]‚£@W ®š†Ûe/ÀýƹV~¼F×R`˜3ˆY“8ÔÒЄ¡Î‰Ãg¼gœ×Ÿ¦H¦¨Ý pæ9¿]"ç•§ÿŠì½d‹üeŒÃz%cóf‹´+¼^=ïþ¸ñœã›cáé¿—|[;¸ÂÁÛZt‹.:ÁBûð÷>;É*8LAûýV4þGGÂßG¨8Ñ=ÃÑ Zt…\]8ßÀ\ ÎNÎ)ÝâýZ³K OöcF‚O¡8Š¢(Š?\“¥¾z£ËIEND®B`‚ipe-7.2.13/src/ipe/icons/snapangle.png0000644000175000017500000000057613561570220017401 0ustar otfriedotfried‰PNG  IHDRÕkgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ< PLTEÿ€€ÿÿÿÿvn÷³tRNS@æØfbKGD Lò pHYs  ÒÝ~üSIDAT×c`@ Œ ‚D9 F†U@QF†} IÅdddkqdS‚`ŠÕHˆ†AŒ—ƒ¨„êšâ1SbP’ a¶CÝÜT¹$І$%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_shear_32x32@2x.png0000644000175000017500000000126313561570220020744 0ustar otfriedotfried‰PNG  IHDR@@ªiqÞbKGDÿÿÿ ½§“hIDATxœí™AkA†ŸY¶Y5 .#¶·”=usIîA¯ÉÞòŠàUÁ“øù¸³˜.u÷Ëk%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/shift_key.png0000644000175000017500000000073513561570220017413 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<9PLTE‚‚‚>šã3™3™ 9—‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚‚ðððééé÷÷÷ñññöööÀƧtRNSè³·*O7+12I‹:ËK pHYs  ÒÝ~ü…IDATÓÏÁƒ P A%ŠþÿÇvšôÒér`æ± ¥?“s”býR¢ä¼U&b×·2[œ\™Ç¾¨¾ÇœÞuÂKýf܆ƒ‰È·‰Œ]{ÅûЮ¼5YžÿV>"'ã,_|œ n9 ©¸Ö³µ5`÷ûu»ÒDž¼¿DzïÍ—Ì€Uü&’C%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/mode_rectangles3.png0000644000175000017500000000076713561570220020651 0ustar otfriedotfried‰PNG  IHDRÄ´l;bKGDÿÿÿ ½§“¬IDAT8íÒ?HÔaÇñ×ÝÏŸZà)˜MÔA‹AÐØZZƒ†n’Û¤h†(Ú\Ê–²Æjk¨¢Ô@œŠÄ@Ãj(î®û6Ü]é©y¨Mõžçû|¿ïïóyž‡ÿúÛJV‰ßBÞáÛf5Û‡÷Åãvn| —kóvÇ |ı§žlv,­«ß w…x‚CƇZ“¡OÙì« #+Aw׊²k¸Êâ ®¾HÓïÑ×16¶ÜèÇ}TÖWð…™ÌKssŒ/Ï .Wn2óš;Á¶5À¿k“äÞ—4-Óôk$É\TÔ6Ót¶ÒÓS.æóu;»š«þ–y¤‹ƒÕ«Èf3™B!IGFÀIŽªþˆfÔ(-·“¦³‘Ë•£³³Ä^ás­à r?Á‰Æ` (••J¿Š'¹ž©Z;†S¸†çxˆÛQM;;ÏÖaz Œ6ý( Êá4îbá0Ï‚(ww—ttT¢µubÜ%Úrž AÄÔTÄÀ@D{ûÛÍ öQÉç‹ÑÕU޶¶ÉÆœ–u²g1”™ž®¯gÖ{È@?¦ü±é^­IEND®B`‚ipe-7.2.13/src/ipe/icons/fit_page.png0000644000175000017500000000145513561570220017204 0ustar otfriedotfried‰PNG  IHDRójœ gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<çPLTEÿÿÿދВŒŽ‰""!:;9%%$ ))(ˆŠ…ÿÿÿ‹ˆøø÷÷÷öþþþöööööõ™™™õõôôôóóóóòòòõõõóóòòòñññðñññðððïïïîîîîîíððïïïîôôôíííìììííìììëëëëêêêéééèèèçççççæëëêêêéæææåååäääääãææåææäååãååäääâääáããàããáââßýýýiøß@tRNS§²ü²'1;GS^kpi]QF:0& GòÐbKGDˆH pHYs  ÒÝ~üéIDATÓmÑëV‚@à1³,ÍR»xkŒDå¢0$šyyÿçñ0ë &íŸßœ}fX’i¤’!„4š©´¿ÿ mÿÃôC:ñçY˜œš¦“;Ý ¦RÉJp²CÕô„™Óô¡1 ÃÒIt0Ò‡¦3¥R¼Ã´)rt¿ÒU5èÛÖtæ"³I'ê¡èzȲrþ9ÜGå|Í]‹åw"Cß}Ïã~¸Z#GŠW¬~Öd£ÜBÀß-²ès.p³Ûî‘ç*›Ê5pîæ6w_(>”ŸÊ•êóËë[­~q?gGèÿ×%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯tEXtSoftwarewww.inkscape.org›î<IEND®B`‚ipe-7.2.13/src/ipe/icons/copy@2x.png0000644000175000017500000000331513561570220016747 0ustar otfriedotfried‰PNG  IHDR,,„ZgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<bKGDÿÿÿ ½§“ pHYs%%IR$ðÂIDATXÃÕ˜MŒÛD†ß{mgw“Íþ4Í$ j…Tn{êp!Nl9r,‰Šm¥.å@N½€**!.ܸ@¥rA@%NˆCQ‘  @*'¥í&ÙMìÄ›8öx†ƒãÄŽÇÞ$Û]ÁH–¿™±gžyç›_ëëëÊÚÚZ‡–––ì³gÏzÓüK*• ]ZYx³\Z5 ¸¾SçõêÎG•JÅžô_€±räHn}ý1và°”Rܺõ½{óæ·Ë¦0ÆÐéLüÿÄÁ0f÷×à'|ÈáP9ÿ? X âÃÿuÐN‚r‰õkµm´Z­Dº‚þøÓ¯:=çÈ$Boß÷Uõ W>xo,vJ•ߎ•}îÌ™3~*0ç²y¹ÑØ^>vì‘ò Ï¿¨ïC(˜÷ïo|¹öëßO¸“ \.—P.—éÝÕqÿÞáû>:Ý}2ïfgç ( П R]—KFŒçù™Rm˜¦™Lo6CDã†B!¹ë8œn÷à1…¦§‹E‹ÅXç@Ïó°å8 DUåN¶mN6ôåvËJmýþaGA“õd›¦™XZí(Qß[–ÇéM‹Íå äóyé—™.1;l£ÐD!0›MiÛíö„ŠŽÂöââ"æçóã)ÂišM3[R9`XòƒÉòòJÂç³aåÝ/ ªª6U²V«I—æímia†¡Ø{ñËòÓQð~j¶Â}tpÎÀ˜›ðaæ3¨JÒ‡·¶ª°íl—HŽÕ(\`ÏÍÍãèÑ£p)ð®T*£T*'ò÷ÝP­nI`8|?m/3žŠBœûD 4j§úp .O(ìyòÓùêê*VWWG!RãiàB¤Oi à(Üöv£¿4Ç¡fÚÌL¢ ×uc{l¸$(!š¦âiSýxt£c …ù„Â=¯ÏuÕëu´Ûí ÕÐ6 Ç?6* „€þ Uó½À.Š(Š 0ÆêµZ"=—›¥Ã#â¸Ý†™Uš'„€Ï‡ö¦"P˜gœÁÒó„X\,fª8.xÜï…£‚ªQUå@Ù a0M ½žÉÛ NHº?ì­æçç¥õ.Á}éf=[ñø’jÛí¾ËAãq9hXV±XD>Ÿ‡¢(ý³ ˆûp xÜe ”Òð¸’Pqyy (,ëþÀ2 ªª‚R BHRá( O‘”R:xd@º®A×µ‰»? ­CQ”t Ÿ÷‰$l´(p–ŠéªÊA ! Èð¨KxžGœþ)" M)4$eŒEZœ½¤wÿ0“A+Šy„yLµR©t®^½òç§×>) é×m€/¸~≓Bžªâ8àYÑ<Î9ªµÚœ6Có…ÏÛø c†Ëï_>Å!^¹ITíþ(ÜVu B½¨ë:TU…»»»øù—Ûèv;3 ¬6ž4p_ ]álUejÞøæ+,-.ƒ Ÿ1pÜ:1Æà¹(¡îÅóïþqéBeÊË@!çbªî—ú)UpêɧÝnÍf3ÍYª¦ ¨Ðö¼`çg™<σmÛ°mÍVC0În?óô³/ÜJNçÜ÷g ù ÊõaœsŽÓƒëºè® §ëÀjY°ÚMιøâÄã'_>}útì2oZ`B¡iÚ@aBHì £ óóú Áãz,ËBÓl ç:ž äKßùXV÷ÄÀ”Ñ{ÕÚ~ýók;¨<²pàšÚ 8ýŸCŽ^ÏËyÌ›­Öïû¸N¹òÚÛ››VZýS]CV*M×õ±/¤÷ º®;cÝ0þ ?EöP)n ø%tEXtdate:create2016-01-20T14:40:38+01:00ãåÃS%tEXtdate:modify2016-01-20T14:40:38+01:00’¸{ïIEND®B`‚ipe-7.2.13/src/ipe/icons/keyboard.png0000644000175000017500000000131313561570220017217 0ustar otfriedotfried‰PNG  IHDRשÍÊgAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<ºPLTEÿÿÿUUUUUUTTTUUUSSSOOOSSSSSSSSSQQQKKK(((DDDPPPRRRSSSKKKLLLOOOOOOEEEUUUúúúñññüûûðïïÿÿÿ«ª¨¯¯¯›››››šåâßàÞØœœœ———TTTïíí¬««òòòBaÖ,tRNSUÇ 8W–ã«Ç±9i°¬¬^— Zg# 0?85.ÌÓ*‚bKGDˆH pHYs  ÒÝ~üÇIDAT(Ï¥ŽÙ‚0E+X7ÜÅ}t\ÛªˆþÿoYLlŠOž¤—I\†?É?„ yª\ #'E(Yåï$•j ê¶E•‚F³Õît{}G¹Àp4²Ç“é,¯þa‹%Õö ‰E\ØëÀ#+8žt`-ÅùÂ8,Nœ8K»²›<˜É”Š»y(âÄ)§VEÏèaâù|¿ÅãÄ)ä©HöàØ¤l…bãÏuMªÐy%"“5q·»@gçºrlÇzŽ3D2ÉÈ`Ÿ%tEXtdate:create2016-01-13T11:29:10+01:00áò7¥%tEXtdate:modify2016-01-13T11:29:10+01:00¯IEND®B`‚ipe-7.2.13/src/ipe/icons/zoom_in@2x.png0000644000175000017500000000261213561570220017446 0ustar otfriedotfried‰PNG  IHDR,,)Zª3gAMA± üasRGB®Îé cHRMz&€„ú€èu0ê`:˜pœºQ<PLTE7i§7g¥7h§:j¨9l¨9j©:l©7i¦9j¨6g¥7g¥:j§8i§9h§8i§8i§9i§8j§8h§7f¦9h¦8h¦;k¨8g§:j§:j¦9l§9i¥9j¦9h¤8j¥8g¢8i¤4dž7i¥7d ­ÆàÂÖêÂÕêÃÖê­Æá¦Ã៾ަÂá®Æà¥Âá¬ÅàŸ½Þ¤Áá«Ãà­Åàž½ß©Ã߬Äàž¼ß¢Àá¨ÁÞªÃà¼ß¢¿á¦Àß³ÉãºÏæ¸Îå·Íå¿Ô霼ߺÐç¯Èã®Çâ¬Æâ«ÅâªÅá©Ãà§ÂàºÛ¿Ò袿ߡ¾ß ¾ß›»ß›ºßšºß™ºß™¹ß˜¹ß˜¸à§Âá–·Þ“µÝ³ÝŒ±ÜŒ°Ü‹°Ü»Þ«ÄℬՈ®Ö‹¯×Š¯Øˆ®×†¬×ƒªÖ©Ö~§Õ|¦Ôz¤Õv¡Ôt ÓqžÒn›ÒkšÑk™Ñj™Ñi™Ñi˜Òh˜Òh—Ò€§Ô‡­Ö†¬Ö…¬Ö„«Ö‚ªÖ€¨Õ§ÕqžÑm›ÑnœÑu¡Ôt ÔsŸÔrŸÔqžÔpÔoÔn›Ô~¦Ó‚¥Ï…©Ñ…§Ñ„§Ð‚¦Ï¥Ï¤Ï~£Î•µÚv¡Ól›ÑrŸÓ°ØuœËs›Êr›ÊqšËp™Éo—Êm—Él–Èg“Ä„§Ñu¡ÓlšÑqžÓ~¥Ñ‚§ÑpžÓ}¤Ð¦ÑsŸÓoÓ{£Ð¥ÏržÔoœÓy¡Ï}¥ÏqÓi˜Ñn›Óx Ï|¤ÎpÓm›ÓvŸÏz£ÎoœÔkšÔtžÍv̆«Ö©Õq›Ê?-N8tRNS¨ö«¼¿ÀÀ£Íò÷ݳãäåæçèxà˜w¹ºÀ »Â ¼Ã¾Ä ¡ì¦¤Çé pHYs%%IR$ðÂIDAT8Ëc`Ã023QŠY,,­¬¬mX‰Slckggï@ŠbRLvtb#Z±³‹+‘ŠÝlÝ]<؉TlïN¼bOG//o¼Š98¡€Ë×ÅËÏ?€› x±(æ ƒàP¿0ÿðˆÈ¨è˜Ø¸¸x>,ŠùA ))9Ù+,,%%55-=##3+›b;;;gww//?ˆÚŒœÜ¼ü‚Â"lŠ‹KJËÊ+*«ªkjëꛚ[ZÛÚ;:»°)²ïîéí«ê¯ž0qÒäÉSê§N›>cæ¬ÙsæbS, The Ipe extensible drawing editor. True ipe-7.2.13/src/ipe/appui_qt.h0000644000175000017500000001401013561570220015567 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Appui for QT // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef APPUI_QT_H #define APPUI_QT_H #include "appui.h" #include #include #include #include #include #include #include #include #include #include #include #include using namespace ipe; // -------------------------------------------------------------------- class PathView; class LayerBox; class QSignalMapper; // -------------------------------------------------------------------- class AppUi : public QMainWindow, public AppUiBase { Q_OBJECT public: #if QT_VERSION < 0x050000 AppUi(lua_State *L0, int model, Qt::WFlags f=0); #else AppUi(lua_State *L0, int model, Qt::WindowFlags f=nullptr); #endif ~AppUi(); QAction *findAction(const char *name) const; virtual void setLayers(const Page *page, int view) override; virtual void setZoom(double zoom) override; virtual void setActionsEnabled(bool mode) override; virtual void setNumbers(String vno, bool vm, String pno, bool pm) override; virtual void setNotes(String notes) override; virtual WINID windowId() override; virtual void closeWindow() override; virtual bool actionState(const char *name) override; virtual void setActionState(const char *name, bool value) override; virtual void setWindowCaption(bool mod, const char *s) override; virtual void explain(const char *s, int t) override; virtual void showWindow(int width, int height) override; virtual void setBookmarks(int no, const String *s) override; virtual void setToolVisible(int m, bool vis) override; virtual int pageSorter(lua_State *L, Document *doc, int width, int height, int thumbWidth) override; virtual int clipboard(lua_State *L) override; virtual int setClipboard(lua_State *L) override; public slots: void action(String name) override; void qAction(const QString &name); void selectLayerAction(QAction *a); void moveToLayerAction(QAction *a); void textStyleAction(QAction *a); void labelStyleAction(QAction *a); void gridSizeAction(QAction *a); void angleSizeAction(QAction *a); void layerAction(String name, String layer); void toolbarModifiersChanged(); void abortDrawing(); void aboutIpe(); void absoluteButton(int id); void selector(int id, String value); void comboSelector(int id); void bookmarkSelected(QListWidgetItem *item); void aboutToShowSelectLayerMenu(); void aboutToShowMoveToLayerMenu(); void aboutToShowTextStyleMenu(); void aboutToShowLabelStyleMenu(); void aboutToShowGridSizeMenu(); void aboutToShowAngleSizeMenu(); void showPathStylePopup(Vector v); void showLayerBoxPopup(Vector v, String layer); private: void addItem(QMenu *m, const QString &title, const char *name); void addItem(int m, const QString &title, const char *name); void addSnap(const char *name); void addEdit(const char *name); QIcon prefsColorIcon(Color color); QPixmap prefsPixmap(String name); void aboutToShowStyleMenu(Kind kind, MENUHANDLE menu, String current); private: virtual void addRootMenu(int id, const char *name) override; virtual void addItem(int id, const char *title, const char *name) override; virtual void startSubMenu(int id, const char *name, int tag) override; virtual void addSubItem(const char *title, const char *name) override; virtual MENUHANDLE endSubMenu() override; virtual void setMouseIndicator(const char *s) override; virtual void setSnapIndicator(const char *s) override; virtual void addCombo(int sel, String s) override; virtual void resetCombos() override; virtual void addComboColors(AttributeSeq &sym, AttributeSeq &abs) override; virtual void setComboCurrent(int sel, int idx) override; virtual void setCheckMark(String name, Attribute a) override; virtual void setPathView(const AllAttributes &all, Cascade *sheet) override; virtual void setButtonColor(int sel, Color color) override; protected: void closeEvent(QCloseEvent *ev) override; private: PathView *iPathView; QMenu *iMenu[ENumMenu]; QToolButton *iButton[EUiGridSize]; QComboBox *iSelector[EUiView]; QToolButton *iViewNumber; QToolButton *iPageNumber; QCheckBox *iViewMarked; QCheckBox *iPageMarked; QToolBar *iSnapTools; QToolBar *iEditTools; QToolBar *iObjectTools; QDockWidget *iPropertiesTools; QDockWidget *iLayerTools; QDockWidget *iBookmarkTools; QDockWidget *iNotesTools; QActionGroup *iModeActionGroup; QAction *iShiftKey; QAction *iAbortButton; QListWidget *iBookmarks; LayerBox *iLayerList; QTextEdit *iPageNotes; QLabel *iModeIndicator; QLabel *iSnapIndicator; QLabel *iMouse; QLabel *iResolution; QSignalMapper *iActionMap; std::map iActions; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipe/main_common.i0000644000175000017500000000675313561570220016261 0ustar otfriedotfried// -------------------------------------------------------------------- // Common code for all platforms // -------------------------------------------------------------------- #include #include // for version info only #include "ipefonts.h" #include extern int luaopen_ipeui(lua_State *L); extern int luaopen_appui(lua_State *L); // -------------------------------------------------------------------- String ipeIconDirectory() { static String iconDir; if (iconDir.empty()) { const char *p = getenv("IPEICONDIR"); #ifdef IPEBUNDLE String s(p ? p : Platform::ipeDir("icons")); #else String s(p ? p : IPEICONDIR); #endif if (s.right(1) != "/") s += IPESEP; iconDir = s; } return iconDir; } static int traceback (lua_State *L) { if (!lua_isstring(L, 1)) /* 'message' not a string? */ return 1; /* keep it intact */ lua_rawgeti(L, LUA_REGISTRYINDEX, LUA_RIDX_GLOBALS); lua_getfield(L, -1, "debug"); if (!lua_istable(L, -1)) { lua_pop(L, 2); return 1; } lua_getfield(L, -1, "traceback"); if (!lua_isfunction(L, -1)) { lua_pop(L, 3); return 1; } lua_pushvalue(L, 1); // pass error message lua_pushinteger(L, 2); // skip this function and traceback luacall(L, 2, 1); // call debug.traceback return 1; } static void setup_config(lua_State *L, const char *var, const char *env, const char *conf) { const char *p = env ? getenv(env) : nullptr; #ifdef IPEBUNDLE push_string(L, p ? p : Platform::ipeDir(conf)); #else lua_pushstring(L, p ? p : conf); #endif lua_setfield(L, -2, var); } static void setup_common_config(lua_State *L) { push_string(L, Fonts::freetypeVersion()); lua_setfield(L, -2, "freetype_version"); lua_pushfstring(L, "%s / %s", CAIRO_VERSION_STRING, cairo_version_string()); lua_setfield(L, -2, "cairo_version"); lua_pushliteral(L, ZLIB_VERSION); lua_setfield(L, -2, "zlib_version"); push_string(L, Platform::latexDirectory()); lua_setfield(L, -2, "latexdir"); push_string(L, Platform::latexPath()); lua_setfield(L, -2, "latexpath"); push_string(L, ipeIconDirectory()); lua_setfield(L, -2, "icons"); lua_pushfstring(L, "Ipe %d.%d.%d", IPELIB_VERSION / 10000, (IPELIB_VERSION / 100) % 100, IPELIB_VERSION % 100); lua_setfield(L, -2, "version"); push_string(L, Platform::ipeDrive()); lua_setfield(L, -2, "ipedrive"); } // -------------------------------------------------------------------- /* Replacement for Lua's tonumber function, which is locale-dependent. */ static int ipe_tonumber(lua_State *L) { const char *s = luaL_checklstring(L, 1, nullptr); int iValue; double dValue; int result = Platform::toNumber(s, iValue, dValue); switch (result) { case 2: lua_pushnumber(L, dValue); break; case 1: lua_pushinteger(L, iValue); break; case 0: default: lua_pushnil(L); } return 1; } static lua_State *setup_lua() { lua_State *L = luaL_newstate(); luaL_openlibs(L); luaopen_ipe(L); luaopen_ipeui(L); luaopen_appui(L); return L; } static bool lua_run_ipe(lua_State *L, lua_CFunction fn) { lua_pushcfunction(L, fn); lua_setglobal(L, "mainloop"); // run Ipe lua_pushcfunction(L, traceback); assert(luaL_loadstring(L, "require \"main\"") == 0); if (lua_pcallk(L, 0, 0, -2, 0, nullptr)) { const char *errmsg = lua_tolstring(L, -1, nullptr); fprintf(stderr, "%s\n", errmsg); return false; } return true; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/main_qt.cpp0000644000175000017500000000723513561570220015743 0ustar otfriedotfried// -------------------------------------------------------------------- // Main function for Qt // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebase.h" #include "ipelua.h" #include #include #include "appui_qt.h" #include #include #include using namespace ipe; using namespace ipelua; #include "main_common.i" // -------------------------------------------------------------------- static void setup_globals(lua_State *L, int width, int height) { lua_getglobal(L, "package"); const char *luapath = getenv("IPELUAPATH"); if (luapath) lua_pushstring(L, luapath); else { #ifdef IPEBUNDLE push_string(L, Platform::ipeDir("lua", "?.lua")); #else lua_pushliteral(L, IPELUADIR "/?.lua"); #endif } lua_setfield(L, -2, "path"); lua_newtable(L); // config table lua_pushliteral(L, "unix"); lua_setfield(L, -2, "platform"); lua_pushliteral(L, "qt"); lua_setfield(L, -2, "toolkit"); #ifdef IPEBUNDLE setup_config(L, "system_styles", nullptr, "styles"); setup_config(L, "system_ipelets", nullptr, "ipelets"); setup_config(L, "docdir", "IPEDOCDIR", "doc"); #else setup_config(L, "system_styles", nullptr, IPESTYLEDIR); setup_config(L, "system_ipelets", nullptr, IPELETDIR); setup_config(L, "docdir", "IPEDOCDIR", IPEDOCDIR); #endif lua_pushfstring(L, "%s / %s", QT_VERSION_STR, qVersion()); lua_setfield(L, -2, "qt_version"); setup_common_config(L); lua_createtable(L, 0, 2); lua_pushinteger(L, width); lua_rawseti(L, -2, 1); lua_pushinteger(L, height); lua_rawseti(L, -2, 2); lua_setfield(L, -2, "screen_geometry"); lua_setglobal(L, "config"); lua_pushcfunction(L, ipe_tonumber); lua_setglobal(L, "tonumber"); } // -------------------------------------------------------------------- int mainloop(lua_State *L) { QApplication::exec(); return 0; } int main(int argc, char *argv[]) { // try to work around bug in Ubuntu, see issue #42. unsetenv("QT_QPA_PLATFORMTHEME"); unsetenv("UBUNTU_MENUPROXY"); Platform::initLib(IPELIB_VERSION); lua_State *L = setup_lua(); QApplication a(argc, argv); a.setQuitOnLastWindowClosed(true); // create table with arguments lua_createtable(L, 0, argc - 1); for (int i = 1; i < argc; ++i) { lua_pushstring(L, argv[i]); lua_rawseti(L, -2, i); } lua_setglobal(L, "argv"); QRect r = a.desktop()->screenGeometry(); setup_globals(L, r.width(), r.height()); lua_run_ipe(L, mainloop); lua_close(L); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/ipe.ico0000644000175000017500000431445613561570220015072 0ustar otfriedotfried  ¨6€€ (Þ (€( @ ÿÿÿÉÿÿÿÿÿÿÿÿýýýöþþþàÿÿÿËýýý·ÿÿÿ¢ÿÿÿŒÿÿÿxüüübûûûJÿÿÿ6bfjC“¼È²fÿÿÿÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ„…‡ÿÿÿÿÿ(((ù üÿ‘޶üüü~ÿÿÿiþþþRÿÿÿ>ÿÿÿþþþßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿËÌÎÿÿÿÿJHHÿø÷÷ÿÿÿÿÿÿÿÿÿÞÞßÿSSUÿKJIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVÿÿÿäää燇‡ÿìììÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿOQSÿÿÿEBBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐÐÒÿQONÿÿÿÿÿÿÿÿÿÿÿÿ$ßßßœœœóÿÿŽŽŽÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìêéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþîÿÿÿ ëëë ÿÿÿñåååÿ===ÿÿ···ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÎñññÿÿÿ÷ÿÿÿÿÿÿÿÿÿOOOÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ($#ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýŸ‹‹‹*èèèþÿÿÿÿîîîÿÿbbbÿõõõÿLLLÿJJJÿÞÞÞÿÿÿÿÿÿÿÿÿLNPÿÿÿjjjÿqqqÿsssÿsssÿqqqÿpppÿsrrÿÿÿÿÿÿÿÿÿÿÿÿÿüüüsÉÿÿÿ ÿÿåååÿÕÕÕÿÿÿ´´´ÿÿÿÿÿÿÿÿÿœ ÿÿÿEEEÿMMMÿQQQÿTTTÿTTTÿOOOÿAAAÿÞÜÛÿÿÿÿÿÿÿÿÿÿÿÿIøÿÿÿÿÿüüüÿÕÕÕÿÿÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÁ¾½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýööö EEE|¤¤¤ÿÜÜÜÿ¼¼¼ÿÿwwwÿ×××ÿÿÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿ‡ˆ‹ÿÿ]ZYÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿè¿¿¿ÿÿÿBÿÿÿÿÿÿÿÿÿÿÿÿ ÿHHHÿÜÜÜÿÿÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ++.ÿÿìëêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÁ5***¹cccÿžžžÿ|||ÿÿ“““ÿÖÖÖÿÿÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöö÷ÿÿ)''ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿyz}ÿíÿÿÿÿÿ+++ÿÿÿÿÿÕÕÕÿÿÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùúÿ557ÿÿ¾½½ÿÿÿÿÿÿÿÿÿÿÿÿÿ””–ÿÿÿ…óÿGGGÿ///ÿÿÅÅÅÿÕÕÕÿÿÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¡¢£ÿÿÿ ÿÿÿÿÁÿÿÿmÿÿÿÿÿÿÿÿÿÿÿÿÿSSSÿÛÛÛÿÿÿµµµÿÿÿÿÿöööÿ‡‡‡ÿ<<<ÿÿÿ333ÿxxxÿòòòÿÚÚÛÿšššÿƒƒƒÿ˜˜˜ÿääãùÿÿÿüüüxÿÿÿÿÿÿÿÿùùùÿÿ[[[ÿÚÚÚÿÿÿ½½½ÿ‚‚‚ÿÿÿÿÿÿÿÿÿaaaÿÿÿÿÿÿÿÿÿÿÿÿÿþþþå¯ÿÿÿÿÿÙÙÙÿÕÕÕÿÿÿÿÿÿÿÿuuuÿÓÓÓÿÿÿÿÿíííÿÿÿÿûûûÿÿÿÿÿýýý¶ÿÿÿÿÿ$$$ÿÿÿÿÿÕÕÕÿÿÿÿ ÿ}}}ÿÙÙÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXXXÿÿÿ222ÿÿÿÿÿûûûŠpppÅ‘‘‘ÿÆÆÆÿ¥¥¥ÿÿ€€€ÿ×××ÿÿÿ¥¥¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒŒŒÿÌÌÌÿYYYÿÿÿÿÿÿÿ_þþþ£ÿÿÿÿÿÿÿÿÿÿÿÿ ÿHHHÿÜÜÜÿÿÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõõõÿqqqÿÿÿÿÿÿÿÿÿÿÿÿùùù2$fffÖ}}}ÿ³³³ÿ‘‘‘ÿÿˆˆˆÿ×××ÿÿÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ„„„ÿîîîÿÿÿÿÿÿÿÿÿÞÞÞÿÿÿ444'ÿÿÿÿÿ)))ÿÿÿÿÿÖÖÖÿÿÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿkkkÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ•••ÿÿPžÿÿ...ÿÿÿÑÑÑÿÕÕÕÿÿÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿgggÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý_ÿÿÿÒÿÿÿÿÿÿÿÿÿÿÿÿÿXXXÿñññÿÿÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿkkkÿíííÿòòòÿÿÿÿÿÿÿÿÿkkkÿÿIÿÿÿÙÿÿÿÿÿÿÿÿÿÿÿÿÿVVVÿÿÿÿÿ ÿÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿyyyÿÿÆÆÆÿÿÿÿÿ¿¿¿ÿÿÿÿÿÿÿÿÿáÿÿÿÿØØØÿ ÿÿÏÏÏÿÿÿÿÿaaaÿÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëëëÿÿÿÿõõõÿÿÿÙþþþÿÿÿê÷÷÷ÿ€€€ÿÿ¶¶¶ÿÿÿÿÿÿÿÿÿæææÿÿƒƒƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÅÅÅÿÿ***ÿ===ÿÿÿFÿÿÿ ÿÿÿòýýýÿ×××ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿIIIÿ§§§ÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿøøøÿ///ÿÿÿJJJíïïïÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿyyyÿÿÿÿÿ@@@ÿŸŸŸÿ÷÷÷ÿÓÓÓÿÿÿKKKÿÿÿÿŸÔÔÔüüüYÿÿÿjÿÿÿzÿÿÿ‹ÿÿÿ¡ýýý¶ÿÿÿÈÿÿÿÚþþþíÿÿÿÿºººÿÿÿÿÿÿÿÿÿšššÿÿÿÿÿÿÿÿrþþþ777R¿Æ555º{{{ýýý€ýýýÿÿÿ ÿÿÿ2øáÿø?øøøøøøààøøðààøøààðððààðððð?ð?ð?þÿÿ€(€  %% ÿÿÿ üüüyÿÿÿ¦üüü~üüücûûûLúúú7ÿÿÿ%óóóëÄ“繋 [”Áãüÿÿÿÿÿÿã´u (ðððýýý´ÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿõË¢ÿøÞÄÿÿÿÿÿýýýïýýý×ÿÿÿ«ýýý‘ÿÿÿoüüüXþþþ?ð¶{[÷çØ!ðððÿÿÿÿÿÿ uÐÿÿÿÿÿÿþþÿÿþÿÿÿÿÿÑ p ÿÿÿÿÿÿºÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÇ›ÿøáËýÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿð®nÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþàÿÿÿÀýýý›ùáÍ‹ð¸ŽÿÿÿKúúú6ÿÿÿ%ÿÿÿééé ÿÿÿÿÿÿÔªU¿?Šöÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿ÷ Š ÿÿÿþþþÅþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÂ’ÿúçÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿð®nÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúãÍÿôÇ›ÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿñòÀ‘Þ÷â˳ÿÿÿŒÿÿÿlÿÿÿWúúú>ùùù.öööðððâââ ì£dÿÿÿ. Uæÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ÷|þþþÿÿÿÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó½ŠÿûìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿñ´yÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÜÀÿöΨÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿó¼‡ÿüîáÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿü÷òÿñ²vÿÿÿÿÿÿÿÿÙéêí¾bgmÈÿÿþÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿà S ÷÷÷!ýýýÙþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¹ÿüñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿò¹ƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õ´ÿ÷Õ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñµzÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâýò»…ÿÿÿÿÿóôõÿ‚†‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñéåæêñúÿÿÿÿÿÿ ©'ùâ×-ýú÷åÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ´yÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûêÚÿó¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöΨÿøÜÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿð®nÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúæÓÿôÄ•ÿüüýÿ ¤ªÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ#""ÿXVUÿ–”“ÿ½½¼ÿÏÏÏÿÇÇÇÿ­¯¯û€‚æKA8êð ðùÿÿÿÿê#f¤wD-å²™ ÿÿÿÿÿÿÿÿÿï®obï­n÷ð®oÿñµzÿò»†ÿô‘ÿõÈÿöÏ©ÿ÷Õ´ÿð®nÿùÞÅÿúèÖÿüïâÿýõîÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿúåÐÿôÅ—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÈœÿùâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿñ²uÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùÝÃÿöÍ¥ÿÓÖÚÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ*%"ÿ|_EÿçäãÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ ÿù߯ÿÂÄÅÿvxzÿ223ÿÿÿÿÿÿbD)ÿÙÔÏéÿÿÿ¾þþþ£ÿÿÿ…ÿÿÿmÿÿÿVûûûBùùù1õÒ¯3í±t;ëëë ÿÿÿ ÚÚÚÔÔÔÿÿÿùùù2ÿÿÿûþûùÿýõíÿüïâÿúèÖÿùáÊÿøÛ¿ÿ÷Ô²ÿð¬kÿõÈÿóÁ‘ÿò»…ÿñµzÿð®oÿð®oÿñµzÿò»†ÿò¹ƒÿò·}ÿöÏ©ÿ÷Õ´ÿøÛ¿ÿùâÊÿúèÖÿüïâÿýõîÿþûùÿóÁÿûéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñåÿòºƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õ³ÿíΰÿPV]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿhebÿÜéÿõÊ¡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¿ŒÿûêÚÿÿÿÿÿÿÿÿÿùúüÿ¡£¦ÿHJLÿÿÿÿÿ0,*ÿ¹µ³ÿ÷ööÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿ÷عÿöЬÿÿÿÿÿÿÿÿÿþþþíÿÿÿÞûûû@ÿÿÿþþþ8þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿð°rÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿýõíÿüîáÿõÌ¥ÿôÔÿøÛ¿ÿ÷Õ³ÿöΨÿõÈÿóÁ‘ÿò»…ÿñµzÿð®nÿð¬jÿñ´xÿò»†ÿôÂ’ÿõÈžÿöÏ©ÿ÷Õ´ÿøÛ¿ÿùâÊÿøÙ»ÿó½ŠÿýõîÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõË£ÿ¶©œÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ$! ÿ¡™ÿÿþýÿ÷Ô²ÿ÷Õ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ³vÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ«­°ÿIKMÿÿÿÿ ÿ‹†ƒÿëéèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ ÿ÷ÝÃýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ9þþþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõíÿñµzÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ô±ÿ÷Ö¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ´xÿûíàÿüîáÿúçÕÿùáÊÿøÛ¾ÿ÷Õ³ÿöΨÿõÈÿò¹‚ÿð±sÿñ´yÿð®nÿð¯oÿñµzÿò»†ÿôÂ’ÿõÈžÿöÏ©ÿíµ~ÿ=:8ÿÿÿÿÿÿÿÿÿÿÿÿÿÿ/,+ÿ½¹¶ÿÿÿÿÿÿÿÿÿõÉŸÿùàÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿð¯qÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüþÿ“„vÿ6/*ÿÿÿÿ\XTÿÕÓÑÿÿÿÿÿÿÿÿÿÿÿÿÿó¼‡ÿûíÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöööÿÿÿDÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿòºƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöΧÿøÜÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿð­mÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÚ¼ÿöѬÿÿÿÿÿÿÿÿÿþûøÿýõíÿüîáÿúçÕÿùáÉÿøÛ¾ÿȘkÿÿÿÿÿÿÿÿÿÿÿÿÿÿ-$ÿ½§”ÿûè×ÿüïãÿýõîÿó½‰ÿûìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîàÿò»†ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÍ¥ÿÚŰÿpsvÿÿÿÿ852ÿ¶³°ÿ÷õõÿþþýÿð¯oÿþû÷ÿÿÿÿÿÿÿÿÿþþþÿÿÿÿæðððûûûLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿÕÕÕÿÉÉÉÿÞÐÂÿó¾‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÈÿùâÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿð±sÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÒ®ÿøØºÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿs[Fÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ­ŽoÿõÈœÿóÁÿòº„ÿñ´yÿð¬jÿð¯oÿñµ{ÿò»†ÿôÓÿõÉžÿöÏ©ÿ÷Õ´ÿøÜÀÿöЫÿó¿ÿüïãÿýõîÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÀŽÿûêÚÿÿÿÿÿ­°´ÿ>@Cÿÿÿ"ÿºµ²ÿüòèÿñ¶}ÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿªÿÿÿ ÿÿÿQÿÿÿÿýýýýÿÿÿÿñññÿÿ@@@ÿ222ÿRLEÿgNÿ»»»ÿôôôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÓÿúçÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿò·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõË¢ÿùàÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿ%! ÿÿÿÿÿÿÿÿÿÿÿÿ ÿŽˆ„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿð¯oÿþú÷ÿýôìÿûîàÿúçÔÿùáÉÿøÛ¾ÿ÷Ô³ÿöΧÿò¹ÿñ¶}ÿòº„ÿñ´yÿð®nÿð¯pÿñµ{ÿò¼‡ÿôÓÿõÉžÿð°rÿöЬÿøÜÀÿùâËÿ×ʾÿhfeÿÿ ÿ®©¥ÿúäÏÿôÅ–ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿxÿÿÿÿÿÿYþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ$$$ÿeeeÿ­­­ÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó½ˆÿûíÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÝÿó¾‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÓÿúçÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâÞÚÿÿÿÿÿÿÿÿÿÿÿÿÿXSPÿïìêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿò¹‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ ÿù߯ÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿýôìÿûîàÿúçÔÿøÜÀÿð°rÿ÷Ô³ÿöΧÿõÇœÿóÁÿé´‚ÿ‰iKÿ[:ÿà¢eÿð±sÿñ²vÿôÓÿõÉžÿõΩþ÷Õ´ÿõΪiÌ™füüüaÿÿÿÿÿÿÿÿÿÿÿÿ;;;ÿÿÿÿÿÿÿÿÿhhhÿÈÈÈÿÿÿÿÿÿÿÿÿÿÿÿÿò·ÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúåÑÿôÅ—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò»†ÿüïâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯ª¨ÿÿÿÿÿÿÿÿÿÿÿÿ"ÿ¸²­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúåÒÿôÄ•ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¾‹ÿûëÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÝÿó¾Šÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿöö÷ÿþû÷ÿôÄ•ÿ÷Ö·ÿúçÔÿùáÉÿ÷Ú½ÿ÷Ô³ÿò¾ŠSÿÿÿÿÿÿiþþþÿÿÿÿÿÿÿÿÿ777ÿÿÿÿÿÿÿÿÿÿ444ÿœœœÿÿÿÿÿÿÿÿÿñ²uÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùßÅÿõË£ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ´xÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‚}xÿÿÿÿÿÿÿÿÿÿÿÿc]ZÿÿýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÛ¾ÿöΨÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ³vÿý÷ðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿù߯ÿõÊ¡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòº„ÿüïâÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿõõõÚ¶múêÛ{ý÷òÿþþýÿÿÿÿÿ|||ÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð­lÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøØ¹ÿ÷Ò¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð­mÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿa\Yÿÿÿÿÿÿÿÿÿÿÿÿ­¦¢ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöЪÿøÚ¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿð°qÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÒ®ÿøØ¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿð®oÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÈÿÿÿè¦nï³z©ñ²vÿð¬kÿñ±sÿÞ¨uÿv\Cÿ"ÿÿÿÿÿÿÿÿÿÿ ÿ}{yÿð±sÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÑ­ÿøÙ»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿñ³wÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿKFBÿÿÿÿÿÿÿÿÿÿÿA=;ÿñëæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÅ—ÿúäÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîàÿò¼‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÅ–ÿúåÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿò¸€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ•ÿÿÿÿÿÿÿÿÿƒþþþÿÿÿÿÿýøóÿüòèÿìÞÐÿƵ¦ÿž}ÿTA/ÿÿÿÿÿÿÿÿÿ ÿ“kCÿôÄ•ÿõÊ ÿöЬÿ÷Ö·ÿøÝÂÿúäÏÿûêÚÿüðåÿôÇšÿùàÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðäÿòº„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ<;9ÿÿÿÿÿÿÿÿÿÿÿhb^ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòº„ÿüïâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùâËÿõÇ›ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¸€ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùãÌÿôÆ™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüühÿÿÿÚÚÚÿÿÿŒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛ²Šÿµ¤”ÿPPPÿÿÿÿÿÿÿÿ#ÿÙȶÿùàÇÿøÙ¼ÿ÷Ó±ÿõÌ¥ÿôÆ™ÿóÀŽÿò¹ƒÿð®oÿð¬jÿð°qÿñ¶}ÿó½‰ÿôÔÿõÉŸÿöЪÿ÷Ö¶ÿöЪÿòº„ÿûéÙÿüðäÿýöïÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ986ÿÿÿÿÿÿÿÿÿÿ ÿ‡‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð°qÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ö¶ÿ÷Ó±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿð®oÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õ³ÿ÷Ô³ÿÿÿÿÿÿÿÿÿýýýýþþþÿÿÿÿDÿÿÿ ÿÿÿ•ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿô‘ÿúèÖÿåååÿ‘‘‘ÿÿÿÿÿÿÿÿcccÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó½ˆÿûíßÿþúöÿüóéÿûíÞÿúæÓÿùàÈÿøÚ¼ÿ÷Ô±ÿóÀÿñ¶|ÿóÀŽÿòºƒÿñ´xÿð­mÿð¯qÿñ¶|ÿó¼ˆÿôÔÿ<6/ÿÿÿÿÿÿÿÿÿÿ ÿ£œ—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿñ²uÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ ÿù߯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñæÿò¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÆ™ÿùâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ*ççç ÿÿÿžÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó½‰ÿûíÞÿÿÿÿÿùùùÿ©©©ÿÿÿÿÿÿÿÿáááÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ¶}ÿýôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÙ»ÿöÑ­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿýôëÿûíßÿúåÒÿK=0ÿÿÿÿÿÿÿÿÿÿ ÿ¤{TÿôÂ’ÿõÉžÿöÏ©ÿ÷Õ´ÿøÛ¿ÿùâÊÿøÜÀÿò¹ƒÿýõîÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¾ŠÿûëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúãÎÿôÆ™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¸ÿüñçÿÿÿÿÿÿÿÿÿþþþÿÿÿÿèÿÿÿþþþÿÿÿ¨þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¹ÿüñçÿÿÿÿÿÿÿÿÿýýýÿ………ÿÿÿÿÿÿ ÿ–––ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð¯qÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÑ­ÿøÙ»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿ_N@ÿÿÿÿÿÿÿÿÿÿÿ«ÿúçÔÿùáÉÿøÛ¾ÿ÷Õ³ÿöΨÿõÈœÿò¹ÿð±sÿñµzÿð®oÿð®oÿñµzÿò»†ÿô‘ÿõÈÿöΨÿð°rÿ÷ÕµÿùáÊÿúçÕÿüîáÿýõíÿþûøÿÿÿÿÿÿÿÿÿ÷Ö·ÿ÷Ó°ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿð®oÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ²þþþÿÿÿÿÿÿ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ´yÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿõõõÿÿÿÿÿÿÿ^^^ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð®nÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ ÿùàÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíßÿzgVÿÿÿÿÿÿÿÿÿÿÿ¬¥žÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷×·ÿ÷Ó°ÿÿÿÿÿÿÿÿÿþûøÿýõíÿüïâÿúèÖÿùâÊÿ÷×·ÿð¯pÿöÏ©ÿõÈžÿôÂ’ÿò»†ÿñµzÿð¯oÿð®nÿñ´yÿñ±sÿò¸€ÿõÇœÿöΧÿ÷Ô³ÿøÚ¾ÿùáÉÿúçÔÿûíàÿúæÓÿòº„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýý…ÔÔÔÿÿÿÿÿÿ¾þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð¯pÿþû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿjjjÿÿÿÿÿÿ===ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿñµzÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÂ’ÿûè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúãÎÿ›†qÿÿÿÿÿÿÿÿÿÿÿ§ž™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÌ£ÿùÞÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíàÿò¼‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿýõîÿò¹‚ÿøÜÁÿùâËÿøÜÀÿ÷ÕµÿöÏ©ÿõÉžÿôÓÿó¼‡ÿñ²uÿð¬kÿð®nÿñ´yÿñ¹ƒþóÀÿñ¼Š†å™f ôôôþþþÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿð­lÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿƒƒƒÿÿÿÿÿÿ444ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüîáÿò»†ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòº„ÿüðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÛ¾ÿÀ«—ÿÿÿÿÿÿÿÿÿÿÿ•މÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÁÿûè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùáÊÿõÈœÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿð°qÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÒ®ÿ÷×·ÿþüúÿýöïÿûîãýûéÙÿõÓ²SþþþÿÿÿÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿð±sÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿBBBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúèÖÿôÂ’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ³wÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ò¯ÿìÒ·ÿÿÿÿÿÿÿÿÿÿ ÿ‚{vÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò·}ÿüóéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Öµÿ÷Ó±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿñ´xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÄ–ÿúäÐÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿøøø&ñĘ9øàÊåûéÙÿüðäÿýöïÿþüúÿÿÿÿÿÿÿÿÿýôìÿñµ{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíííÿ ÿÿÿÿÿÿhhhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëëëÿ†ylÿK>0ÿQQQÿRRRÿRRRÿRRRÿPPPÿbbbÿÌÌÌÿþýüÿð­mÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÉŸÿøàÉÿ(/8ÿÿÿÿÿÿÿÿÿÿ1/-ÿ‰ˆˆÿ———ÿ¨§§ÿ¶µµÿÀÀÀÿÃÂÁÿº‡UÿÇÆÅÿÈÈÈÿÉÉÉÿÉÉÉÿÉÉÉÿÉÉÉÿÉÉÉÿÉÉÉÿÀ|ÿïœÿÈÈÈÿÈÈÈÿÇÇÇÿÆÆÆÿÅÅÅÿÃÃÃÿÁÁÁÿ¹«žÿ­‰gÿ¸··ÿùõôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ¶|ÿüóêÿÿÿÿÿÿÿÿÿþþþÿþþþÏÿÿÿð»†HóŘòóÀÿòº„ÿñ´yÿð®nÿð¯pÿñµ{ÿò¹ÿð¯qÿõÈÿöΨÿ÷Õ³ÿøÛ¾ÿNF?ÿÿÿÿÿÿÿ¦¦¦ÿÿÿÿÿÿÿÿÿÿÿÿÿõõõÿ€€€ÿÿÿÿÿÿÿÿÿ///ÿÐÊÅÿñ´xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÀŽÿúéÙÿbhrÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿe\Xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿð¯pÿþþýÿÿÿÿÿÿÿÿÿþþþÿýýý ÿÿÿ 6+++†mmmü```ÿ___ÿkkkÿ„„„ÿ¨¦£ÿÚÒËÿøÝÄÿò¹‚ÿùáÊÿøÛ¿ÿ÷Õ´ÿdTDÿÿÿÿÿÿÿÿë³ÿóÀŽÿôÆ™ÿõÌ¥ÿÙº›ÿND;ÿÿÿÿÿÿÿÿÿÿº±§ÿò»†ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò·ÿüóéÿ¤«´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ#"!ÿÞØÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíÞÿò¼‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿxÿÿÿwæÿÿÿÿÿÿÿÿÿÿVD4ÿ²²²ÿáááÿGGGÿÿÿÿÿÿÿÿ~zwÿüðäÿûêÙÿúãÎÿøÝÂÿØ» ÿMA5ÿÿÿÿÿÿÿÿÿÿ³‹eÿñ´yÿöѬÿ÷×·ÿùÝÃÿúäÏÿûêÚÿüðåÿýöðÿþüúÿð¯oÿþüùÿêîòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ…~xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùßÅÿõÊ ÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿüüüU%¶ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ...ÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿPPPÿÿÿÿÿÿÿÿÿÿµ™}ÿó¿ÿøÙ»ÿ÷Ó°ÿõ̤ÿôÆ™ÿóÀŽÿò¹ƒÿñ³xÿð­lÿð¬jÿñ¶|ÿ﹆ÿ:42ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ842ÿÿüøÿÿÿÿÿÿÿÿÿÿÿÿÿöѬÿøØºÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúú8ÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿËËËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿPPPÿÿÿÿÿÿÿÿÿÿ¶Ÿˆÿ÷Ò¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðäÿòºƒÿýóëÿùëÝÿ‘Œ‰ÿÿÿÿÿÿÿÿÿÿ ÿD3#ÿ@1#ÿA3&ÿC7+ÿD3$ÿE8*ÿG?6ÿLD=ÿSLFÿWRMÿ[XTÿ_]\ÿcccÿ`WNÿ_M<ÿcccÿbbbÿbbbÿ___ÿXXXÿQQQÿJJJÿFEDÿ>-ÿ<<<ÿ555ÿ***ÿA>>ÿ»·ÿÿÿÿÿÿÿÿÿÿÿÿÿô‘ÿúçÔÿÿÿÿÿÿÿÿÿþþþÿþþþé÷÷÷#8Ýÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¤}WÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿPPPÿÿÿÿÿÿÿÿÿÿµ™~ÿøÚ¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúçÔÿôÔÿÿÿÿÿÿÿÿÿçëïÿ ÿÿÿÿÿÿÿÿÿfa[ÿýóëÿüïãÿûéØÿùâÌÿñµzÿöΧÿöЪÿõÊ ÿôÄ•ÿó½Šÿò·ÿð°rÿð¬kÿð¯oÿñ²vÿó¿ŒÿôÅ—ÿõË¢ÿöÑ­ÿøØ¹ÿùÞÅÿúäÐÿùÞÄÿò¹ÿý÷ñÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ´xÿýõîÿÿÿÿÿÿÿÿÿþþþÿÿÿÿºÿÿÿCóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿohaÿó¾‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿPPPÿÿÿÿÿÿÿÿÿÿ´”tÿùáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùÞÅÿõ̤ÿÿÿÿÿÿÿÿÿúúúÿ[bjÿÿÿÿÿÿÿÿÿGDBÿðêæÿÿÿÿÿÿÿÿÿÿÿÿÿñ²vÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿôÇ›ÿ÷×·ÿûëÛÿúäÐÿùÞÅÿøØºÿöÑ­ÿõË£ÿôŘÿò¸€ÿð°rÿñ³vÿð¬kÿð°rÿò·~ÿó½ŠÿôÄ•ÿõÉŸÿöÏ©ÿð¬kÿøÜÁÿùâÌÿûéØÿüïãÿûñé—âââ 5Ùÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ§†fÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿOOOÿÿÿÿÿÿÿÿÿÿ³ŽjÿûéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õ´ÿ÷Õ´ÿÿÿÿÿÿÿÿÿþþþÿÃÉÏÿÿÿÿÿÿÿÿÿ/+)ÿÆÀ¼ÿÿÿÿÿÿÿÿÿþú÷ÿð¯pÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó½ŠÿûìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ô±ÿ÷ÖµÿÿÿÿÿÿÿÿÿþùõÿüòéÿûìÞÿúæÓÿùàÈÿöͦÿñ¶}ÿöͦÿôÇ›ÿòÀŽþòº„ÿð±s¡ä¡]‹ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÇÇÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿOMKÿÿÿÿÿÿÿÿÿÿ²ˆ`ÿüñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõ̤ÿùÞÄÿÿÿÿÿÿÿÿÿÿÿÿÿ÷÷÷ÿ>FNÿÿÿÿÿÿÿÿ ÿ™“ÿÿÿÿÿÿÿÿÿüðäÿòºƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ±tÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÇšÿúãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÜÁÿöÍ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿO%°øÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ***ÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿOKHÿÿÿÿÿÿÿÿÿÿ±ƒVÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÔÿúçÔÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿ¶ºÃÿÿÿÿÿÿÿÿÿhb_ÿÿÿÿÿÿÿÿÿúåÐÿôÅ–ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿð°rÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¹ƒÿüðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöΧÿøÛ¾ÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿ5Îåùÿÿÿÿ ÿÿ!ÿ,"ÿXMCÿ¢š’ÿËÅÀÿRRQÿ ÿÿÿÿÿÿÿ{{{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿNIDÿÿÿÿÿÿÿÿÿÿ°€Qÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòº„ÿüðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôõõÿDLSÿÿÿÿÿÿÿÿ=:7ÿÙÔÐÿÿÿÿÿøÚ½ÿöЪÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíÞÿó¼ˆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿð®oÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÀŽÿûéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓööö JXUQµnhcÿ`YSÿ_VNÿi^Rÿ{k\ÿ˜‚kÿ¾~ÿê¬pÿò»†ÿòºƒÿñ´xÿð®nÿiL0ÿÿÿÿÿÿÿÿíÔ»ÿúäÐÿûêÚÿüñåÿÞØÒÿNF?ÿÿÿÿÿÿÿÿÿÿ±…Yÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ²uÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÃÇÍÿÿÿÿÿÿÿÿÿž˜•ÿÿÿÿÿöϪÿøÚ½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùáÊÿõÈœÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿò·}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ²vÿý÷ðÿÿÿÿÿÿÿÿÿÿÿÿÿýýý«ÿÿÿ¿¿¿ÿÿÿxÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¸€ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿ\YVÿÿÿÿÿÿ ÿ›€fÿôŘÿó¿ÿò¹‚ÿÓiÿK6"ÿÿÿÿÿÿÿÿÿÿ²†\ÿûëÛÿüñæÿý÷ñÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿð¯oÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöö÷ÿkqzÿÿÿÿÿÿÿÿd^[ÿüùöÿôÅ–ÿúåÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õ´ÿ÷Ô²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúæÒÿôÄ•ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿñ²uÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿÿýýýˆÌÌÌÌÌÌýýý‚þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ³xÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìììÿÿÿÿÿÿÿeeeÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿMC9ÿÿÿÿÿÿÿÿÿÿ±ƒVÿó¿Œÿò¹ÿñ³vÿð­lÿð°qÿñ¶|ÿò¼‡ÿó¿ÿð¯pÿöΧÿ÷Ô²ÿøÚ¼ÿùàÇÿúåÒÿûìÝÿüñçÿÛÙØÿ"ÿÿÿÿÿÿÿ'#!ÿ¾¸´ÿòºƒÿüðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÉŸÿùàÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÙ»ÿöѬÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûé×ÿóÀŽÿÿÿÿÿÿÿÿÿÿÿÿýþþþÿÿÿÿhÚÚÚýýýŒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð¯oÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ^^^ÿÿÿÿÿÿAAAÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿM@5ÿÿÿÿÿÿÿÿÿÿ´•xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿýôëÿûîàÿøØºÿò¹‚ÿøÜÀÿ÷ÖµÿöЫÿõÊ ÿôÄ•ÿó¾‹ÿò¸€ÿî°tÿžvOÿÿÿÿÿÿÿÿp^Nÿî«lÿùãÌÿûìÝÿüòèÿýøóÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿó½‰ÿûìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõË£ÿùÞÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÚ½ÿöÏ©ÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿKâââ ÿÿÿ˜ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿð­lÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ„„„ÿÿÿÿÿÿ444ÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿL?1ÿÿÿÿÿÿÿÿÿÿ¶›‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùáÉÿõÉŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿè±|ÿmquÿÿÿÿÿÿÿ$ÿ²OÿôÄ•ÿó½Šÿò¸ÿñ²uÿð¬jÿñ±sÿò·ÿó½‰ÿð®nÿôƘÿöÏ©ÿ÷Õ´ÿøÛ¾ÿùáÉÿúçÔÿûíÞÿüòéÿó½‰ÿûëÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõ̤ÿøÝÂÿÿÿÿÿÿÿÿÿÿÿÿÿýýýëùùù/ÿÿÿ þþþ£þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿñ±sÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿdddÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿL<-ÿÿÿÿÿÿÿÿÿÿ¶ ŒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøØºÿöÒ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúèÖÿóÁ‘ÿãåçÿDHMÿÿÿÿÿÿÿaI1ÿñîìÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýøóÿüòéÿúçÔÿð°rÿùáÉÿøÛ¾ÿ÷Õ´ÿöÏ©ÿõÉžÿôÔÿó½‰ÿò·~ÿð¬jÿð¬jÿñ²uÿò¸€ÿó¾ŠÿôÄ•ÿõÉŸÿöϪÿ÷Õµÿò·~ÿ÷Ô²ÿúçÔÿûíàÿüóêÿüøóÅôôôìììÿÿÿ­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýôëÿñ¶|ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïïïÿÿÿÿÿÿÿaaaÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿK:*ÿÿÿÿÿÿÿÿÿÿ·¦–ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöϪÿøÛ¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùÞÃÿõÌ£ÿÿÿÿÿÉÌÐÿ,/3ÿÿÿÿÿÿ ÿ˜”ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíÞÿó½ˆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿñ²uÿþþýÿýøòÿüòèÿûìÝÿúæÓÿùàÈÿøÚ½ÿ÷Ô²ÿð¬kÿõÈœÿôÂ’ÿ泃ÿ¼dÿ¤vKוi=Kÿÿÿÿÿÿÿ·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüïãÿòº„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿrrrÿÿÿÿÿÿÿ›››ÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿK8&ÿÿÿÿÿÿÿÿÿÿ¹¬ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÇšÿúãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ô²ÿ÷Õµÿÿÿÿÿÿÿÿÿ²¶»ÿ!&ÿÿÿÿÿÿ-)'ÿÇ¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùáÉÿõÈžÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûêÚÿó¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýôìÿñ´yÿÿÿÿÿÿÿÿÿ³¶ºþ137ÿì² 5...MÚŠŠŠÿÿ€€€ÿˆˆˆÿ˜˜˜ÿ®®®ÿȼ¯ÿ趆ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‰‰‰ÿÿÿÿÿÿÿÿéééÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿK6"ÿÿÿÿÿÿÿÿÿÿ¹±ªÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¾ŠÿûíÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ ÿù߯ÿÿÿÿÿÿÿÿÿüüýÿ¢¦«ÿÿÿÿÿÿÿGB?ÿÜÚ×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õ´ÿ÷Õ³ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùÝÃÿõ̤ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúæÓÿôÂ’ÿÿÿÿÿçéìÿW[aÿÿÿÿ °$j° à ýÿÿÿÿ ÿÿ3+#ÿL:*ÿumeÿ¯§ŸÿÏÉÃÿmlkÿ ÿÿÿÿÿÿÿnnnÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿßÛØÿK6#ÿÿÿÿÿÿÿÿÿÿ»·´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñµzÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÀŽÿûéÙÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿ ¤ÿÿÿÿÿÿÿVOMÿäàßÿÿÿÿÿÿÿÿÿÿÿÿÿõÉžÿùàÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöЬÿøÙ»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøØºÿöѬÿÿÿÿÿ•™žÿ ÿÿþÿÿ‹: œòÿÿÿÿÿÿÿÿÿÿÿÿ ÿ3&ÿÿÿÿÿÿÿÿ$ÿàÄ©ÿù߯ÿúåÑÿûëÛÿüñæÿÜÐÃÿK9'ÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð®nÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ¶}ÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûüÿ¡¤©ÿ $ÿÿÿÿÿÿRNKÿÝÚØÿÿÿÿÿÿÿÿÿó½‰ÿûìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÄ•ÿúåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ¡ÿùÞÅÿÃÇËÿ%(+ÿÿÿÿþÿõ eU ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ­–€ÿöѬÿõÊ¡ÿôÅ–ÿó¿Œÿò¹ÿÓ›eÿK5!ÿÿÿÿÿÿÿÿÿÿ¸©šÿûìÝÿüòèÿýøòÿþþýÿÿÿÿÿÿÿÿÿýöïÿñ´yÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð®nÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüýÿ®±µÿ(ÿÿÿÿÿÿ<97ÿÀ»¸ÿÿÿÿÿñ±tÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò·}ÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¼ˆÿÔËÂÿ>AFÿÿÿÿÿÿþÿäB2Óÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ›››ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛʹÿL=.ÿÿÿÿÿÿÿÿÿÿ³mÿó¾‹ÿò¸€ÿñ²uÿð¬kÿð°rÿò·~ÿò¹‚ÿð°rÿõÉžÿöÏ©ÿ÷Õ´ÿøÛ¾ÿùáÉÿúæÓÿûíÞÿûëÛÿñ³wÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿ¹Žfÿ@BFÿÿÿÿÿÿ!ÿ}xrÿá¤iÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð®oÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿÈ”dÿBCHÿÿÿÿÿÿÿÿþÿ Ì"-Còÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ_QCÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚíÿL?2ÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿüóéÿøØºÿó¾‹ÿùáÉÿøÛ¿ÿ÷Õ´ÿöÏ©ÿõÉŸÿôÔÿó½‰ÿñ´yÿð­lÿð¬jÿñ²uÿò¸ÿó¾ŠÿôÄ•ÿõÉŸÿ÷Ò¯ÿõË¢ÿò¸ÿÖijÿa][ÿÿÿÿÿÿ ÿ4(ÿ‹ÿðíìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüïãÿòºƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúûüÿ“ÿ)!ÿÿÿÿÿÿÿÿÿþÿÿ if3:áÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¶¶¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙ¾¤ÿMA6ÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÛ¿ÿöÏ©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùâÊÿõÈœÿþþýÿýøóÿüòèÿûìÝÿúæÓÿùàÈÿøØ¹ÿôÔÿòºƒÿõÈÿå·‹ÿtXÿÿÿÿÿÿÿ ÿ*"ÿeTCÿ©‘zÿàÆ¬ÿùâÌÿúèÖÿøØºÿôÄ•ÿþú÷ÿÿÿÿÿÿÿÿÿõö÷ÿÁÂÄÿ~‚ÿ89;ÿÿÿÿÿÿÿÿÿÿþþÿ¯!&˜ÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ###ÿÑÑÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿظ™ÿMC9ÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ó°ÿ÷׸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøØºÿöÑ­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ò¯ÿ÷׸ÿÿÿÿÿÿÿÿÿúúûÿÏÑÔÿX[`ÿÿÿÿÿÿÿÿÿ#ÿ0'ÿK;,ÿ]E-ÿ`F-ÿ\C,ÿK6#ÿ6)ÿ%ÿÿ ÿÿÿÿÿÿÿÿÿÿþÿÿ ©"%-Àÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;;;ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿײÿNE=ÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ ÿùáÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöΧÿøÛ¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÇœÿùâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòòòÿ±´·ÿ46;ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿ'€ëÿÿÿÿÿÿÿÿÿÿUUUÿ¨¨¨ÿÐÐÐÿAAAÿÿÿÿÿÿÿ ÿ‹‹‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÖ­ƒÿNGAÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÁÿûéÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÄ•ÿúåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¼ˆÿûíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿîîïÿž}]ÿ111ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚ U3 mmmtŠŠŠÿiiiþ\\\ÿ[[[ÿfffÿ}}}ÿ   ÿŘnÿåØÌÿòòòÿûûûÿÿÿÿÿòòòÿaaaÿÿÿÿÿÿÿ'''ÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÕ¦zÿNJEÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¸€ÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòº„ÿüïâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ²uÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿí®rÿïëæÿº¼¿ÿY[^ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿë{Ì™fî³z}î¿‘ÿíšÿíǤÿîÍ­ÿïÓ¸ÿòÚÃÿöâÏÿñµzÿúèÖÿýøóÿþþýÿÿÿÿÿÿÿÿÿùùùÿIIIÿÿÿÿÿÿÿ­­­ÿÿÿÿÿÿÿÿÿÿÿÿÿÔ oÿOKIÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð¯pÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð°rÿíèäÿÃÃÃÿ¢¢¢ÿˆˆˆÿvvvÿlllÿiiiÿnlkÿsT6ÿÿ«««ÿÐÐÐÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿñ±tÿÿÿÿÿýýýÿöööÿèèêÿ¢¤§ÿUVYÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ:74ÿrmi® ÷âËcúæÒÿùàÈÿøÚ¾ÿ÷Õ³ÿöÏ©ÿõÉžÿôÔÿð­lÿñ¶}ÿñ²uÿð¬jÿð±sÿò·}ÿó¼ˆÿÚ­‚ÿÿÿÿÿÿÿkd]ÿüñåÿýöðÿþüúÿÒšdÿONLÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿñ±sÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿêêêÿžžžÿZXWÿ ÿ ÿ ÿÿÿÿÿÿÿÿÿÿ ÿÿ111ÿoooÿ···ÿôå×ÿó½ˆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿøøøÿõõõÿÍ¿²ÿ˜y\ÿrrtÿNNOÿ333ÿ ÿÿÿÿ'#ÿC6(ÿonmÿ§¥¤ÿàßÞÿøø÷ýóóóWÿÿÿÿÿÿ]þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð®oÿþûùÿÿÿÿÿÿÿÿÿþùõÿüóêÿûíàÿúçÕÿTLDÿÿÿÿÿÿA3%ÿò¹ÿñ³xÿð­mÿÒ—]ÿK8&ÿÿÿÿÿÿÿÿÿÿ¹°§ÿýõîÿþû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿòºƒÿÿÿÿÿÿÿÿÿøøøÿžžžÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWG8ÿÃÃÃÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÚ¾ÿôͧÿüüüÿûûûÿúúúÿúúúÿùùùÿùùùÿúúúÿòаÿóаÿüüüÿþþþÿÿÿÿÿÿÿÿÞÿÿÿ1ÿÿÿÿÿÿhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿð­lÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€~{ÿÿÿÿÿÿ555ÿÿÿÿÿÿÿÿÿýöïÿÓiÿOLJÿÿÿÿÿÿÿÿÿÿ²‰aÿñµzÿð¯oÿð­mÿñ³xÿò¹‚ÿò¹ƒÿñ²vÿẔÿsaPÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ...ÿ¢¢¢ÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿöͦÿøÜÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÆ™ÿúãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÃÿÿÿÿÿÿÿÿÿoÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿñ²uÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿokfÿÿÿÿÿÿ;;;ÿÿÿÿÿÿÿÿÿüðäÿÔ£sÿPPPÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿþüúÿýöðÿüñåÿëȦÿu]Fÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ&&&ÿ®®®ÿûûûÿÿÿÿÿóÀŽÿûéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¸€ÿüñçÿÿÿÿÿÿÿÿÿþþþÿÿÿÿ¨ÿÿÿ¿¿¿ÿÿÿyþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýóëÿñ¶}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿ" ÿÿÿÿÿÿYYYÿÿÿÿÿÿÿÿÿûé×ÿÕ©~ÿPPPÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ©©©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿC<5ÿÕ±ÿï°uÿûè×ÿýöïÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð¯oÿþýüÿÿÿÿÿþþþÿþþþÿÿÿÿ‘ÿÿÿÿÿÿƒÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿüïâÿò»…ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ’’’ÿÿÿÿÿÿ ÿÿÿÿÿÿÿÿÿÿùâËÿ×®‰ÿPPPÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿêêêÿVVVÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿHHHÿ""!ÿÿÿÿÿÿÿÿÿÿg@ÿì´ÿñ´xÿð®nÿð®oÿñ´yÿòº„ÿóÀŽÿôÂ’ÿð°qÿöÑ­ÿ÷׸ÿøÜÂÿúãÍÿ÷áÉ€ˆˆˆååå•éééÿÔÔÔÿÃÃÃÿÂÂÂÿÎÎÎÿåååÿëÛÌÿ綆ÿøøøÿþþþÿÿÿÿÿÿÿÿÿýýýÿ¼¼¼ÿÿÿÿÿÿÿÿÛÛÛÿÿÿÿÿÿÿÿÿøÛ¿ÿØ´“ÿPPPÿÿÿÿÿÿÿÿÿÿ½½½ÿÿÿÿÿÅÅÅÿ&&&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿEEEÿ™™™ÿêêêÿÿÿÿÿ¸´°ÿ!ÿÿÿÿÿÿÿÿÿÿVVVÿìììÿÿÿÿÿþûùÿýõîÿüðäÿûêÙÿöΨÿó¿ŒÿøØºÿ÷Ó°ÿõÌ¥ÿóŘôð·z0‹ïÿÿÿÿÿÿ ÿ:.#ÿvvvÿ½½½ÿéééÿóóóÿ¥¥¥ÿÿÿÿÿÿÿÿWWWÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õ´ÿØ»žÿPPPÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿ©©©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ ÿHHHÿœœœÿëëëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÞÿ{`Eÿ ÿÿÿÿÿÿÿÿÿÿ,,,ÿÛÛÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ó°ÿ÷Ö¶ÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÕÿÿÿ' v÷ÿÿÿÿÿÿÿÿÿÿÿÿÿCCCÿÿÿÿÿÿÿÿÿ×××ÿÿÿÿÿÿÿÿÿÿÿÿÿöΧÿÙÁ¨ÿPPPÿÿÿÿÿÿÿÿÿÿNNNÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿMMMÿ“Šÿ߯€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùàÈÿõÉŸÿSSSÿÿÿÿÿÿÿÿÿÿÿÿÍÍÍÿÿÿÿÿÿÿÿÿÿÿÿÿôÄ–ÿúåÐÿÿÿÿÿÿÿÿÿÿÿÿÿýýý¾ÿÿÿmÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿŒ‹‰ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÇ›ÿÚdzÿPPPÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ$$$ÿRRRÿ¢¢¢ÿìììÿÿÿÿÿùàÈÿõÉŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ô²ÿ÷Õ´ÿÝÝÝÿ///ÿÿÿÿÿÿÿÿÿÿÿÿËËËÿÿÿÿÿÿÿÿÿñ¶|ÿüóêÿÿÿÿÿÿÿÿýþþþÿýýý¦ÿÿÿ-Êÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿaH0ÿð®nÿð®oÿñ´yÿòº„ÿóÀŽÿñ²uÿÖ«‚ÿMA6ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ(ÿXXXÿ¦¦¦ÿíííÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õµÿ÷Ô²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÈžÿùáÉÿÿÿÿÿ©©©ÿÿÿÿÿÿÿÿÿÿÿÿÿÓÓÓÿþûøÿð¯pÿþþýÿÿÿÿÿÿÿÿÿþþþÿýýýBñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿDDDÿÿÿÿÿÿÿÿÿþûùÿýõîÿüðäÿûêÙÿñµ{ÿØ»žÿMC:ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ000ÿ___ÿ¤“ƒÿ录ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ¡ÿùßÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¼ˆÿûíÞÿÿÿÿÿÿÿÿÿuuuÿ ÿÿÿÿÿÿÿÿÿÿÿ///ÿàÓÇÿò¼‡ÿÿÿÿÿÿÿÿÿþþþÿÿÿÿûÿÿÿg=çÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>>ÿ×××ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ³wÿÞØÒÿPPPÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ2&ÿ`H1ÿ¡vLÿâ£fÿñ³wÿñ²uÿñµ{ÿôÅ–ÿõÊ¡ÿöЬÿ÷Ö¶ÿøÜÁÿùâËÿúèÖÿó¼‡ÿùáÊÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð°rÿþùõÿÿÿÿÿÿÿÿÿàààÿÿÿÿÿÿÿÿÿÿÿÿÿOF>ÿîÄœÿÿÿÿÿÿÿÿÿþþþÿÿÿÿæÿÿÿ<©ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ444ÿåååÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿð­lÿßÞÝÿPPPÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ91(ÿnnnÿ°°°ÿóóóÿÿÿÿÿÿÿÿÿþýûÿý÷ðÿôÇ›ÿöÑ­ÿúåÑÿù߯ÿøÙ¼ÿ÷Ô±ÿöΧÿõÈœÿô‘ÿð¬kÿñµ{ÿð°rÿð¬kÿñ²vÿò¸€ÿó¾‹ÿôÄ•ÿõÈžÿð­lÿ÷ÕµÿøÛ¿ÿäιÿe^Vÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€p`ÿÿÿÿÿÿÿÿÿþþþÿýýýÏÿÿÿBØÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿÿÿÿÿÿÿYYYÿþþþÿÿÿÿÿÿÿÿÿýùôÿð±sÿàààÿPPPÿÿÿÿÿÿÿÿÿÿÿÿ$$$ÿCCCÿtttÿ¬’xÿîѵÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÂ’ÿúçÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð®nÿþþýÿÿÿÿÿþýüÿý÷òÿüñçÿûìÝÿúæÒÿ÷Ó°ÿò·}ÿ÷Ô³ÿ俜ÿ\K;ÿÿÿ_H1ÿ ÿÿÿÿÿÿÿÿÿÿÿÿ¿´©ÿûñçýýøóÿüüúºÿÿÿ @¯åÿÿÿÿÿÿÿÿÿÿ<<<ÿfffÿ………ÿ555ÿÿÿÿÿÿÿÿ¨¨¨ÿÿÿÿÿÿÿÿÿüòèÿò¸ÿàààÿPPPÿÿÿÿÿÿÿÿÿÿ<<<ÿ}}}ÿ···ÿöööÿÿÿÿÿõÇ›ÿúãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¸€ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿò¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùàÇÿõÉŸÿøøøÿnnnÿÿÿªªªÿÿÿÿÿgggÿÿÿÿÿÿÿÿÿÿÿÿB3%ÿé°zþñ±tÿî«iÏâªU 777jxxxÿYYYÿKKKÿDDDÿDDDÿIIIÿTTTÿaK6ÿ‚{tÿ¬¬¬ÿÝÝÝÿÿÿÿÿÿÿÿÿÎÎÎÿJJJÿÿÿÿÿÿÿ555ÿþþþÿÿÿÿÿûëÜÿó¾‹ÿàààÿPPPÿÿÿÿÿÿÿÿÿÿ»»»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¾‹ÿûìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿð®oÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúçÕÿôÂ’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ô²ÿ÷ÕµÿŽŽŽÿÿÿ¥¥¥ÿÿÿÿÿÿÿÿÿïïïÿ5)ÿÿÿÿÿÿÿÿÿÿÿÿ”””ÿÿÿÿÿýýý‰øøø*þþþÿÿÿÿÿêêêÿàààÿàààÿçççÿ÷÷÷ÿò·ÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâââÿ754ÿÿÿÿÿÿÿ½½½ÿÿÿÿÿúäÐÿôÅ—ÿàààÿPPPÿÿÿÿÿÿÿÿÿÿ»»»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñµ{ÿýõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿñ²uÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÜÁÿöͦÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÈœÿµ¤“ÿÿÿÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿºˆXÿÿÿÿÿÿÿÿÿÿÿÿ888ÿèèèòÿÿÿXî«hkð°qÿñµ{ÿò»…ÿóÀÿôÆ™ÿõË£ÿöÑ­ÿð¯qÿ÷׸ÿùâÊÿúçÔÿûíÞÿüòèÿýøòÿþýüÿÄ»±ÿÿÿÿÿÿ ÿvvvÿÿÿÿÿùÞÄÿõÌ£ÿàààÿPPPÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð®nÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíàÿó¼‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÒ®ÿøØºÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿß­|ÿC@<ÿÿcccÿóóóÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿñ³wÿ’’’ÿÿÿÿÿÿÿÿÿÿÿÿíÿÿÿ/ÿÿÿ3þúöÿûòêýüïâÿûéÙÿúäÏÿùÞÅÿøÙ»ÿð¬kÿöÍ¥ÿõÈÿôÓÿó½‰ÿò¸ÿñ²uÿð¬kÿð¯oÿ@.ÿÿÿÿÿÿG>5ÿøÜÁÿõÈÿõÇ›ÿÜÐÃÿOKIÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ðÿñ³xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúãÎÿôÆ™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÇ›ÿúãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ|[;ÿÿ(((ÿÕÕÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûéÙÿóÀŽÿþþþÿ]]]ÿÿÿÿÿÿÿÿÿÿÿ555ò ÿÿÿ;ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿð­mÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùáÊÿzaIÿÿÿÿÿÿ4,%ÿöͦÿò¸€ÿò¸€ÿÕ¦wÿK9'ÿÿÿÿÿÿÿÿÿÿ´œ…ÿøÜÁÿùâËÿúçÕÿùàÈÿò¹ƒÿýøóÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÙ¼ÿöЫÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¼‡ÿüîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕÑÌÿ0#ÿÿžžžÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÜÁÿöÍ¥ÿÿÿÿÿäääÿ---ÿÿÿÿÿÿÿÿÿÿø\ÿÿÿDþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿñ²uÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùßÅÿr^Kÿÿÿÿÿÿ999ÿÿÿÿÿõÊ ÿùàÇÿàààÿPPPÿÿÿÿÿÿÿÿÿÿ´™€ÿöͦÿõÈœÿôÂ’ÿò·~ÿð¯qÿñ±tÿð¬jÿð°rÿñ¶|ÿò»†ÿóÁÿôÇšÿòº„ÿóÀŽÿ÷׸ÿøÝÂÿùâÌÿúèÖÿûíàÿüóéÿýøóÿñ±sÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ{slÿÿDDDÿãããÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöЪÿøÙ¼ÿÿÿÿÿÿÿÿÿ½½½ÿ ÿÿÿÿÿÿÿÿÿÿŸÿÿÿLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿò·}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÙ»ÿ-&ÿÿÿÿÿÿSSSÿÿÿÿÿôÔÿúæÓÿàààÿPPPÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿøÜÁÿöΧÿÿÿÿÿÿÿÿÿþùõÿýôëÿüîáÿûé×ÿúãÍÿòº„ÿõË¢ÿ÷Ó°ÿöͦÿõÇœÿôÂ’ÿó¼ˆÿò·~ÿð±sÿð¬jÿð°rÿò·}ÿò»†ÿóÁÿôÇšÿõ̤ÿÙ¹™ÿ;0&ÿÿ¡’„ÿúèÖÿûíàÿüóêÿýùôÿþþþÿÿÿÿÿôÂ’ÿúçÔÿÿÿÿÿÿÿÿÿÿÿÿÿŒŒŒÿÿÿÿÿÿÿÿÿÿÉ"ÿÿÿþþþRþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüïâÿò»†ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿš„oÿÿÿÿÿÿ ÿ………ÿÿÿÿÿó¼ˆÿûíàÿàààÿPPPÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ó±ÿ÷×·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¼‡ÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüîáÿò»†ÿþùõÿýóëÿüîáÿûé×ÿúãÍÿùÞÃÿ–ƒqÿ ÿ1&ÿϨƒÿô‘ÿó¼‡ÿò·}ÿñ±sÿð¬jÿð±sÿð­lÿò¹ÿóÁ‘ÿôÇ›ÿõÌ¥ÿêÈ¥ÿPE;ÿÿÿÿÿÿÿÿÿå\ÿÿÿ]ÿÿÿÿâââÿÇÇÇÿ»»»ÿ¹¹¹ÿÂÂÂÿÑöÿè·‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¿¿¿ÿÿÿÿÿÿÿÿÓÓÓÿÿÿÿÿñ¶|ÿýôëÿàààÿPPPÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ ÿùàÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ²uÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúãÎÿôÆ™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿdddÿÿuiÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿð¯oÿüîáÿûè×ÿúãÍÿùÝÃÿøØ¹ÿÓ³•ÿÿÿÿÿÿÿÿÿÿ*AAA¸AAAÿ///ÿ&&&ÿ!!!ÿ!!!ÿ$$$ÿ*&#ÿ2(ÿJJJÿyyyÿµµµÿúúúÿÿÿÿÿ¢¢¢ÿ%%%ÿÿÿÿÿÿÿJJJÿÿÿÿÿÿÿÿÿð¯oÿþû÷ÿàààÿPPPÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿóÁ‘ÿûé×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿð®oÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÙ»ÿöÑ­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿØØØÿ:::ÿÿ´ª ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüîáÿò»†ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ´´´ÿÿÿÿÿÿÿÿÿ°hÜúÿÿÿÿÿÿÿÿÿ ÿÿ333ÿMMMÿÿÿÿÿÿÿÿ ÿÊÊÊÿÿÿÿÿþûùÿð®nÿÿÿÿÿàààÿPPPÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿò¹ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿò¸€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöΧÿøÜÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¬¬¬ÿÿ1$ÿÓÏËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùáÉÿõÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿz`FÿÿÿÿÿÿþÿÆ)]ôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýôìÿñµzÿÿÿÿÿàààÿPPPÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿð°qÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúçÕÿôÂ’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÔÿúçÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿˆˆˆÿÿ_F.ÿëëëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ô²ÿ÷Õ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÚ gÿEDCÿÿÿÿÿÿÿÙG'¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿUD3ÿðÅ›ÿöÏ©ÿ÷Õ³ÿöÑ­ÿñ¶|ÿúåÒÿÜÎÁÿOKHÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿþúöÿð°rÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùÝÃÿõ̤ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¸€ÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿmmmÿÿ„gKÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÇœÿùâÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿñ´xÿÏÏÏÿÿÿÿÿÿÿè`@íÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZUOÿðÜÊÿùáÉÿøÛ¿ÿ÷Õ´ÿôŘÿñ´yÿôÄ–ÿÕ¦zÿK:(ÿÿÿÿÿÿÿÿÿÿ´œ…ÿøÜÁÿùâÌÿù߯ÿñ¶|ÿüóêÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ô±ÿ÷Õµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð®oÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõõõÿZZZÿÿfÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòº„ÿüïâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúçÔÿôÂ’ÿüüüÿ§§§ÿÿÿÿÿÿór@ìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ...ÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿùàÈÿõÉŸÿÿÿÿÿàààÿOOOÿÿÿÿÿÿÿÿÿÿ´™€ÿöͦÿõÇœÿò»…ÿð°rÿñ¶}ÿð°rÿð¬jÿñ±tÿò·ÿó½ˆÿôÓÿò·}ÿóÀÿ÷Ô±ÿøÙ¼ÿù߯ÿúåÐÿûêÚÿüðåÿûîàÿñ´yÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåååÿJJJÿÿ«“}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð¯oÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÙ»ÿöЬÿÿÿÿÿðððÿpppÿÿþÿÿü€$¸ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>>ÿýýýÿÿÿÿÿÿÿÿÿøÚ¼ÿöЪÿÿÿÿÿàààÿNNNÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿù߯ÿõË¢ÿÿÿÿÿÿÿÿÿþþýÿýøóÿüòéÿûíÞÿúçÔÿò¸€ÿöЬÿ÷ÖµÿöЬÿõË¢ÿôÅ—ÿó¿ÿò¹ƒÿñ²uÿð¬jÿð®nÿñ´yÿó¼‡ÿó¿ÿôÅ—ÿÒ®‹ÿ>5+ÿ ÿ±“uÿùâÊÿúçÔÿûíßÿüòéÿýøóÿþþýÿüóéÿñ¶}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ¡ÿù߯ÿÿÿÿÿýýýýÜÜÜÿ,,,ôÿþÿÿ‰Sòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿbbbÿÿÿÿÿÿÿÿÿ÷Ó°ÿ÷Ö·ÿÿÿÿÿßßßÿMMMÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿ÷Ö¶ÿ÷Ô²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ¶|ÿýóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùàÇÿõÊ ÿþüùÿýöïÿüîáÿûêÚÿúåÐÿÒ¼§ÿ;3,ÿ ÿ³‘rÿõÈÿôÓÿó½ˆÿò·ÿñ±tÿð¬jÿð¯qÿð®nÿò¼‡ÿô‘ÿõÇœÿöͦÿ÷Ó°ÿøØºÿùÞÅÿò¸€ÿøÛ¿ÿüïãÿýõîÿýú÷ÿ¨¨¨ÑÿÿÿÿŒKÛÿÿÿÿÿÿÿÿÿÿÿÿIIIÿvvvÿ ÿÿÿÿÿÿÿÿ¸¸¸ÿÿÿÿÿõÌ¥ÿøÝÂÿÿÿÿÿáááÿRRRÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿöͦÿøÝÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð®nÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õ´ÿ÷Õ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚÚÚÿ???ÿ ÿ¹¶³ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÕµÿõÌ£ÿûîàÿúèÖÿùâÌÿøÜÁÿ÷×·ÿöÑ­ÿõË¢ÿð¬jÿóÀŽÿòº„ÿñµzÿÜ eýA/èÿÿÿÿŠˆˆˆ¢¢¢ß\\\ÿ'''ÿÿÿÿÿÿ>:7ÿoooÿ¬¬¬ÿîîîÿþþþÿÿÿÿÿÓÓÓÿÿÿÿÿÿÿÿ<<<ÿÿÿÿÿôƘÿúäÏÿÿÿÿÿåååÿ[[[ÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿôÅ–ÿúåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿñ´yÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÊ ÿùàÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâââÿFDBÿÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÌ£ÿøÝÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿñ¶}ÿÿÿÿÿÿÿÿÿ÷÷÷ÿ÷ÿÿþÿýƒöÓ¸ûòêâýùöÿÿÿÿÿÿÿÿÿûûûÿúúúÿÿÿÿÿò·~ÿüóéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÜȳÿÿÿÿÿÿÿÿÇÇÇÿó¿ŒÿûêÚÿÿÿÿÿëëëÿhhhÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿò¼‡ÿüîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûëÜÿó¾‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¿ÿûëÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïïïÿRMHÿÿ©©©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó¿ŒÿûêÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúåÐÿôÅ–ÿÿÿÿÿÿÿÿÿÆÆÆÿÿÿþÿÿövï­pBð´yõð¯qÿð¬kÿñ²uÿò·ÿó½ˆÿôÂ’ÿð®oÿõÉŸÿ÷Ò¯ÿøØ¹ÿùÝÃÿùãÌÿúèÖÿûíàÿ÷Õµÿ²”vÿÿÿÿÿÿ ÿÿò¸€ÿüñçÿÿÿÿÿôôôÿ}}}ÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿñ³vÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùáÊÿõÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ´yÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿdZOÿÿ”””ÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿñ²uÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ö·ÿ÷Ó°ÿÿÿÿÿâââý...ÿÿþÿÿÿëeõõõÿÿÿýþþþÿþýüÿýøòÿüòèÿûíßÿúçÕÿð¬kÿøÜÀÿ÷׸ÿöÒ®ÿöÍ¥ÿõÇ›ÿô‘ÿó¼ˆÿñ±tÿð®oÿ4%ÿÿÿÿÿÿK>2ÿð¯oÿöÒ®ÿøÛ¿ÿùáÉÿ“‡{ÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿþýûÿð®nÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷׸ÿöÒ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð®oÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ{iXÿÿqqqÿñññÿÿÿÿÿöööÿ¤¤¤ÿÒÒÒÿúõðÿð±sÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÉžÿùàÈÿóóóÿlllÿÿÿÿÿÿÿÝNÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð®nÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÑ­ÿøÙ»ÿ{{{ÿÿÿÿÿÿ60*ÿð¬kÿ÷Ô²ÿöÏ©ÿõÉŸÿ©ˆgÿÿÿÿÿÿÿÿÿÿ²’sÿöΧÿöÏ©ÿð±sÿùÞÅÿúãÎÿûéØÿüïâÿýôëÿþùõÿÿÿÿÿöΧÿøÜÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿò¸€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿš}bÿ ÿEEEÿÛÛÛÿäääÿKKKÿÿ???ÿäÕÇÿó¾Šÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò»…ÿùìßÿªªªÿÿÿÿÿÿþÿË1÷÷÷ ÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿñ²vÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõË¢ÿùÞÅÿ}}}ÿÿÿÿÿÿ653ÿñ²vÿÿÿÿÿÿÿÿÿÿÿÿÿÄÄÄÿÿÿÿÿÿÿÿÿÿµ¤’ÿøÜÀÿõ̤ÿñ´yÿõË£ÿôÆ™ÿóÁÿò»†ÿñ¶|ÿð°rÿð¬jÿð­mÿñ³vÿò¼‡ÿóÁ‘ÿôÇšÿõ̤ÿöÑ­ÿ÷×·ÿöϪÿòº„ÿúçÔÿûìÞÿüòèÿþùõÿþýûÿÿÿÿÿÿÿÿÿÀ”jÿ/,*ÿÿyyyÿ(((ÿÿÿ555ÿàȯÿõË¢ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿð¯oÿÕÓÑÿÿÿÿÿÿÿÿÿ¶ÿÿÿ$ÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿò·~ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôƘÿùãÎÿBBBÿÿÿÿÿÿLHEÿò¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÚÚÚÿFFFÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿùâÌÿõÈœÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿò¹ÿúçÔÿüîáÿûè×ÿúãÍÿùÞÃÿøØºÿ÷Ó°ÿó¾‹ÿò¸€ÿôÓÿó½Šÿò¸€ÿñ±sÿð­lÿð¯oÿñ´yÿç¦hÿP>-ÿÿÿÿÿÿ%!ÿÙ°ˆÿöÍ¥ÿüðäÿýõîÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿüñæÿá«wÿ@@@ÿÿÿÿÿÿÿÿÿšùùù,ÿÿÿÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüîáÿò»†ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÀŽÿÀ³¦ÿÿÿÿÿÿ ÿyphÿóÀŽÿÿÿÿÿÿÿÿÿÿÿÿÿóóóÿwwwÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿøÙ¼ÿöѬÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð°rÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÑ­ÿøÙ»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿùìÞÿÉ”bÿB>:ÿÿÿÿÿÿ ÿÑšeÿòº„ÿòº„ÿñµzÿð¯qÿð­lÿñ²uÿò¸ÿí´|ÿxX:ÿÿÿÿÿÿÿÿÿìjúúú3ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûéÙÿóÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔ£sÿ'%#ÿÿÿÿÿÿÿ½«›ÿôÆ™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ§§§ÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿöѬÿøÙ¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿð°rÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÆ™ÿúäÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöööÿ¥šÿ"ÿÿÿÿÿÿÿÿÅ•fÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿýøòÿüòèÿ¯‘tÿÿÿÿÿÿÿÿþÿÐ3ÿÿÿ:þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúåÑÿôÅ—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÓÓÓÿ3'ÿÿÿÿÿÿÿ999ÿøÜÁÿöÍ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍÍÍÿ222ÿÿÿÿÿÿÿÿºººÿÿÿÿÿõÈÿùâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðäÿòºƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò»†ÿüîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöööÿ………ÿÿÿÿÿÿÿÿÿÿ›pGÿúùøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿßßßÿÿÿÿÿÿÿÿÿÿÿ¬¿?ôÇ›aøÚ¾ÿùàÇÿúåÑÿûêÚÿüðäÿýõîÿøÝÂÿõÉŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãããÿ¥¥¥ÿÿÿÿÿÿÿÿÿ­­­ÿ÷Õµÿ÷Ô±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóóóÿrrrÿÿÿÿÿÿÿÿºººÿÿÿÿÿó¿ŒÿûëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúåÑÿôÄ–ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð°rÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙÙÙÿCCCÿÿÿÿÿÿÿÿÿÿeM6ÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõõõÿOOOÿÿÿÿÿÿÿÿþÿînÚ‘móÆ›löÏ©ÿõÊ ÿôÅ–ÿó¿ÿòº„ÿñµzÿð®oÿð¬kÿñ²uÿã¬wÿÊqÿ¡€`ÿI<.ÿÿÿÿÿÿÿÿÿ^\YÿþüúÿöÏ©ÿøÚ¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯¯¯ÿ ÿÿÿÿÿÿÿºººÿÿÿÿÿñ¶|ÿýôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÛ¿ÿöΧÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿñ±tÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿœœœÿ ÿÿÿÿÿÿÿÿÿ%ÿèèèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‹‹‹ÿÿÿÿÿÿÿÿÿÿÿÉÿÿÿÿÿÿUÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷×·ÿôÏ«ÿ»·³ÿqmiÿ0-+ÿÿÿÿÿÿÿÿÿÿ?0!ÿߦmÿð­mÿð¬jÿñ²uÿò¹‚ÿó¿ŒÿôÄ•ÿõÉŸÿöÏ©ÿܽŸÿRE8ÿÿÿÿÿÿÿºººÿþþþÿð®nÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÒ®ÿøØ¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîàÿó¼‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿbFÿ ÿÿÿÿÿÿÿÿÿÄÄÄÿþþþÿÿÿÿÿÿÿÿÿ¾¾¾ÿÿÿÿÿÿÿÿÿþÿøŒüüü]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ò¯ÿ®—ÿÿÿÿÿÿÿÿÿÿÿÿDDDÿÙÙÙÿÿÿÿÿÿÿÿÿóÁ‘ÿùáÉÿüñåÿûëÛÿúæÒÿùáÉÿøÛ¿ÿ÷Öµÿš|_ÿ ÿÿÿÿÿÿ¯}Mÿð±sÿð¬jÿò»†ÿóÁÿôÆ™ÿõË£ÿöѬÿ÷ÖµÿøÛ¿ÿó¾ŠÿöÒ®ÿûëÛÿüñåÿýöïÿþûøÿÿÿÿÿÿÿÿÿúãÍÿôÇ›ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿä§kÿ{ywÿ ÿÿÿÿÿÿÿÿiiiÿ÷÷÷ÿÿÿÿÿåååÿ***ÿÿÿÿÿÿÿÿÿÿÿÔ+ÿÿÿÿÿÿhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöΧÿE=5ÿÿÿÿÿÿÿÿÿÿÿZZZÿÝÝÝÿÿÿÿÿÿÿÿÿÿÿÿÿò»…ÿüïâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞÅ­ÿQC7ÿÿÿÿÿÿÁÁÁÿûêÙÿòº„ÿüîáÿûéØÿúäÏÿùÞÅÿøÙ»ÿ÷Ô²ÿöΨÿñ²uÿó¿Œÿó¾‹ÿò¹‚ÿñ´yÿð®oÿð­mÿñ³vÿñ²uÿñ´xÿôÓÿõÈœÿöͦÿ÷Ó°ÿøØ¹ÿùÝÃÿùÞÅÿð°qÿîàÔÿzuÿÿÿÿÿÿÿÿÿÜÜÜÿýýýÿ]]]ÿÿÿÿÿÿÿÿÿþÿø‹ÿÿÿüüütþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÇÿ2-(ÿÿÿÿÿÿÿÿÿ---ÿ………ÿóóóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ´yÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Õ³ÿ¦zÿÿÿÿÿÿhhhÿ°¡”ÿÒ©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ´yÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿý÷ñÿõÈÿ÷Ò¯ÿúçÔÿùâËÿøÜÁÿ÷׸ÿöÒ®ÿöÍ¥ÿó¿ÿñ²uÿó¼ˆÿì²|ÿŽiEÿ ÿÿÿÿÿÿÿzgTÿ‡tbÿÿÿÿÿÿÿÿÿÿÿÿÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÅ–ÿ[SLÿÿÿÿÿÿÿ&"ÿgUCÿÀÀÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿð­mÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÍ¥ÿðÕ¼ÿoooÿÿÿÿÿÿÿG;0ÿ|||ÿ«««ÿÚÚÚÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð®nÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÂ’ÿúèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùÞÅÿõË¢ÿÿÿÿÿÿÿÿÿÿÿÿÿ¸¸¸ÿKJIÿÿÿÿÿÿÿ ÿÿÿÿÿÿÿÿÿÿÿñaÿÿÿýýýˆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÀŽÿʽ°ÿLLLÿÿÿÿDDDÿ|||ÿµŸŠÿôΨÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿð¯qÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÅ—ÿúåÑÿÔÔÔÿ888ÿÿÿÿÿÿÿÿÿEEEÿsssÿ¤¤¤ÿ×××ÿüóêÿñ¶}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¸ÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ó°ÿ÷Ö·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞÞÞÿ†††ÿ)&#ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿü éÔª ûñæœþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò»†ÿüïâÿÕÕÕÿÿ‘‘‘ÿ¬¬¬ÿ×××ÿÿÿÿÿ÷Ô³ÿ÷Õµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿñ¶}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó½Šÿûíßÿÿÿÿÿ«««ÿÿÿÿÿÿÿÿÿÿÿÿ@@@ÿiaZÿ—wXÿÔÔÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð®nÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÇšÿùãÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¿©’ÿtaOÿ///ÿÿÿÿÿÿÿÿÿÿÿÿÿËìªg*ð³wÈð°rÿð¬jÿñ±sÿñ¶}ÿò»†ÿóÁÿð¯oÿôÇšÿöЫÿ÷Õ´ÿøÚ¾ÿù߯ÿúäÐÿûêÙÿõÈÿ÷Õ´ÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÞÿó½‰ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ¶|ÿýõíÿÿÿÿÿýýýÿˆˆˆÿ ÿÿÿÿÿÿÿÿÿÿÿÿ ÿ;;;ÿcccÿ˜˜˜ÿÒÒÒÿÿÿÿÿÿÿÿÿýõíÿñµ{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò»…ÿüîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöΧÿøÛ¿ÿcccÿÿÿÿÿÿÿÿÿÿÿÿæ?ÿÿÿ ÿÿÿ¯ÿÿÿÿþþýÿþùõÿýóëÿüîáÿûéØÿð°qÿøÛ¾ÿøÚ¼ÿ÷Õ³ÿöϪÿõÊ¡ÿôŘÿóÀŽÿñ±sÿñ²uÿð±sÿð¬jÿð±sÿñ¶|ÿò»…ÿóÀŽÿó¾Šÿñ´yÿöЪÿ÷Õ³ÿøÚ¼ÿù߯ÿúäÏÿûéØÿüîáÿð®nÿý÷ðÿþþþÿÿÿÿÿóóóÿmmmÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ666ÿ[[[ÿ’’’ÿ˽°ÿóÀŽÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð°qÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÁÿʼ­ÿ...ÿÿÿÿÿÿÿÿÿÿÿ þWÿÿÿ ýýý¾þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð­mÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÔÿúæÓÿÿÿÿÿÿÿÿÿþùõÿýôëÿüïâÿûêÙÿöÏ©ÿó¿ŒÿøÚ½ÿ÷Õ´ÿöЫÿõË¢ÿôƘÿóÁÿòº„ÿð¬kÿñ±sÿð¬jÿð°rÿñµ{ÿß«yÿ[H5ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ/*&ÿPB5ÿŒŒŒÿÎÎÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿñ³vÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿç¬tÿHFCÿÿÿÿÿÿÿÿÿÿÿÿËìììÿÿÿÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿð®nÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó½ŠÿûìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøØºÿöÑ­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿò¹ÿÿÿÿÿÿÿÿÿþùõÿýôìÿüïãÿæÖÈÿ^ULÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ)$ÿKC;ÿƒwkÿǸ«ÿüîáÿùâËÿó½ŠÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿpQ4ÿÿÿÿÿÿÿÿÿÿÿÿý÷÷÷gÿÿÿÿÿÿÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿñ³vÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò¸€ÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÑ­ÿøØ¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûêÙÿóÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëà×ÿmS:ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ$ÿB3%ÿxY:ÿ¾‰Wÿð¬kÿð¯pÿñ´yÿò¹ƒÿó¿ŒÿôÄ•ÿŸ`ÿ ÿÿÿÿÿÿÿÿÿÿÿ­­­ÿúúúûúúú4ÿÿÿþþþéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿò·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ²uÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõË¢ÿùÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùâËÿõÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûé×ÿ踊ÿ•••ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿ???ÿzxwÿÅ¿¹ÿüðåÿûëÛÿÔòÿ4+"ÿÿÿÿÿÿÿÿÿÿ)ÿ¹‡Uÿð³xÿñ¸üí¯r:óóóÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿÿÿÿÿûíßÿó¼‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýýýÿÿÿÿþþþÿð­lÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÄ•ÿúåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÚ½ÿöЫÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùàÈÿõÊ¡ÿúúúÿÁÁÁÿ///ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿ888ÿ€€€ÿEEEÿÿÿÿÿÿÿÿÿÿaPAÿÞÞÞÿþûøÿüõîýûïäûÔª¿¿¿ÿÿÿ:ûûûJþþþ[ÿÿÿoÿÿÿƒÿÿÿ—ùåÒ¶ò½ŠÙÿÿÿÞÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿýùõÿð°qÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿó½ŠÿúëÜÿÿÿÿÿþþþÿÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿ÷Ó°ÿ÷׸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷׸ÿ÷Ó°ÿÿÿÿÿÿÿÿÿæææÿwwwÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿÿÿÿÿÿÿÿÿ¤Šrÿè̱ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕÿÿÿÿÿÿÿÿÿߟâªcÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿÿóóóøäÑ'ï®obÿÿÿ9ÿÿÿLþþþ[ÿÿÿoÿÿÿ‚ýýý•ÿÿÿ¯ðµ{ßûñçëÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõË¢ÿù߯ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõΨÿøÛ¿ÿÿÿÿÿÿÿÿÿÿÿÿýöööÿÊÊÊÿKKKÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿzzzÿàààÿð¾Žÿûè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒÌ™fÿÿÿÿÿÿä¡]ªªªÿÿÿÿÿÿþþþëëë òòò÷÷÷ ðµ|Zõ×¹MÿÿÿJÿÿÿXÿÿÿlÿÿÿ‚ÿÿÿ›ÿÿÿ·óÔßùãÍîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóóóÿ¸¡ŒÿE:0ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿnnnÿÙÙÙÿöööÿÿÿÿÿñ³vÿý÷ðÿÿÿÿÿÿÿÿÿÿÿÿÿûûûN¿?ÿÿÿéªj ¿ÿÿÿþþþþþþÿÿÿÿÿÿ ë·‡O×°Œ[ŒŒŒk444¹õÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ///ÿÿàààýøøøÿÿÿÿÿÿÿÿÿý÷òÿñ²vÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ# E‘Ôÿÿÿÿÿÿÿÿÿÿÿÿÿÿü---îxmcïÈ yúõõõÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûéØÿóÀÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿ AlލºÅǶ¡„_0 ff3ªªUÿÿÿÿÿÿÔÔÔëëë òòòÿÿÿ!ôÅžGñÀ^ÿÿÿIÿÿÿ\þþþqÿÿÿ‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÿÿÿÿÿÿþÿÿÿÿÿÿà?ÿÿÿÿðÿÿÿÿÿÿàÿÿÿ€ÿÿÿÿÿàÿ?ÿÿÿÿÿàÿÿÿÿÿàÿÿÿÿÿàÿÿÿÿÿàÿÿÿÿàÿÿÿàÿÿÿàÿÿÿàÿÿÿàÿÿÿàÿÿÿàÿÿÿàÿÿÿàÿÿÿàÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿÀÿÿÿ€ÿÿþÿÿøÿÿðÿÿðÿÿðÿÿðÿÿð?ÿÿø?ÿÿþ?ÿÿÿ€?ÿÿÿÀ?ÿÿÿ€ÿÿÿ€ÿÿÿ€ÿÿÿ€ÿÿÿ€ÿÿÿ€?ÿÿÿ€ÿÿþÿÿøÿÿðÿÿðÿÿðÿÿðÿÿðÿÿøÿÿü?ÿÿÿ€ÿÿÿÿ€ÿÿÿÿ€ÿÿÿÿ€ÿÿÿÿ€ÿÿÿÿ€ÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿþÿÿÿüÿÿÿøÿÿÿðÿÿÿðÿÿÿðÿÿÿðÿÿÿøÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿüÿÿÿøÿÿÿðÿÿÿðÿÿÿðÿÿÿðÿÿÿøÿÿÿüÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþ?ÿÿÿþ?ÿÿÿþÿÿÿþÿÿÿÿüÿÿÿÿüÿÿÿÿüÿÿÿÿüÿÿÿÿüÿÿÿÿüÿÿÿÿüÿÿÿÿüÿÿÿÿüÿÿÿÿÿÀÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ(  ÿÿÿÿÿÿÿÿÿÿÿÿ  #.? O a u‹˜š¡£¥¥¡Ÿœ™y `I 4"  3ÿÿÿýýýªÿÿÿƒüüühûûûQÿÿÿEÿÿÿ@ÿÿÿ7ÿÿÿ,ÿÿÿ!ÿÿÿÿÿÿ þþþÚÚÚÿÿÿÿÿÿÿÿÿf  % 9 T}¯Åâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ а ” ^6 /ÿÿÿ4ÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýýþþþîÿÿÿÝÿÿÿÍýýý¾ÿÿÿ³ÿÿÿ¬ÿÿÿœýýý…üüükÿÿÿQÿÿÿ9ÿÿÿ&öööÿÿÿôôôòòòÿÿÿççç ÿÿÿ ÚÚÚÿÿÿÿÿÿªªªÿÿÿ: " 7"`“·ßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿü à$Z 0 $úúú>ÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿþþþÿýýýûýýýçþþþÑÿÿÿ¹þþþ£ÿÿÿýýýƒüüüxÿÿÿiÿÿÿVûûûBùùù.ÿÿÿòòòÿÿÿððâé¿” ÿÿÿ ÿÿÿÿÿÿÿÿÿªªª? # - N†¼ ìÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿ ÿ Î Œ#H( ÿÿÿÿûûûLþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùÿÿÿôÿÿÿðÿÿÿìþþþåúðåÕðÁ“¼ǫ́¢ÿÿÿ‡ÿÿÿoüüüaüüüZûûûRÿÿÿFþþþ8øøø*ÿÿÿÿÿÿòòòðððÿÿÿÿÿÿ ßßß¿¿¿ÿÿ B+!L  óÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿ í ¢*[ /" ÿÿÿÿÿÿZÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿûîáÿð¿ÿõÔ³ÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿûþþþíþþþßýýýÒÿÿÿÇýýýÁýýý¶ÿÿÿ¢ÿÿÿŠþþþqüüüXÿÿÿEÿÿÿ;úúú6ÿÿÿ0øøø)ÿÿÿ"õõõÿÿÿðððîîîÿÿÿ âââ ÌÌÌÿÿÿ+ 8 `£ Þ ÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿí 'Z+/[$ÿÿÿüüügÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿjÿö×¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿäÿÿÿÐýýý¼ÿÿÿ«ÿÿÿžÿÿÿ”ýýý…ÿÿÿsüüü_ûûûKÿÿÿ9ÿÿÿ,øøø(ÿÿÿ%÷ÿÿ!ÿÿÿòÚÂîªwçй ååå ÿÿÿÿÿÿÿÿÿE 7 e®ìÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÞ ‹ JP+#ÿÿßßßÿÿÿsÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéØÿﻇÿöÚ¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿýýýýÿÿÿúýýýöþþþéÿÿÿÔÿÿÿ¼õÝťøäÒ~üüüxþþþpüüübûûûTÿÿÿCúúú4øøø(ÿÿÿ%ÿÿÿ#ÿÿÿÿÿÿÿÿÿååå ¿¿¿1P)!T%œßÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿú¹+o05¶Hÿÿÿ ÿÿÿ|ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÔÿﺅÿ÷ÝÄÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöÙ½ÿ︂ÿúêÚÿþþþÿÿÿÿÿÿÿÿÿýýýùþþþíýýýãýýýÛÿÿÿÔÿÿÿÎÿÿÿ¼ýýý§ýýýüüüyÿÿÿfþþþ[üüüVÿÿÿOÿÿÿEúúú:ÿÿÿ/ÿÿÿ&ÿÿÿ ÿÿÿôôôÿÿÿééé ÌÌÌ?0 'm¾ ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÕ!‰7J™Dÿÿÿ ýýý€þþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÑÿ︃ÿøàÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÔ´ÿ﹄ÿûîàÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿþþþÿþþþÿÿÿÿÿþþþÿÿÿÿóþþþâýýýÒÿÿÿÃÿÿÿ¸ýýý¯ýýý£ÿÿÿ‘þþþ~üüüjÿÿÿXÿÿÿJÿÿÿCþþþ?ÿÿÿ7ùùù.øøø%öÿÿÿóóñÉ“ï¯ÿéé Úþþÿÿÿ05yÈ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿé ›V™?ÿÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿøãÍÿ︂ÿùäÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЬÿ(ÿûñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿÿÿÿÿÿÿÿÿýýýøÿÿÿçÿÿÿÓÿÿÿ¾ÿÿÿ«ýýý›ñĘ•ð¾Žýûùþþþqÿÿÿ`ûûûOÿÿÿBúúú<ÿÿÿ:úúú3þþþ)ÿÿÿòòòççç ÿÿÿªªª\/ (}Íÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ í ¦'`ŸUééé ýýý‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÊÿ︃ÿùçÔÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÌ¥ÿð¾ŒÿüôêÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿñÂ’ÿòÄ™ÿþþýÿÿÿÿÿýýýøÿÿÿñÿÿÿëÿÿÿæþþþàýýýÓýýýÀÿÿÿ¬ýýý˜ÿÿÿ‡ÿÿÿ}ÿÿÿxþþþpüüücüüüUûûûHúúú;ÿÿÿ4ùùù/þþþ)÷÷÷ ÿÿÿÿÿÿ ;w3vÈÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ ñ ¯&dÔqìììÿÿÿ•ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÅÿ﹄ÿúéÙÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿòÈŸÿñÀ‘ÿüôíÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿþóË¥ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿûþþþîþþþâÿÿÿ×ÿÿÿÎÿÿÿÇÿÿÿ¼ýýý®ÿÿÿœÿÿÿ‹ÿÿÿzÿÿÿmüüüeüüü_ÿÿÿTûûûHúúú<ÿÿÿ0øøø&ÿÿÿ þþþóççì£mÔª\ÿ 6] µýÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ ï®*aÿâ ÿÿÿþþþ£þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ú¿ÿðº†ÿúìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿòÆ™ÿòÄ—ÿüõïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿî·€ÿôÒ±ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿýýýôÿÿÿäÿÿÿÔÿÿÿÄÿÿÿ·ÿÿÿ¯ýýýªøëÜí³zŽöÞÅ}ÿÿÿnüüü`üüüYüüüVûûûMþþþ?ùùù0ÿÿÿ"óóóÿÿÿÿÿÿ ßßßÿÿÿ+n5 (ž ëÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ ê­L)Wÿÿÿÿÿÿ²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþüÿö׸ÿð¼Šÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿñÔÿòÈžÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿî´zÿöØ»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿùèÖÿí´{ÿ÷ãÎþÿÿÿûÿÿÿ÷ÿÿÿôÿÿÿðþþþåÿÿÿÕýýýÄÿÿÿ´ÿÿÿ¥ÿÿÿÿÿÿšýýý‘ÿÿÿ‚üüürÿÿÿbûûûTÿÿÿKÿÿÿGúúú?ÿÿÿ2ÿÿÿ$ÿÿÿþþþmþHi Ñÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿã'ªX.BòòòÿÿÿÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿõÓ±ÿð¾ÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿð¿ŽÿóÌ¥ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿí±uÿ÷߯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýýÿøãÎÿî³{ÿúëÛÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþöþþþíþþþåþþþßýýýÛÿÿÿÓÿÿÿÆýýý¸ÿÿÿ©ÿÿÿœýýý‘ýýý‹ÿÿÿƒüüüuÿÿÿfÿÿÿWÿÿÿHÿÿÿ<úúú3ÿÿÿ,ÿÿÿ"óóóÿçç cª$4Ÿ ïÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ÿ Ø “›+)ÿÿÿÿÿÿÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿôЫÿñÁ’ÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿð½ŠÿôÑ­ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúîáÿì°sÿùåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷ÞÅÿîµ}ÿûñåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿþþþÿþþþÿÿÿÿÿþþþÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿûýýýïÿÿÿãÿÿÿØþþþÏÿÿÿÈýýýÁÿÿÿ·ÿÿÿªûóéœðØŽñ̤‚üøô|ÿÿÿvüüüjÿÿÿYûûûGÿÿÿ6ÿÿÿ&öööÿÿÿÿÿÿÿÿÿ ÿÿÿ"Y< ÅýÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÎ?#€ÿÿ ÿÿÿÿÿÿÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿóͦÿñÄ–ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿﺇÿöÕ¶ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿì¯rÿúêÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿöØ»ÿ︂ÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿûðåÿñÁ’ÿôϬÿýú÷þÿÿÿúÿÿÿñþþþåýýýØÿÿÿÌÿÿÿÀÿÿÿ»ÿÿÿ¸ýýý®ÿÿÿ ÿÿÿÿÿÿþþþq÷üüidŠ   èÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ õÀc1WôôôÿÿÿÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿòÊ¡ÿòÆšÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿ﹄ÿ÷Ú¿ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿøâÌÿí¯sÿûðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿôÑ®ÿð¼‰ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýþþþþÿÿþþÿÿÿÿÿúìÝÿð½‹ÿöÔ´ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûÿÿÿõ÷ûÿñ‚’®õ !þÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ è)¥–4'ÿÿÿýýýÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿòÈžÿòÈžÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÕÿï¸ÿøßÆÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÛÀÿí°vÿýöîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿóÊ¡ÿñÁ’ÿþýúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿùæÔÿð»ˆÿ÷Ú¾ÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþþÿöùüÿxŠ™ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿüÙH+{ÿÿÿÿÿ ýýýÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿòÆšÿóÊ¢ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÎÿï·€ÿøâÌÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿõÕµÿî´{ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿñÕÿòÇœÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÉÿð»‡ÿøàÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôøûÿo…–ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ÷# ÀpB=øøø(ýýýäþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûòéÿñÄ–ÿôͧÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿøàÈÿï¸ÿùåÑÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÏ©ÿî·ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿð½‹ÿôͧÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ÷Ú¿ÿð»ˆÿùåÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöùûÿrˆšÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþè6ÿ“ùùù/þþþîþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðåÿðÁ’ÿôЭÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿ÷ÜÁÿ﹃ÿùèÖÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿòÈŸÿﻊÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüõîÿÿõÔ²ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿõÕ¶ÿð½ŒÿûëÜÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøúûÿ~“¡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿýÏo;Iÿÿÿ5ÿÿÿùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿð¾ÿõÓ²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿö׺ÿﺅÿúêÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿñÕÿñ“ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüóêÿí´|ÿ÷Ú¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿôϬÿñÀ’ÿûðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûüþÿ‘£Äÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ ó>’Ì3ÿÿÿ9ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÝÿ)ÿö׸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÓ±ÿð¼‰ÿûíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð½ÿòÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðäÿî²xÿøàÉÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿó̤ÿòŘÿüôìÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýþÿÿ±ÊÙÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ# Õk+Gúíà;üòçÿýöðÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÙÿﺆÿöÚ¾ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΪÿð¿Žÿüðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿï¹…ÿôΪÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúêÛÿí²xÿùæÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõïÿòÈÿòÉŸÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓàìÿ %ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿGC>ÿkifÿ‡ƒwÿ®®¨ÿÈÅÅÿ×ÖÕÿÝÝÞÿÖÖÖÿÍÏÏþÀÂÂý®°µü‘”˜üqqsûcfhüHKNü$'ýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ ûDŽ¡5í¯v:îµ}ÿî·þð»‡ÿð¿ŽÿñÖÿòÇÿó̦ÿõÓ²ÿöÚ¾ÿøáËÿúè×ÿûïáÿüòçÿüóëÿüöïÿýùõÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿùèÖÿ﹃ÿ÷ÝÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿóË£ÿñ“ÿüòéÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöïÿîµ~ÿöÖ¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿùãÏÿî³zÿúíÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿüòèÿòÖÿôͦÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëó÷ÿ!)Xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ_YPÿª¡™ÿåàÚÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿöøùÿØÝáÿ¢¦®ÿknwÿ:>Hÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ+ Òn3<ÿÿòΪ?óË£ÿñÅ™ÿð¿ÿﻆÿï¶ÿî³zÿí±vÿí°tÿì¯rÿí¯rÿí¯sÿí°vÿî²xÿî´}ÿ﹃ÿ*ÿñÁ“ÿòÇ›ÿóÌ¥ÿôÑ®ÿõÕ¶ÿöÛÀÿøáÌÿùèØÿûïäÿüöïÿýùöÿþûùÿþüúÿþýüÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÕÿ︂ÿøâËÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿòÇœÿòÅ™ÿüõìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûòçÿî²xÿ÷ÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÜÂÿïµ~ÿûòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿûîàÿð¿ÿôÒ¯ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùúüÿVw’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ'ÿyl^ÿÒÈÁÿÿýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿûýÿÿÍÔÚÿ‹“ÿ>FCÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ û_<ˆ·„GÿÿûûøIþûùÿýúöÿþøóÿýöðÿýõìÿüñçÿûíáÿùèØÿøãÎÿ÷ÞÃÿöعÿõÒ°ÿóͧÿòÈŸÿñÄ–ÿð¿Žÿﺆÿî¶~ÿí³xÿí°uÿì®rÿì®qÿí®pÿí¯qÿí°tÿí²xÿîµ|ÿî·‚ÿ*ÿð”ÿòÈŸÿóΪÿõÕµÿ÷ÚÀÿøâÌÿôÒ°ÿîµ~ÿ÷Û¿ÿý÷ñÿþú÷ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùöÿòÄ—ÿòÉŸÿýöïÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìàÿí°uÿùæÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿõÔ´ÿ﹄ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúéØÿð½Šÿö×¹ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ•²Îÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿQD<ÿÁ³©ÿÿýùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿòÈÿî”ÿ¼ÀÍÿx~‡ÿ(06ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ`K-ñÞÓýýûú¢öÞÅ—ðº‰øåÒyÿÿÿ`ûûûFùùù,ÿÿÿÿÿÿÌÌÌ¿¿¿ÿÿÿÿÿÿÿÿÿVÿÿÿÿþþþÿÿþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþýÿþþüÿþýüÿþýûÿþûøÿýúöÿýøòÿýõîÿüòéÿûðäÿúìÞÿùè×ÿøãÎÿ÷ÞÃÿö×¹ÿôÑ­ÿóË£ÿñÆ™ÿðÁ‘ÿjÿ﹄ÿî¶ÿî³yÿí±uÿí¯sÿì¯qÿí®pÿì­nÿí¯sÿî³yÿîµ~ÿ﹄ÿ*ÿð“ÿñÈÿóϪÿõÖ¸ÿ÷ÝÄÿùäÐÿúè×ÿúìÝÿûïâÿüóêÿýøòÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿñÁ’ÿóÌ¥ÿýøòÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÖÿí¯sÿúìßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿó̦ÿð¾ŒÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùãÎÿﻇÿ÷ÝÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×çòÿ!ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿraXÿÜÖÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüõîÿð¿ŽÿóÉ ÿÿÿÿÿÿÿÿÿÿÿÿÿÚâêÿˆ•ÿ19=ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ" ÿÁ²Ÿþïϯüð½üúíàüÿÿÿûÿÿÿúÿÿÿúÿÿÿùÿÿÿùÿÿÿðÿÿÿÞÿÿÿÈýýý°ýýý˜ÿÿÿƒÿÿÿsüüühÿÿÿYÿÿÿEÿÿÿ1ÿÿÿÿÿÿÿÌÌüþþeÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþþÿÿþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþýÿþýüÿþüûÿýûùÿýú÷ÿýøòÿüõíÿûñçÿûîàÿúéÙÿùåÒÿøáÊÿóÊ¢ÿí²wÿòÆ›ÿóÊ¢ÿñÄ–ÿð¾Œÿﺅÿî¶ÿî´zÿí±vÿí°tÿì¯rÿí¯qÿí®rÿì°tÿí²xÿíµ|ÿ︃ÿð¼ŠÿñÁ‘ÿòÅšÿóÉ¢ÿôЬÿö׸ÿ÷ÞÅÿùåÓÿûìßÿüñçÿüóêÿýôíÿý÷òÿþúöÿþüúÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿñÀÿôЫÿýùôÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷âËÿí¯sÿûñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿñÅ™ÿñÄ–ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ÷ÞÄÿﻇÿùãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùúþÿ5Kuÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ#ÿ~M.ÿîÖÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüóêÿ﹄ÿôÒ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙâìÿ‡Žÿ'/7ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€a@ÿݱ…ÿüóìÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿþÿÿÿúýýýöÿÿÿðÿÿÿëÿÿÿæýýýâÿÿÿÜÿÿÿÌýýý±ýýý•üüüyÿÿÿ`ÿÿÿQûûûJÿÿÿ@ùùù2÷÷÷#òòòÿÿÿÚÚÚüüütþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿ÷Ú¿ÿﻇÿûíßÿÿÿÿÿþüúÿþú÷ÿýøôÿüöîÿüñæÿúìßÿùçÕÿøâËÿ÷ÝÃÿö׺ÿõÓ±ÿóͧÿòÈÿñ“ÿð¼Šÿ︂ÿîµ{ÿî²wÿí°tÿí¯rÿí­pÿì®pÿì¯rÿí°tÿî²xÿîµ~ÿﺅÿð¿ŽÿñĘÿòÊ¢ÿôÏ«ÿõÔ³ÿöÙ¼ÿøáÊÿ÷ÞÅÿ﹄ÿôÏ«ÿüôìÿýûøÿþûøÿþüùÿþüúÿþýûÿþþýÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿöÜÁÿí±vÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿýøôÿð¿ŽÿòÉ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿöغÿð½ŠÿúéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿˆŸÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ!ÿyd[ÿä·‘ÿ﹃ÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿûíÞÿï¶ÿöÚ¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¹ÀÖÿclvÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ9&ÿÒŵÿú÷õÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿþþþÿýýýüÿÿÿðýýýâÿÿÿÖýýýÊÿÿÿÁýÿÿ»ÿÿÿ¬ôÕ¸”í¸€wùîßZÿÿÿ@ÿÿÿ/øøø'÷÷÷"õõõÿÿÿÿÿÿ ÿÿÿâââ ÿÿÿƒþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿöÖ·ÿð¼‰ÿûðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþýûÿþûøÿþùõÿý÷òÿýõîÿüñçÿûíÞÿùçÕÿøâÊÿ÷Û¿ÿõÕµÿôЬÿóÊ£ÿòÆšÿñÁ’ÿiÿÿî´|ÿí±wÿí°tÿí¯rÿí®qÿì­pÿì¬mÿí¯qÿí²xÿîµ}ÿï¹…ÿð¿ÿòÅšÿóÌ¥ÿôÓ±ÿöÙ½ÿ÷ÞÅÿøâÍÿùæÔÿúìÝÿûñçÿýöðÿþû÷ÿþýûÿþýûÿþýüÿþýüÿþýýÿþþýÿþþýÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÖ·ÿí´{ÿý÷òÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿý÷òÿﺆÿôЫÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿõÓ±ÿñÀŽÿûïâÿÿÿÿÿÿþþÿÿÿÿÿÙëõÿ "ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ_SIÿÙÑÄÿÿÿÿÿóÇœÿñÀÿÿýûÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿùäÐÿîµ~ÿøãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõüÿÿŒž©ÿ:@Fÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¥Œ€ÿïêåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýþÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿóͦÿ(ÿýõîÿÿÿÿÿþÿÿÿÿÿÿÿýýýûýýýéÿÿÿÖÿÿÿÃýýý±ÿÿÿ¢ýýý—ÿÿÿ‰ÿÿÿtÿÿÿZûûûAøøø*ÿÿÿééé ççç ÿÿÿ ÿÿÿççç ýýýŽþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýûøÿôÓ±ÿð¾ÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþýÿþüúÿþû÷ÿýøóÿýõîÿüóéÿûïãÿúëÜÿùæÓÿøâÍÿôϪÿî³zÿð¿ŽÿòÈÿòÖÿð¿Žÿﻇÿï·ÿîµ{ÿî²wÿí°tÿí¯rÿí¯rÿì¯rÿí°uÿí²xÿî´|ÿï·ÿﻇÿðÀÿñÅ™ÿóË¥ÿõÓ²ÿ÷Ú¿ÿøáËÿùæÓÿúéØÿúëÝÿûïäÿüóêÿü÷ñÿþû÷ÿþüúÿþüúÿþüûÿþýûÿþýüÿþþýÿÿÿÿÿôЫÿÿýùõÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ðÿî¶~ÿöÖ·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôΪÿñÔÿüóêÿÿÿÿÿÿÿÿÿþÿÿÿFe„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ94/ÿ¿¬šÿÿÿÿÿÿÿÿÿþüûÿð½ŠÿóÊ¢ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿ÷Û¿ÿï¸ÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ·ÇÖÿ]gqÿ!"$ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿkT:ÿÜÕÎÿÿþüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿñÄ–ÿòĘÿýøóÿÿÿÿÿÿþþÿÿÿÿþþþþÿþþþÿþþþÿÿÿÿÿþþþÿþþþÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿõýýýÏûûûPééé ýýý–þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôÏ«ÿðÀ‘ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÔÿ﹃ÿøàÉÿþýüÿþýüÿýú÷ÿýøòÿüôìÿûðäÿúìÝÿúçÕÿùâÎÿøÞÅÿöغÿôÒ¯ÿòÌ¥ÿñÆšÿðÀ‘ÿð¼Šÿ﹄ÿîµ~ÿî³yÿí±vÿí¯sÿí®rÿì¯rÿí°tÿí²wÿí´|ÿî·ÿﻇÿðÀÿñÄ—ÿòÉŸÿóΨÿõÔ´ÿöÛÀÿøâÍÿúêÛÿòÖÿﻇÿûñåÿüôëÿýöïÿþùóÿþú÷ÿþüùÿþüúÿþüûÿþýûÿþýüÿþþýÿþþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿí³zÿ÷ÞÃÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿý÷ñÿóÊ¢ÿòÆšÿý÷ñÿÿÿÿÿÿÿÿÿ¨ÅÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ'"ÿƒogÿÿ÷éÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿí¶~ÿõÖ¶ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿýú÷ÿôЭÿð»‰ÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÜåïÿu|…ÿ)+8ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ)ÿ¾²¡ÿõòïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿð¼ŠÿôЫÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿþþþÿýýýÚûûûGÿÿÿ ýýý›þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿóͦÿñ”ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÊÿï·ÿøãÎÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþýûÿþûøÿýøóÿüôìÿûïäÿùêÚÿøåÑÿ÷ßÇÿöÚ¾ÿöÕ¶ÿôЭÿòÊ£ÿñÅ™ÿðÀ‘ÿﻈÿï·‚ÿîµ}ÿí³yÿí°vÿí¯sÿí®rÿì®rÿì­mÿì®qÿî´|ÿ﹃ÿð½‹ÿñÔÿòÈžÿóͧÿôÒ°ÿõÖ·ÿöÜÀÿøâËÿùèÖÿúîáÿûóêÿüöïÿý÷ñÿý÷óÿýùôÿýúöÿþûøÿþüùÿþüúÿþýûÿþýüÿþýýÿþþþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûìßÿî±wÿùäÐÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿüôëÿòÆ™ÿóÊ¢ÿýúöÿÿÿÿÿòøÿÿ 6LÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿN>7ÿÍÁ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñæÿí°tÿøàÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿýøôÿòÆœÿñÁ“ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿéóøÿ‘ÿ9?Fÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‡{mÿèÞÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿúîàÿ︂ÿöÛÀÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÅÿÿÿ.ÿÿÿ þþþ£ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿóË£ÿñĘÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÃÿï·ÿúçÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþýüÿþûøÿýùõÿý÷ñÿüôëÿûïãÿúêÚÿøäÐÿ÷ÞÆÿöغÿî´{ÿﺄÿòÉ ÿòÅ™ÿñÀ‘ÿð¼ˆÿ︂ÿïµ}ÿí³yÿí²vÿí±tÿí¯sÿí¯sÿí°tÿí±wÿî´{ÿï·ÿð¼Šÿñ•ÿòÉ ÿôÏ«ÿöÖ¶ÿöÚ¾ÿ÷ÞÄÿøáËÿùæÓÿúëÝÿûðæÿüôíÿý÷ðÿý÷òÿýøóÿýùõÿþú÷ÿþûùÿþüûÿþýüÿþýûÿùæÒÿí±wÿúëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûðäÿñÁ’ÿôϪÿþüúÿÿÿÿÿ}’¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ$ÿypfÿÿøèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÙÿí¯sÿúêÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ïÿñ¿ŽÿòÉ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñöûÿœ¥ÿ@HNÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[A0ÿÍǽÿÿÿûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿùãÎÿî¶ÿùåÑÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿ®ÿÿÿÿÿÿÿÿÿ¯þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿóÊ¡ÿòÇœÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿöÚ½ÿ︂ÿúëÛÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿ﹄ÿôÒ¯ÿþýýÿÿüúÿþúöÿý÷ñÿüôìÿüñåÿûíßÿúè×ÿøãÎÿ÷ÝÄÿõ×¹ÿôÑ®ÿóÌ¥ÿòÈÿñÕÿð¿Žÿ(ÿ︂ÿîµ}ÿí³yÿí²wÿí±uÿí±uÿí±wÿî²yÿíµ|ÿî¶€ÿﺆÿð½Œÿñ•ÿòÉŸÿôÏ«ÿõÖ¸ÿ÷ÝÃÿøáËÿøãÍÿôÒ°ÿí²xÿøåÑÿüóéÿýôíÿý÷ñÿýøóÿýùôÿýúöÿþûøÿþüûÿþýýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿð¾ŒÿõÔ´ÿþþþÿàðüÿ!9ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ<2-ÿ»©“ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøáÌÿí±uÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿûòçÿ﹄ÿõÓ°ÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïôúÿ”ž§ÿDKRÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"ÿ®ÿôñëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöغÿ﹃ÿúíßÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ’ªªªÿÿÿýýý¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿòÆ›ÿóÊ¡ÿþþüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÖ·ÿﺄÿûíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿýùõÿîµ}ÿõغÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿþüûÿýùõÿýöïÿüòèÿûîàÿúêÙÿùåÒÿøáÉÿ÷ÛÀÿõÖ·ÿôЭÿóË£ÿñÆšÿñ“ÿð¾ÿðº†ÿî·ÿî´}ÿî²yÿí±vÿí±uÿî±vÿí¯sÿí­pÿî¶ÿﻇÿð½Œÿñ“ÿòÆšÿòÊ¢ÿôЬÿöÖ·ÿ÷ÝÂÿøãÍÿùèÖÿúêÛÿúìÞÿûîâÿüñæÿüóëÿüöïÿýøòÿýùôÿýúöÿþûøÿþüúÿþýüÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÓÿﻈÿ÷Ú¿ÿÿÿÿÿd}ŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿdSDÿãÒÆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöغÿîµ}ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúìÜÿî¶~ÿ÷ÜÃÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿéðöÿ™¤ÿ>IQÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ}rbÿâÖÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôͦÿñ¿ÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýòÿÿÿrÿÿÿýýýÍþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿñÖÿô̦ÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÒ°ÿð¼ˆÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöîÿî²xÿ÷ÞÄÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿþüûÿýùõÿüõïÿüñçÿûíßÿúèÖÿøâÍÿ÷ÞÆÿöؼÿð¿Žÿí²wÿóÊ¢ÿòÆ›ÿñÁ’ÿð½Œÿðº†ÿî·ÿîµ}ÿî³yÿí±wÿí°uÿí±tÿí²wÿí´{ÿî¸ÿﻈÿðÀ‘ÿñÅ™ÿòÉ¡ÿôΨÿôѯÿõÖ·ÿ÷ÛÁÿøáËÿúæÔÿûìÜÿûïãÿûðæÿüòèÿüôìÿýöïÿý÷òÿýùõÿþû÷ÿþûùÿþüûÿþýýÿøàÉÿﻇÿøãÌÿÓç÷ÿ.ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ~rgÿúóèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿô̦ÿð¼‰ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿùäÏÿîµ}ÿùæÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÝèïÿƒ’žÿ5=KÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿR?-ÿü¯ÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿñÕÿòÉŸÿý÷òÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýâÿÿÿUÿÿÿÿÿÿÛþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðåÿñÀÿõЬÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΩÿð¾ÿûñåÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñæÿí±vÿøâËÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿó̦ÿð¾ÿþýüÿþýûÿþú÷ÿýøóÿüõíÿûñçÿúíÞÿùçÕÿøâËÿ÷ÝÂÿöعÿõÓ±ÿóϪÿòË¢ÿòÆšÿñ“ÿñ½Œÿﺆÿî¸ÿî¶~ÿî´{ÿí²xÿí²wÿí²wÿí²wÿí´zÿï·ÿﻇÿð¿ÿòÅ™ÿóÊ£ÿôЬÿõÕ´ÿö×¹ÿ÷ÛÀÿøßÈÿóͧÿ︂ÿ÷Û¿ÿ]rÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ+ÿ£‰ÿÿýøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿñÁ“ÿòÅšÿÿýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿþüúÿöÚ¿ÿï·€ÿûïäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÑØãÿz€‹ÿ!,5ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ(ÿ¤‘ÿöñëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿð¼‰ÿõÓ²ÿýú÷ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÎúúú7óóóþþþéþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿð½ŒÿõÔ²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿóË£ÿñ“ÿüòéÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÝÿí°tÿùæÔÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþûøÿòÄ™ÿòÄ—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþýüÿþû÷ÿýøóÿýõîÿüòéÿûïãÿúëÜÿùæÓÿøáÊÿ÷ÛÁÿö׸ÿôѯÿôͨÿòÉ¡ÿòÄšÿñÁ’ÿð½Œÿﺆÿï·ÿî¶~ÿî´|ÿî³{ÿí³zÿí°tÿí®pÿɨÿ'ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ7-#ÿ½­—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿ﹄ÿôЭÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿþûøÿôÑ®ÿ'ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ»ÇÐÿdm{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿwi[ÿåÖÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿúíßÿ︃ÿ÷ÜÃÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿ¹ÿÿÿÿÿÿÿÿÿòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìßÿﻇÿõ×¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿòÇÿòÆšÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿùåÒÿí°uÿúëÞÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýùõÿð¾ŽÿóË£ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿýú÷ÿý÷ñÿüóëÿûðåÿúìÞÿùé×ÿùåÐÿøàÈÿöÙ»ÿñ¿ÿî´|ÿgoÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ?6,ÿʾ±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿí²yÿ÷ÛÀÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýùôÿòÈÿñÁ“ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðôüÿ«²ºÿNZdÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿQ@2ÿļ¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿùâÌÿ︂ÿùäÑÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¨ÿÿÿþþþöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿ﹄ÿöÛ¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿñÄ—ÿòÉ¡ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿ÷ÞÆÿí²xÿûñçÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿÿôÒ¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿôΩÿׯ¡ÿ&4BÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿS<3ÿÓȼÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÞÿí°tÿùæÓÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿð¿ŽÿóÊ¢ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÝäéÿ‹zÿ%)/ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ-!ÿ¤‘…ÿú÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö׸ÿﺆÿúìÞÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿ”ÿÿÿÿÿÿõþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿúéÚÿÿ÷ÞÄÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿñÁ’ÿôΨÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö×¹ÿîµ|ÿüöïÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüòèÿîµ~ÿ÷Ú¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿüõîÿòÈžÿˆŽ“ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZ=3ÿÜʾÿþýüÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÑÿí°tÿûïâÿþÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüðäÿ﹃ÿöÕ´ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿóÉ ÿÀ¥Šÿmv‡ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ|o]ÿðæÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÌ¥ÿñÀÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿôÿÿÿv÷÷÷$ýýýõþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúè×ÿî·ÿøáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿð¿ÿõÒ¯ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÑ­ÿÿýùõÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûìßÿí²yÿøâÌÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñçÿñ•ÿ==SÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿV3 ÿÖ¨€ÿôѯÿõÔ´ÿöغÿ÷ÜÂÿøáÊÿùåÒÿúéÙÿúìÞÿûîãÿûñèÿüõíÿýøóÿþüùÿþþþÿÿÿÿÿÿÿÿÿ÷ÞÅÿî´zÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿúêÙÿï¶}ÿ÷àÈÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿñ”ÿõѯÿîñúÿ²»Âÿ:K_ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿTF:ÿÓȾÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿñÖÿóÉŸÿý÷ñÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþàþþþRÿÿÿ0ÿÿÿ÷þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÑÿ︂ÿøäÐÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñæÿð¾ŒÿõÕ´ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóË¢ÿlÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùçÕÿí²wÿúéØÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûíàÿµ¦šÿ&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿH.ÿϘgÿﺅÿî¸ÿî¶ÿî¶~ÿî¶~ÿî¶ÿî·ÿ︃ÿﺇÿð½‹ÿðÀÿñÄ—ÿóÉŸÿôΨÿõÒ±ÿõÖ¸ÿöÛÀÿñÅ™ÿî´zÿøáËÿúéØÿûíàÿûñæÿüóêÿüõîÿýøóÿþûùÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøãÍÿîµ|ÿúêÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÛÿñ½Œÿ÷ÛÁÿÿÿÿÿþÿÿÿÙàçÿ~“ ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ4*ÿ¸¤’ÿÿýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿð½ŠÿõÓ²ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿËÿÿÿ,ÿÿÿ=ÿÿÿûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáËÿ︃ÿùèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿûíàÿð¼‰ÿöعÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÅ™ÿñ•ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿøâËÿí²wÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéØÿagsÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>3%ÿκ¦ÿûîâÿúëÜÿúè×ÿùåÐÿøáÉÿ÷ÜÂÿöØ»ÿõÔ´ÿôЭÿóͧÿòÉ ÿñĘÿñÀ’ÿð½Šÿ﹄ÿï¶ÿîµ}ÿîµ}ÿí¯qÿí®qÿï·ÿﺅÿð¼Šÿð¿ŽÿñÁ“ÿñĘÿòÈŸÿó̦ÿôÑ®ÿöÖ·ÿöÚ¾ÿ÷ÞÄÿøáÊÿùåÑÿúéÙÿûîáÿüòèÿýõîÿý÷ñÿýùôÿþûøÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿöÚ¾ÿï·ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùäÐÿð»ˆÿùåÒÿÿÿÿÿÿþþÿÿÿÿÿóúþÿÂÉÏÿGWiÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ}mÿúöîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéØÿ﹃ÿøÞÅÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿ·ÿÿÿ ÿÿÿÿÿÿGÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ÷ÝÄÿ﹄ÿúëÜÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿúéÙÿð»‡ÿ÷ÛÀÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿð¿ÿòÈžÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÜÂÿî´zÿüöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿêåÑÿ221ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ5)ÿǺ©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþýüÿþüùÿþúöÿýøòÿüõîÿüòèÿûîâÿúêÛÿúèÖÿùäÐÿ÷àÉÿïµ}ÿð¿ÿõÓ³ÿôÏ«ÿóË¥ÿòÈžÿòĘÿñÁ‘ÿð½‹ÿﺅÿï·€ÿî´|ÿí³zÿí´yÿîµ{ÿî¶ÿ︄ÿ)ÿð¿ÿñ•ÿñÅ™ÿòÈžÿóË¥ÿôÑ­ÿõÖ¶ÿöÚ¾ÿ÷ßÅÿøáËÿùåÑÿùéÙÿûîáÿüóêÿý÷òÿýú÷ÿþüúÿþýûÿþþþÿþüúÿôѯÿð¼‰ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿøßÇÿﺇÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâçìÿŽŸ®ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿdN?ÿëßÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøÞÆÿï·€ÿúèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýŸÿÿÿÿÿÿPÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿöÙ½ÿﺆÿûïâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÒÿﺅÿ÷ÞÆÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿﻇÿóΩÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿö×¹ÿî·ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ ©®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ)ÿ¹¥Œÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿî¶ÿõÕµÿýûøÿþúöÿýøóÿýöðÿüôìÿüòèÿûîâÿúëÛÿúçÕÿøãÏÿøàÉÿöÝÃÿöØ»ÿõÔ³ÿôЫÿóÊ£ÿòÆ›ÿñÕÿðÀÿjÿﺅÿï·ÿî¶}ÿî´{ÿí´zÿî´{ÿîµ~ÿÿðº‡ÿð¾Žÿñ”ÿñÆ›ÿóÉŸÿó̦ÿôЭÿõÓ²ÿð¼Šÿ﹄ÿ÷âÌÿùèÖÿúëÛÿûïâÿüóêÿýøòÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöغÿð½‹ÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷úýÿÆÏÕÿ6Rcÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ7.%ÿÓÅ«ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöÕµÿﺄÿûïâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþöýýý€ªªªüüüVþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿõÕ¶ÿﻉÿûòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÊÿ﹄ÿøâÌÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿî·€ÿõÕµÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþüûÿôѬÿﻇÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ[`zÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¢ˆzÿÿÿùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûòçÿí±vÿøáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþûùÿþùõÿý÷òÿüõîÿüóêÿüñæÿûîáÿûêÛÿùçÕÿùäÏÿøàÈÿ÷ÜÂÿöÙ¼ÿõÕµÿôЬÿóË£ÿòÆ›ÿñ“ÿð¾ÿ(ÿÿî·ÿî¶}ÿí®pÿì¯qÿîµ~ÿî¶ÿï¸ÿﺆÿð½ŒÿñÁ’ÿòÅ™ÿóÊ¡ÿóͧÿôÑ­ÿõÕµÿöÚ¿ÿ÷ßÈÿùåÑÿúêÚÿûíáÿûðæÿüôëÿýøòÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿôΪÿòÕÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâéíÿ}“¥ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¨—ˆÿø÷õÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÌ¥ÿñÀÿüóêÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýèÿÿÿbÿÿÿÿÿÿWÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿôÓ±ÿð½Œÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÂÿ﹄ÿùæÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôëÿî´{ÿ÷ÜÁÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿòÉ ÿðÀ‘ÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäöøÿ36:ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ~o`ÿÿøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéÙÿí°uÿúêÚÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿþþýÿþýûÿþûùÿýùõÿý÷òÿüõíÿüòéÿüðåÿûîàÿúëÛÿùçÕÿöÛ¿ÿî²xÿòÆ›ÿ÷Ú¾ÿõÔ´ÿôЭÿóˤÿòÆ›ÿñ“ÿð½‹ÿï¹…ÿî¸ÿî¶~ÿîµ}ÿîµ|ÿîµ}ÿï¶ÿï·€ÿ﹄ÿﻇÿð½‹ÿðÁ‘ÿòŘÿóÉ ÿóΨÿôѯÿõÖµÿöÚ¾ÿøàÈÿùæÒÿúëÜÿûñåÿüóêÿüõîÿýøòÿþû÷ÿþþýÿÿÿÿÿý÷òÿóÇžÿôϪÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöùüÿ¼ÇÒÿ#0Mÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ.ÿâÙËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿòÄ—ÿóÉ ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÛÿÿÿFÿÿÿÿÿÿYþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞÞÞÿµµµÿ£££ÿ§§§ÿ¾¾¾ÿëëëÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿôÑ­ÿðÀÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöÙ»ÿﺅÿúêÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïâÿî²wÿøäÎÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþú÷ÿñ“ÿòÆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¡¯Çÿ"ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿbI;ÿõêÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÉÿí²xÿüñæÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿúëÛÿîµ|ÿøàÉÿÿÿþÿþûøÿýùõÿýøòÿüõíÿüòéÿûðåÿûîàÿúëÛÿùçÖÿøãÏÿøßÈÿ÷ÛÀÿö׸ÿõÓ±ÿôϪÿóË£ÿòÆ›ÿñÁ’ÿð½Šÿ﹃ÿîµ~ÿî´{ÿî³yÿí´yÿî´{ÿïµ}ÿî·€ÿ﹃ÿﻇÿð½‹ÿñÁ’ÿñÅ™ÿóÉ¡ÿôЫÿó̦ÿï·ÿòĘÿøâÌÿùæÔÿúìÞÿüòèÿýöðÿýùõÿþûøÿþüúÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿàãëÿctŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿjE4ÿïçãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûòèÿð½‹ÿõÔ²ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýýýÌÿÿÿ+ÿÿÿüüübÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿáááÿrrrÿ"""ÿ ÿ ÿÿ ÿ ÿ ÿ///ÿyyyÿÉÉÉÿýùôÿóϪÿðÁ’ÿþùöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÕµÿð»ˆÿûìßÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéØÿí±tÿúêÛÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýøóÿﻈÿôΩÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿd{“ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ8/$ÿ×Ç´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõ׸ÿï·€ÿýöïÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøâÌÿî´|ÿúìÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþüúÿþûøÿýúöÿýùôÿý÷òÿýöîÿüóêÿüñåÿúíáÿúëÜÿúèÖÿùäÐÿøàÈÿ÷ÛÀÿöÖ·ÿôÑ®ÿóͦÿòÉŸÿñŘÿñÀ‘ÿð¼Šÿ﹃ÿîµ~ÿí²xÿì­oÿí¯rÿí²yÿî³{ÿîµ~ÿ︂ÿﻇÿð¾ŒÿñÁ’ÿñÅ™ÿóÊ¡ÿôÏ«ÿõÕ´ÿöÚ¾ÿ÷ÞÆÿîÝËÿž£¦ÿ &ÿÿÿÿÿÿÿÿÿÿÿÿ ÿð™ÿÿýùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿﺄÿ÷ÝÄÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýýý¶ÿÿÿÿÿÿÿÿÿoþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõõõÿqqqÿÿÿÿÿÿÿÿÿÿÿÿÿÿaQBÿ»—tÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÒ¯ÿð½ŠÿûîâÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøäÏÿí°tÿûðæÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýõíÿî¶ÿõÖ·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿóÿÿÿAHWÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ!ÿ°“~ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿóÌ¥ÿð¾ŒÿþùõÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿöÙ»ÿî¶ÿüóêÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþýÿþýüÿþüúÿþûøÿýùöÿýøôÿý÷ñÿýöîÿüóêÿûðæÿûîáÿûìÞÿõÓ³ÿîµ~ÿõÕµÿ÷ÝÄÿõÖ·ÿôЮÿóÌ¥ÿòÇœÿðÕÿð¿Žÿ(ÿÿî¶ÿî´{ÿî²xÿî²wÿí²wÿî³yÿÆ¡wÿB@DÿÿÿÿÿÿÿÿÿÿÿC/ÿßнÿûóêÿýøòÿþýûÿþÿÿÿÿÿÿÿÿÿÿÿøáÊÿﺆÿúéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿúýýý—þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÜÜÜÿ***ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ!!!ÿvvvÿÜÜÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿôΩÿñ¿ÿûðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÅÿí±vÿüõîÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüñæÿî³yÿ÷ÞÄÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿºÌîÿ%,;ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿteSÿÿÿûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ“ÿòÇœÿþûùÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþüûÿôΩÿﻇÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿöÙ½ÿð¼Šÿüóéÿþþýÿþûøÿýúöÿýøóÿý÷ñÿýõîÿüóêÿûðæÿûíáÿúëÛÿùçÕÿøãÏÿøàÉÿ÷ÛÀÿö׸ÿõÑ­ÿäÅ¥ÿyvnÿ ÿÿÿÿÿÿÿÿÿ n5ÿí±tÿî·€ÿﻆÿð¾ŒÿñÁ“ÿòÆšÿóˤÿð½Œÿî´{ÿôÓ±ÿøäÏÿùéÙÿúíáÿûðåÿüóêÿýøñÿþûøÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðþþþwÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚÚÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿCCCÿ¬¬¬ÿ÷÷÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿóˤÿñ•ÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöØ»ÿí³zÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûìßÿí±uÿùåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ£¸ÿ"ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿB5.ÿöÛÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿð¹ƒÿôЮÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþûùÿñÄ—ÿñÕÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúøÿôЭÿñÁ“ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþþþÿþþýÿþýüÿþýüÿþüúÿþûùÿþúöÿýøóÿý÷ðÿµÂÌÿ%6Cÿÿÿÿÿÿÿ0ÿÒ­ŠÿôЬÿóÊ¢ÿòŘÿð¿ÿð»†ÿï¸ÿîµ}ÿí°rÿì­oÿí±uÿí±wÿí²xÿî³zÿîµ}ÿï¸ÿﻇÿð¿ÿñÖÿóÈžÿô̦ÿõÑ®ÿö×·ÿ÷ÞÃÿùäÏÿúëÜÿûñæÿüõíÿý÷ðÿüøòãûøõTÿÿÿ ýýýžÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñññÿ"""ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŠŠŠÿíííÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿòÈžÿòÆšÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÒ°ÿî·ÿýùöÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúè×ÿí°tÿúëÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ^mŽÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ$ÿÀŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿî³zÿöÛÀÿþýüÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýøóÿﻇÿôÌ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿóÉ ÿóÉŸÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâèõÿ\kÿ ÿÿÿÿÿ‡jHÿôéÝÿþú÷ÿýùõÿýøòÿýöïÿüôëÿüòéÿúéØÿð¾ÿñÖÿ÷ÜÃÿ÷ÝÃÿöظÿõÓ°ÿôΨÿòÉ ÿñÖÿホÿð¹…ÿî¶~ÿî³yÿí²vÿí°uÿí°tÿí°uÿí±wÿí³zÿîµ}ÿ︂ÿﻇÔî•.ççç ÿÿÿªþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿaaaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿtttÿãããÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿñÅ—ÿóÊ¡ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóÌ¥ÿð½Šÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøâÍÿí±wÿüñèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëýÿÿCN]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿqbQÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïâÿí±vÿùåÐÿþþýÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüòéÿî¶~ÿöÖ¸ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüñèÿñÁ“ÿõÑ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿ’£µÿ )ÿÿÿ ÿƺ©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüñèÿð¾ŽÿõÔ³ÿýùõÿþýüÿþüúÿþüùÿþûøÿþúöÿýøóÿü÷ðÿüôìÿüòèÿûïãÿúëÜÿùçÓÿøáÊÿ÷ÛÀÿõÕ¶ÿôЭÿòË¢þòÇ›ÿð”Çç¢s ÿÿÿ ÿÿÿ¬ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍÍÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿsssÿâââÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿñ“ÿôΩÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÆšÿñ”ÿþûøÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ÷Û¿ÿî´|ÿüöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿºÒìÿ&5Dÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ9-&ÿøÛÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÑÿí²wÿúìÞÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúêÚÿî³zÿøáËÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûìÞÿð½‹ÿ÷Û¿ÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÑÝäÿ?G]ÿÿeG3ÿêߨÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúèØÿðº‡ÿ÷ÜÂÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþÿÿÿþþþÿÿþþÿþþþÿþþýÿþþýÿþýüÿþýüÿþüûÿþüùÿþúøÿþùõÿýøòºÿÿÿ ÿÿÿ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVVVÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿxxxÿåååÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñæÿð¿ŽÿôÒ°ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿñÀ‘ÿòÈŸÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿõÓ±ÿ﹄ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ™«¾ÿ)ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ±’rÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÚ¿ÿî¶~ÿûóéÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøáÉÿî´yÿûìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÐÿðº†ÿùæÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùÿÿÿisÿ·¬˜ÿÿýõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿøÞÅÿðº‡ÿùäÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþüÿÿÿžëëë ýýý·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöööÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ–––ÿìììÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíàÿð½Šÿö×·ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýúÿð¼‰ÿóÏ«ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿóÊ¢ÿð½Œÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿo‡Ÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿX;3ÿÿÿñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЬÿð»‰ÿýöñÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿöÕµÿï¶€ÿüöîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÛÀÿð»‡ÿûòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÔ³ÿð¾ŒÿûìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿýÿÿðþþþwÿÿÿÿÿÿÂþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¹¹¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ000ÿµµµÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿð¼‰ÿöÚ¼ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùöÿï¸ÿõÖ·ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿñ”ÿòÅ—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿW^}ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿγ™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿñÆšÿñÔÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿóË¢ÿ(ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúøÿõÒ°ÿð¿ŽÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿóË£ÿòÄ—ÿüòéÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþâûûûJÿÿÿýýýÐþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‹‹‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿfffÿÙÙÙÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùçÖÿﻇÿöÜÁÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ðÿïµ|ÿöÛÂÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿﻉÿóË£ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿáõþÿDRZÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿdN6ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð½‹ÿóÌ¥ÿþüùÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿñÁ‘ÿòÕÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿóË£ÿòÆ™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöðÿñÄ–ÿóÌ¥ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÔÿÿÿ òòòýýýáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿtttÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ   ÿïïïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿøäÐÿðº†ÿøßÆÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿí²yÿ÷ßÇÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿî¶~ÿõÒ°ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÕîÿ,;MÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿØÄ¦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿï·€ÿõÕ¶ÿþüûÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýùöÿ﹄ÿôͦÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüôìÿòŘÿôͧÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿñ¾ŒÿöÕ¶ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿýýýÅÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿrrrÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿbbbÿ×××ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÈÿﻇÿøâÍÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíßÿí²wÿøäÏÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþùõÿí±xÿöÙ¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¦´Îÿ#6ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿfP5ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿî´zÿ÷ßÅÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüóêÿîµ|ÿö×¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûðäÿñ¾ÿö×¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿùæÓÿﺅÿ÷߯ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýÿÿÿ§òòòýýýþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ………ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ000ÿ¯¯¯ÿöööÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÛÁÿﻈÿùåÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿùçÖÿí²xÿùèØÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüôíÿí°tÿøàÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŽ¢±ÿ !ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿØÄ¦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÚÿí²yÿùçÕÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúéÚÿí²xÿøâÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÛÿ﹄ÿøãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÄÿ﹃ÿúçÔÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÿÿÿ„ÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯¯¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿƒƒƒÿéééÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö׺ÿð½ŠÿúéØÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿøàÊÿî´{ÿúîàÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûîáÿí°sÿúçÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿr„žÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ^@0ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ßÇÿî´}ÿûîâÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿøßÆÿî³zÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùâÌÿï·ÿûíáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÕµÿ)ÿúìÞÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿëüüücÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿèèèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ]]]ÿØØØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿõÔ²ÿð¾ÿûìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÚ¾ÿî¶ÿûòèÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿùçÔÿî°uÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ`i„ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿѲ™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÔ³ÿﺄÿüóëÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþþÿõÔ²ÿî·ÿý÷ðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷Ù¾ÿðº†ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿó̦ÿñÕÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿãûûûC÷ïç ý÷òÿýøôÿýúöÿþûøÿþüúÿþýûÿþýüÿþþýÿþþýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ@@@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿBBBÿÅÅÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿôЬÿñÀÿûïäÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÓ²ÿﺅÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿøÞÅÿî³yÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîþÿÿSamÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿL1%ÿÿÿõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿóÉ¡ÿðÀÿý÷ñÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿþþþÿóÈžÿ*ÿÿýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôЬÿñÀ‘ÿÿýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿñÄ—ÿó̤ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýýýÔ÷÷÷#óÂ.óÆšÿòÊ£ÿôЬÿöÖ¶ÿ÷ÛÀÿøáÉÿùãÎÿùæÓÿúéØÿúíÞÿûðäÿüóêÿýöïÿý÷ñÿýøóÿýùõÿýú÷ÿµ³±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ000ÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿóͧÿñ•ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóͧÿð¾ŒÿýùôÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿöÕ¶ÿî·€ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚîÿÿCTaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ½xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ’ÿòÇœÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿñ¿ŽÿòŘÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöïÿòÇ›ÿóÊ¢ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿúîàÿð¾ŒÿõÕ¶ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿþÿÿÿ»ÿÿÿîÀŽ=ð¼ˆÿ︃ÿï¶ÿîµ|ÿî³zÿî³yÿî³yÿîµ|ÿï·ÿ﹄ÿð¼ŠÿðÀÿñÄ–ÿòÇÿóˤÿôϬÿõÔ´ÿöÙ¼ÿF>8ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ$$$ÿ©©©ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿóÊ¢ÿñŘÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÇÿñÖÿýúöÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿôͧÿ(ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÆßôÿ2FYÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ* ÿÿóÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿﻆÿôЬÿþûùÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøõÿ﹃ÿôΩÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿüñçÿð¾ŒÿõÖ¶ÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿùåÒÿﺆÿ÷ÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿøýýýšûñëMüóéÿûîàÿúèØÿøãÎÿ÷ÞÅÿöÙ½ÿõÕ·ÿõѯÿóͨÿòÉ ÿòÅ™ÿñÁ“ÿð¾ÿð»‰ÿï¹…ÿï·‚ÿî¶~ÿîµ|ÿÄ”dÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ£££ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿòÇÿòÈžÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ”ÿóÉŸÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿñÅ™ÿñ“ÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ»Ëçÿ)6Mÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ~T?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿî¶~ÿöÙ¼ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿîµ{ÿöÙ½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿûîâÿ︂ÿøáËÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÃÿﺇÿùæÓÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÿÿÿvÿÿÿÿÿÿ\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþýûÿþúöÿý÷ñÿüôëÿûñæÿûíàÿúéÙÿøåÐÿ÷àÇÿ÷Û¿ÿ©“~ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¥¥¥ÿýýýÿÿÿÿÿÿÿÿÿýöïÿñĘÿóˤÿý÷ñÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿð¾ŒÿóΨÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþþýÿð¿ÿóÈžÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ±½Òÿ *;ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×¹œÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðäÿî´{ÿøâËÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùé×ÿí²xÿùåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿîµ}ÿúêÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿõÔ³ÿñ¿ŽÿûíàÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýéÿÿÿLÿÿÿÿÿÿhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯¯¯ÿ)))ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ­««ÿþýüÿÿÿÿÿüóêÿñ“ÿôЬÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúõÿï¹…ÿõÔ²ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþýÿ﹄ÿôΪÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŸ°¾ÿ,ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ/ÿÿüêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøäÑÿî´|ÿúéÙÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÄÿî´zÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøáÊÿî¶~ÿüòêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿóÌ¥ÿòÅ™ÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿÿÿÿáÿÿÿ#ÿÿÿþþþpÿÿÿÿýýýþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÈÈÈÿdddÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¹¤ÿøàÉÿöÙ¼ÿﺅÿóÊ¡ÿúëÛÿûñæÿüòéÿüôìÿýöïÿýøôÿþú÷ÿþýûÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿî¶ÿöÚ½ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿî´|ÿõÖ·ÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ–§·ÿ %ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿzS=ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÙ½ÿ︂ÿûðäÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿõÓ±ÿî·€ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÕ¶ÿð¼‰ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüõíÿòÅ™ÿó̦ÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÙÿÿÿÿÿÿrþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëëëÿ¶¶¶ÿkkkÿ$$$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ'ÿÆ—hÿî´{ÿí®qÿî´zÿð¼ŠÿñÀÿñÔÿòÆšÿóÊ ÿôΨÿõÓ°ÿö×¹ÿ÷ÛÁÿøßÇÿøáÌÿùåÑÿúè×ÿûëÝÿûïäÿüóéÿüõîÿý÷ðÿýøôÿþû÷ÿþüûÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñæÿî´{ÿ÷àÉÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöïÿí±vÿ÷ÝÄÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ—¨¸ÿ %ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿʧƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôϪÿkÿüõìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿòÈžÿð¾ŒÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿóÊ¢ÿòÅšÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûîáÿðÀÿõÔ³ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÅÿÿÿÿÿÿtþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíííÿÓÓÓÿ³³³ÿxxxÿ333ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ<5.ÿÞº•ÿî³yÿð¿ŽÿóÊ ÿòÆšÿòÕÿñÀÿð½‹ÿﺆÿ﹂ÿî¶ÿïµ|ÿï´|ÿîµ}ÿï·ÿð¹…ÿð¼ŠÿñÀÿñÖÿòÇœÿóÉ¡ÿó̧ÿôÑ®ÿõÕ¶ÿöÚ¾ÿ÷ÞÅÿøâÌÿùåÑÿúçÖÿúëÜÿûïâÿüòèÿüõîÿý÷òÿýùõÿþûøÿþüûÿÿÿÿÿúìÞÿí³xÿúéÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðäÿí°sÿùåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿˆ¯ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿòÆšÿñÄ–ÿýøóÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿð¿ŽÿòÇÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüôìÿñ¿‘ÿõÑ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÒÿð¼‰ÿ÷ÜÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿùýýýžÌÌÌýýý€þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñññÿßßßÿ¾¾¾ÿxxxÿ###ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ`YRÿè´ÿ÷ÜÁÿýùôÿüõïÿüóëÿüðæÿûíàÿúéÙÿùåÑÿøáËÿøÝÄÿ÷Û¿ÿö׸ÿõÓ±ÿôΩÿóÊ¡ÿòÆ›ÿñ•ÿñÀÿð½‹ÿﻇÿ﹃ÿï¶€ÿîµ~ÿîµ}ÿîµ}ÿï¶ÿ︂ÿﻇÿð¾Žÿñ•ÿòÆ›ÿóÉ¡ÿôͧÿôЭÿöÔ³ÿ÷Ú¾ÿôÏ«ÿí¯rÿöØ»ÿùçÕÿúêÛÿûíàÿüñçÿüôíÿýøòÿýúöÿþûøÿþüûÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùéØÿí°sÿúìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿy“©ÿ$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿQ3ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ¿Žÿóˤÿýúöÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿ︂ÿõÓ±ÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüñçÿ﹄ÿ÷ÝÄÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÜÂÿð¼‰ÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÿÿÿmÔÔÔýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòòòÿÞÞÞÿ«««ÿKKKÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‘qPÿõßÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþüûÿýú÷ÿý÷òÿüõíÿüòéÿûðäÿûîàÿúëÚÿùæÓÿøâËÿ÷ÞÅÿ÷Ú¾ÿö×¹ÿõÔ³ÿôЬÿóˤÿòÇœÿòÕÿð¿Žÿð¼‰ÿðº†ÿ︃ÿï·€ÿï·€ÿî²xÿì¬nÿîµ|ÿ︂ÿﺆÿñ½‹ÿñÁ‘ÿòÄ™ÿôÉ ÿô̦ÿôЫÿõÓ²ÿö׸ÿ÷ÛÀÿ÷ßÈÿùäÐÿùèÖÿúêÛÿúíàÿûñæÿüôìÿýøòÿýûøÿþýûÿþþýÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâËÿî±vÿüòéÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿw‘©ÿ%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ™kTÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿï¹…ÿõÔ³ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïäÿî³yÿ÷ÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿïµ}ÿúéÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿôÔ²ÿðÀÿûîàÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýþÿÿÿÿÿÿÿêÿÿÿ;þþþÿÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿïïïÿÁ´©ÿ]H3ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿͼ¬ÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþýüÿþüúÿþú÷ÿýøòÿüõíÿüòèÿûïäÿûíßÿúëÛÿúçÕÿøãÎÿøáÊÿòÆ›ÿí±vÿôЫÿôÑ®ÿôͧÿòÈŸÿòÄ–ÿð¿ÿñ¼‰ÿ﹄ÿï·ÿï¶ÿî¶ÿî¶~ÿî¶ÿï·ÿ︃ÿﺆÿð½ŠÿñÀÿòÖÿòÈžÿóÌ¥ÿôЫÿõÓ±ÿöÖ·ÿ÷Ú¿ÿ÷߯ÿøäÎÿúèÖÿúëÜÿúîâÿüñæÿüôìÿý÷òÿþûøÿþþýÿÿÿÿÿ÷ÛÁÿîµ|ÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿw‘©ÿ%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛº“ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿî¶ÿ÷ÝÂÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúèÕÿí²wÿúè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøâÍÿïµ}ÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿóÌ¥ÿòÆšÿüôìÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýâÿÿÿßßßÿÿÿ°ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿùçÕÿä°{ÿ̺¨ÿiiiÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ951ÿøøøÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÕµÿï·ÿüóëÿþû÷ÿýøóÿüõîÿüóéÿûðåÿûîàÿúëÛÿúé×ÿùåÑÿøàÊÿ÷ÝÂÿöØ»ÿõÕ´ÿôÑ®ÿôΨÿóÉ¡ÿòÅ™ÿñÁ’ÿð½Šÿﺅÿï·€ÿî¶~ÿîµ}ÿîµ}ÿï¶~ÿî·€ÿ﹃ÿð»†ÿð½Šÿñ¿ÿñ•ÿòÆ›ÿóË£ÿôΪÿõÒ±ÿñÁ’ÿî³yÿöÜÁÿøâÍÿùçÕÿúìÝÿûðäÿüòéÿüõîÿýøòÿþú÷ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿw‘©ÿ%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿî¶~ÿùåÑÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøÞÄÿí³zÿüðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿöؼÿð¹„ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôëÿòÅ™ÿôͧÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÎÿÿÿ ÿÿÿ¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøãÏÿî·ÿùçÔÿùùùÿÓÒÓÿXXXÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒŒŒÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿôÏ«ÿﻈÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþüúÿþûøÿýúöÿýøóÿýöïÿüôëÿüñæÿûîáÿúìÝÿúéÙÿùæÔÿøãÍÿ÷ÞÅÿöÙ½ÿõÕµÿôÑ®ÿóͨÿóÊ¡ÿòÅ›ÿñ”ÿð¿ÿð»‡ÿï¸ÿïµ~ÿí°sÿí­pÿîµ|ÿî·€ÿ︃ÿðº‡ÿð½‹ÿñ¿ÿñ“ÿñÆ™ÿóÉ ÿóͧÿõÑ®ÿöÕ¶ÿ÷Ù½ÿ÷ÝÄÿøâÌÿùæÔÿúëÜÿûïäÿüôëÿýöïÿýøóÿýú÷ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿw‘©ÿ%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿBÿÿÿõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ßÇÿï·ÿûìÝÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõÒ±ÿ︂ÿüöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôΩÿòÁ‘ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûíßÿð¿ÿõÕ´ÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýûÿÿÿªâââ þþþÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøàÊÿï·ÿúêÛÿÿÿÿÿÿÿþÿýýýÿ¾¾¾ÿ222ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿßßßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÊ¡ÿñÀ‘ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþüúÿþûøÿýùõÿýøóÿýöðÿüôìÿüòçÿûïâÿúëÝÿúèØÿúæÓÿ)ÿ(ÿ÷ÜÁÿöÖ·ÿôѯÿóͦÿóÉŸÿòÅšÿñ”ÿð¿ÿð»ˆÿ︃ÿï¶~ÿî´{ÿî´{ÿîµ|ÿîµ}ÿï·€ÿ﹄ÿð¼‰ÿðÀÿñÁ“ÿòĘÿòÈžÿóÌ¥ÿôЭÿõÖ¶ÿöÚ¾ÿ÷ÝÄÿøáËÿùåÒÿúëÛÿûïãÿüóëÿý÷ñÿýùõÿv¦ÿ%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ^>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÔ´ÿﻇÿûñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþüÿòÇÿðÀÿýûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿý÷ñÿòĘÿôË£ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿùæÓÿﻇÿ÷ÝÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýöÿÿÿ„ÿÿÿ ÿÿÿÆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÞÅÿï·ÿûîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿ‰‰‰ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿUTUÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòĘÿòÆœÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿð¾ÿóË£ÿÿýýÿþûøÿýùõÿýøòÿýöïÿüõíÿüóêÿûðäÿúíÞÿúéØÿùåÒÿùãÍÿøàÉÿ÷ÝÂÿö׺ÿõÒ°ÿóͧÿóÈžÿòÄ—ÿñÀ‘ÿð¾Œÿﻇÿ︂ÿî¶ÿîµ|ÿî´|ÿî´{ÿî´}ÿï¶ÿ︃ÿð¼‡ÿð¾ŒÿñÂ’ÿòÄ—ÿqx{ÿ%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿmX9ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿóË£ÿðÀÿüöîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿð½‹ÿóÊ¢ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿð»‰ÿö×¹ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÅÿﺆÿùåÒÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿòÿÿÿ^ÿÿÿ ÿÿÿÉþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷ÜÂÿ︂ÿüñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙÙÙÿ555ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÅÅÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿñÀÿóͧÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿþùöÿ︂ÿõÓ±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþþÿþþýÿþýüÿþüûÿþûøÿýùöÿýøóÿýöðÿüõíÿüôëÿüòèÿûîâÿúêÛÿùæÔÿøãÍÿ÷àÇÿ÷ÝÃÿöÙ¼ÿõÓ³ÿóΩÿóÉŸÿòÄ—ÿñÀÿð¼‰ÿpqpÿ%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿueIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿñÖÿòÇœÿýøóÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿï¶ÿõÖ¶ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿúìßÿîµ~ÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿõÕµÿð¾ÿûíßÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿëúúú9îîîþþþÏþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿöÛ¿ÿ﹄ÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿuuuÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ===ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿð»‡ÿõÓ³ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôíÿî³zÿöÛÀÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþýüÿþýûÿþüúÿþûùÿþúöÿýøôÿý÷ñÿýöïÿüôìÿüóêÿuŠœÿ%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¦wcÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð½ŒÿóÏ«ÿýúöÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúîáÿî³xÿøâÊÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿøãÏÿî³{ÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿóÌ¥ÿòŘÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÙÿÿÿÿÿÿÿÿÿØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿöعÿﻇÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ­­­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ½½½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿï·‚ÿöÚ½ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿí±uÿùãÎÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿw“§ÿ$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¶TÿøäÏÿúéÙÿûïâÿüòèÿüôíÿý÷òÿþú÷ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿ︄ÿöغÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÔÿí²wÿùêÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿöÙ¼ÿï·€ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿñÄ—ÿóͧÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþüÿÿÿ»õõõÿÿÿäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿõÓ²ÿð½‹ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×××ÿ"""ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿCCCÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿî¶~ÿ÷ÞÄÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿí°sÿûêÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿ–¦µÿ #ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÂ8ÿí³zÿî´|ÿï¶ÿ︃ÿð»‡ÿð½ÿñ”ÿòÆ›ÿòÊ£ÿôϪÿôÓ²ÿö׺ÿ÷ÝÄÿøãÍÿùéØÿûîáÿüóêÿýöïÿý÷ñÿýùöÿþüúÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïäÿî¶€ÿ÷àÉÿþýüÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÛÁÿî´{ÿûñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõѯÿð½‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûìÝÿð½ŠÿõÖ¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýùÿÿÿ–ÿÿÿýýýñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôÏ«ÿðÀÿýû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿéééÿ111ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÒÒÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïâÿî´|ÿøâËÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÐÿì°sÿüñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ–¦´ÿ #ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿݰÿö×¹ÿôÒ¯ÿóͦÿòÉŸÿñĘÿðÁÿð¼Šÿ﹄ÿï¶ÿî³{ÿî²xÿí²wÿî²xÿî²yÿî´{ÿï¶~ÿð¸‚ÿð»†ÿñ½Œÿñ“ÿòÆ›ÿóˤÿôЬÿõÕµÿöÙ½ÿ÷ÞÅÿøãÎÿùéØÿûîâÿüóëÿþú÷ÿøâÌÿï¶€ÿùèÖÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôЭÿ﹄ÿüöñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿýùõÿòÈžÿòÇ›ÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿùæÓÿï¹…ÿøÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþöÿÿÿlÿÿÿ ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿóË£ÿñÕÿþýúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòòòÿ777ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿfffÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéÙÿî´|ÿùæÒÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÈÿí±vÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¦´ºÿ!%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâÄ¢ÿþüúÿþûùÿþûøÿþûøÿþùõÿý÷ñÿüôëÿûðåÿúíßÿúêÚÿùçÖÿøãÎÿ÷ÞÅÿöغÿõÒ¯ÿóÌ¥ÿòÇœÿñÔÿð¿Žÿð¼ˆÿð¹‚ÿï¶~ÿî´{ÿî²xÿí²vÿî²vÿî²xÿî³zÿîµ}ÿï¸ÿð¼ˆÿï·€ÿí¯rÿðÁ’ÿóˤÿõÑ®ÿöÖ¸ÿ÷ÛÀÿøàÉÿùäÐÿúéØÿûîáÿüóëÿýøòÿýüùÿþýüÿþþýÿþþþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿòÅ™ÿñ“ÿýüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿý÷ñÿð½ŒÿõÓ±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÆÿﻇÿùæÓÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÿÿÿCÿÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ðÿòÇœÿòÆ›ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïïïÿ666ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿøãÎÿîµ}ÿúêÚÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöØ»ÿîµ}ÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿªµ½ÿ!&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãÅ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþþÿþþþÿþþþÿþþýÿþþýÿþýýÿþýüÿþýûÿþüúÿþüúÿþûùÿþûøÿýùõÿüöïÿûòèÿúîâÿúêÛÿùçÔÿøãÏÿ÷ÞÆÿöÙ¼ÿôÒ±ÿó̦ÿòÇ›ÿñÕÿî´|ÿí¯rÿîµ~ÿîµ}ÿí´yÿí²xÿî±vÿî±wÿî²vÿî³yÿîµ{ÿî·ÿﺆÿð½‹ÿðÁ‘ÿòÅšÿóË£ÿõЭÿö׸ÿ÷ÜÃÿøâÌÿùçÔÿúëÛÿûïâÿüóêÿý÷òÿþûùÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýû÷ÿð¼‰ÿóÌ¥ÿÿþýÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòçÿïµ}ÿøáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿöÕ¶ÿñ¿ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿÿÿÿðÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöïÿñÄ—ÿóÉ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäääÿ&&&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¦¦¦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿ÷ÝÃÿî·ÿûîáÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿôϬÿð»†ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿ·¾Øÿ$'9ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãÅ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿþþþÿþþýÿþþýÿþýýÿþýüÿþýûÿþýúÿþüúÿÿÿÿÿòÈžÿñ“ÿúìÞÿûðäÿúêÜÿùæÔÿøâÌÿ÷ÞÅÿöÙ¼ÿõÓ³ÿôΨÿóÈžÿñ”ÿð¾Œÿﺅÿï·€ÿîµ|ÿí³yÿí²wÿî±vÿî±vÿî²wÿî³xÿî´|ÿî·€ÿﺅÿð½‹ÿñÁ‘ÿòÅ™ÿóÉ¡ÿôЫÿöÖ¶ÿ÷ÜÁÿùâÍÿúèÖÿúìÞÿûðäÿúìÜÿîµ|ÿöÖ¶ÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúéÙÿî²wÿûîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿó̦ÿòĘÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿäÿÿÿ&ÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿñÁ“ÿô̦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍÍÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿNNNÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÖ·ÿﺇÿûòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÇžÿñÁÿÿýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿºÊÛÿ'1<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãÅ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ“ÿóˤÿýøóÿÿÿÿÿþþþÿþþþÿþþþÿþþþÿþþýÿþýüÿþüúÿþúùÿýúöÿýùõÿýøóÿüôíÿüðåÿúëÜÿùæÒÿøàÉÿ÷ÜÁÿöغÿõÓ±ÿóͨÿòÈžÿñÕÿð¾Œÿﺅÿî·€ÿî´|ÿî³yÿí²wÿí±vÿî±uÿî²wÿî³xÿï´{ÿïµ}ÿí®oÿï·€ÿñ”ÿòÆšÿóÊ£ÿôЫÿõÖ¶ÿ÷ÜÁÿøâÌÿúèÖÿúíàÿûðäÿüòéÿüõîÿýøôÿþûùÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøßÉÿî³zÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüóêÿòŘÿó̤ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýýÿÿÿÄÿÿÿ2þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿüôìÿð¿ÿôЬÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôЬÿð¾ÿýõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿðÀÿóÇÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÄÕßÿ/;AÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãÅ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿþÿÿÿÿÿÿýúøÿ*ÿõÔ²ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿþþÿÿþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿÿýûÿþûøÿýùõÿý÷òÿüöïÿýôìÿüñæÿúëÜÿùæÓÿøàÉÿ÷Ú¾ÿõÕ¶ÿõÑ­ÿô̦ÿñ¿ÿí®pÿﺅÿﺅÿî¶€ÿî´{ÿî²xÿí±vÿí°uÿî±vÿí²wÿî³xÿï´|ÿï¸ÿð»‡ÿñ¾ŽÿñÖÿòÈžÿóͦÿôÑ®ÿö×·ÿ÷ÜÁÿøáÌÿùè×ÿúíàÿûòçÿüóëÿüõïÿýøòÿþúöÿýüúÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿöÔµÿﺅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûìÞÿð¿ÿõÔ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûÿÿÿ“ÿÿÿÿÿÿAþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüóéÿð½‹ÿõÓ²ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøøøÿ]]]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¸¸¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÊ¢ÿñÕÿý÷ñÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿﺅÿôΪÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿßàÜÿFC@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãÅ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôëÿ﹃ÿ÷ÜÁÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÙ»ÿîµ|ÿûîáÿýôìÿüòèÿüðäÿûìÝÿùçÓÿ÷ßÈÿ÷Ù½ÿõÔ³ÿóΩÿòÊ¡ÿñÆšÿñÁ’ÿð¾‹ÿﺄÿï·ÿî´{ÿî²xÿî±vÿî±vÿí°vÿí²wÿî³yÿî´|ÿï·€ÿð»ˆÿð¿ÿñĘÿóÉ ÿôΩÿõÓ²ÿöØ»ÿ÷ÝÃÿøãÌÿùèÖÿûëÜÿòÅ™ÿñÔÿþüùÿýùôÿýú÷ÿþûùÿþüûÿþýýÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿÿþþÿÿþþÿÿÿþÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÐÿ(ÿ÷ÞÆÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿÿÿÿøÿÿÿ\ÿÿÿQÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿð»‡ÿö׺ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿØØØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿvvvÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÅ™ÿóÈžÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿî´{ÿö×¹ÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿïåÐÿSKFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãÅ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÛÿ︂ÿøãÎÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóΨÿï»…ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿýûùÿýøóÿýõíÿûñçÿûîâÿúëÜÿùæÔÿøàÉÿöÙ½ÿõÓ³ÿôΨÿòÉ ÿòÅ—ÿðÀÿð¼Šÿ﹄ÿï¶~ÿï´{ÿî²wÿî±wÿî±uÿí±uÿí²wÿî²yÿì¯qÿî²wÿﻈÿð¿ÿñĘÿóÉ¡ÿôϬÿõÕµÿöÚ¿ÿ÷߯ÿøãÍÿùèÖÿûíßÿüòçÿýöïÿýùõÿþú÷ÿþûøÿþüùÿþüúÿþýûÿþýýÿþþýÿþþýÿþþþÿþþþÿþþþÿþþþÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ÷ÜÂÿ)ÿùè×ÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýõþþþ)ÿÿÿüüüaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíàÿ﹄ÿ÷ÜÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ:::ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿðÁ’ÿó̦ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ðÿí°uÿøßÆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÝÄÿ]T[ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãŦÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøàÊÿ﹃ÿúêÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÕÿñ”ÿþýûÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿýùõÿüöîÿûñèÿûîáÿúêÛÿùæÔÿøáÉÿöÛ¿ÿõÕ´ÿóÌ¥ÿì¯qÿð¼ˆÿñÁ‘ÿð½Šÿ﹄ÿï¶ÿî´{ÿî²xÿî±wÿî±vÿí±vÿî²xÿî³zÿî¶}ÿï·‚ÿðº‡ÿñ¾ŽÿñÄ–ÿòÊ ÿóЫÿõÖ¶ÿ÷ÛÀÿøàÉÿùäÐÿúèÖÿûíÞÿûñåÿýõìÿýøóÿþúøÿþüùÿþüúÿþüúÿþýûÿþýüÿþþþÿýúöÿõÓ³ÿñ¿ÿûñæÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþþþÿþþþïÌÌÌÿÿÿþþþqÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÛÿî¸ÿøáÈÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞÞÞÿ"""ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýû÷ÿð½ŒÿôÒ®ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòçÿì¯sÿùåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿõ×¹ÿhgjÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿáÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõ×¹ÿð¼ˆÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿﻆÿó̦ÿþþþÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôëÿî°tÿúéÙÿÿÿÿÿþú÷ÿýöïÿüñçÿúíßÿùè×ÿùåÐÿøàÉÿ÷Ú¿ÿõÕµÿôÏ«ÿòÉ¡ÿòĘÿñÀÿð½Šÿï¹…ÿî·€ÿî´|ÿî²yÿî²wÿî±vÿî±wÿî³yÿî´{ÿî¶ÿ﹄ÿð»‰ÿñ¿ÿòÖÿóÉŸÿôΩÿöÕµÿ÷Û¿ÿøáËÿ÷áÊÿñŘÿðÀÿùéÙÿüóëÿüöðÿýùõÿþû÷ÿþûøÿþûùÿþüúÿþüûÿþýüÿþýýÿþþýÿþþýÿþþþÿþþþÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÓÿÿÿüüü}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿùè×ÿî¶ÿùäÐÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöööÿ†††ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÖÖÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿﺅÿõ׸ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûëÝÿì¯sÿúëÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþú÷ÿôЭÿ€ypÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓ¯‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóϪÿñÀ‘ÿüòéÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿî¶~ÿõ×¹ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþþýÿùçÕÿí°uÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþýýÿþýûÿþüúÿþúöÿýöðÿüñèÿûìÞÿùçÕÿøâÌÿ÷ÞÅÿöÙ½ÿõÔ´ÿôϪÿóÊ¡ÿòÅ™ÿñÀÿð½‹ÿðº…ÿî¸ÿîµ}ÿî´zÿî²xÿî±wÿí°vÿí­pÿí°tÿï·€ÿﺅÿð½‹ÿñÁ’ÿòŘÿóÉ ÿôΩÿõÔ³ÿöÚ¾ÿøàÈÿùåÒÿúéØÿúëÛÿûîáÿûñçÿüôìÿý÷òÿýùöÿýùöýýú÷«ªªªýýý„þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿùæÔÿí¶}ÿùèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÊÊÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¯¯¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿî·€ÿ÷ÝÃÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùãÎÿí±vÿüñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿóÉ¡ÿ—ˆzÿ*ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÆštÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÇœÿòÇÿýöðÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìÝÿî³yÿøãÍÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷Ù¾ÿï¶ÿþû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþýüÿýüùÿþùöÿþøóÿýöïÿüòçÿûìÞÿùçÔÿøáËÿ÷ÝÃÿôÏ©ÿîµ|ÿð¾ŒÿóË£ÿòÅ™ÿñÁ’ÿð¾Œÿﻆÿï¸ÿï¶~ÿî´{ÿî³yÿî²xÿî²xÿî³yÿï´}ÿï·ÿﺆÿð¿ÿñ•ÿòÆ›ÿóÊ£üóÏ«€ªªªÿÿÿ‡þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùåÐÿîµ}ÿúëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâââÿDDDÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŽŽŽÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîàÿîµ}ÿùãÎÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÚ¾ÿï´}ÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿý÷òÿòÕÿ¦š•ÿ ,<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÉwÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿñÀÿôÏ«ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÊÿî³yÿûíßÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿôË¥ÿñÁ’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùéØÿ'ÿ÷ßÇÿÿÿÿÿþûùÿýùôÿü÷ðÿüôíÿüñçÿûìßÿúçÕÿøáËÿ÷ÜÁÿö׸ÿõÓ°ÿôΩÿóÊ¡ÿòÅ™ÿðÁ’ÿð¾Œÿﻆÿï·‚úì²wSÿÿÿýýý’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿøâÍÿî¶}ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóóóÿ~~~ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿtttÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿî´{ÿúéØÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôѯÿ﹄ÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýóëÿð½Œÿ¸µ°ÿ.?PÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÄ–tÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöïÿﻉÿö×¹ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿõÕ¶ÿî¶~ÿüõîÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþû÷ÿñ¿ŽÿôΩÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ÷ÝÃÿﺆÿùè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿýùõÿü÷ïÿûòêþúñæðùéÙ/¿¿¿ýýý¡þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøßÇÿî¶ÿûñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¨¨¨ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ___ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÍÿî´{ÿûíáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÉ ÿð¿Žÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûïäÿ﹄ÿÕÏÀÿAPZÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯iÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿï¹…ÿ÷ÞÆÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿóÊ£ÿð»‡ÿýûøÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿïµ~ÿ÷ÛÀÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿõÔ´ÿð¾ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÙÿÿÿÿÿÿýýý±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿ÷ÛÀÿ︃ÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¿¿¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿQQQÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿ÷ÞÅÿîµ}ÿûðæÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÁ’ÿñÅ™ÿÿýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúëÜÿî·ÿíßÈÿR[mÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¢u`ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùæÓÿ﹃ÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ“ÿòÕÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿüõîÿí¯tÿúèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ðÿóË£ÿòÅ™ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýý´ÿÿÿÿÿÿÂþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿõ׸ÿð»†ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇÇÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿIIIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÙ»ÿÿüòèÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿﺇÿóˤÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿùåÒÿï¶}ÿùçÔÿ\sŽÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿdIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿ÷ÝÄÿﻇÿúëÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿﻇÿóͨÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúëÜÿí¯rÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüòéÿñ“ÿôͧÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿŒÔÔÔþþþÑþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿôÓ°ÿð½‹ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÈÈÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõÓ±ÿ(ÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîµ~ÿôÓ°ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøáÉÿî¶~ÿûíàÿ|•¨ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿhM.ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÔ´ÿð¾ÿûïäÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýôëÿî¶~ÿöÙ¼ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿ÷߯ÿî³yÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûíáÿﻇÿöÖ¶ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþeÿÿÿýýýÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôΩÿðÀÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÅÅÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿKKKÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóΧÿñÀ‘ÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿí±wÿöÚ½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿöÛÀÿï¸ÿüòèÿœ«¾ÿ)ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿP/ÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÌ¥ÿòÄ—ÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÙÿî³{ÿùäÐÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþýüÿôЮÿð¼‰ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúçÖÿ︂ÿ÷߯ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþÿÿÿ<ÿÿÿýýýÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøôÿóË£ÿñÕÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¸¸¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVVVÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÈžÿòÅšÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿí°tÿøáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþüùÿõÔ³ÿð»‡ÿüöðÿ¯Éãÿ!/?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ9ÿÿýïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿñĘÿóˤÿý÷ñÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷߯ÿî´{ÿûîáÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþüúÿòÖÿóÈžÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÞÆÿﺅÿùéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿßßßÿÿÿÞþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿòÈžÿòÆšÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿ™™™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿgggÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýÿòÖÿóˤÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿí°sÿùèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿóͦÿñ¿ÿýú÷ÿÖîÿÿ8FPÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýóÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿð¿ŽÿõÓ±ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿõÓ²ÿï·€ÿýöïÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿýùöÿ﹄ÿöÖ·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿõÔ´ÿð½Œÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþàþþþýýýáþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿý÷ñÿñÅšÿòÉ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìììÿhhhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ~~~ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿñ¿ŽÿõÑ®ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÔÿí°uÿúîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýøôÿòÅ™ÿòÅ™ÿþýýÿøÿÿÿKRnÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÜ¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿ(ÿ÷Û¾ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóÉ ÿð½Šÿþûøÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüóêÿí±wÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýöðÿóÊ¡ÿòÄ—ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýýý¶ÿÿÿÿÿÿæþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿðÔÿóÌ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛÛÛÿ)))ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿšššÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùóÿ(ÿöÖ·ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÅÿí³zÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿñ¿Žÿô̦ÿÿÿÿÿÿÿÿÿcz”ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞ»˜ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿﺆÿøáÊÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ‘ÿòÆšÿþüúÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúéÙÿí®rÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüòêÿñÁ‘ÿóͦÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿ€ÿÿÿ"þþþíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿð¿ŽÿôЬÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¶¶¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ½½½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿ﹄ÿ÷Ú¾ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÖ¶ÿî¸ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüòçÿﺅÿõÕ´ÿÿÿÿÿþÿÿÿŠŸ«ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¼“tÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøãÎÿﻆÿùæÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿð»†ÿôЭÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿøßÇÿî±uÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíàÿð»ˆÿö׸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿHò—*òÈŸöôͦÿôЭÿõÖ¶ÿ÷Ú¿ÿøßÈÿùåÑÿúéÙÿûíàÿûðæÿüôíÿýùôÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüòéÿð¼‰ÿõÔ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìììÿ]]]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿçççÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿÿ÷ÞÅÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΪÿ)ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúíàÿî·€ÿ÷ÝÂÿÿÿÿÿÿÿÿÿ¨¼Ýÿ&7ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒoUÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöÚ¿ÿð½‹ÿúìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿï¶~ÿ÷ÛÀÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿõÕ¶ÿ︂ÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿùæÓÿ﹄ÿøâÌÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿî•.ñÁ‘ÿð¾Œÿﻇÿ﹄ÿï·‚ÿï¶ÿï¶~ÿï¶ÿï·€ÿ︂ÿðº‡ÿñ¾ÿñ”ÿòÇœÿóÊ£ÿôΪÿõÓ²ÿöغÿ÷ÞÄÿøãÏÿúéØÿûíàÿûðåÿüóêÿý÷ñÿþûøÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿﺅÿöÙ½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿËËËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÆÆÆÿpppÿ;84ÿ&ÿ$!ÿ%%%ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ&&&ÿ)))ÿ>>>ÿtttÿÑÑÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿòÇÿñ“ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùè×ÿïµ|ÿøåÐÿÿÿÿÿÿþþÿÕíÿÿ3?Gÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ7)ÿ©›—ÿÃÀÀÿÞÛØÿñïíÿýüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôѯÿñÁ’ÿüñæÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúèØÿî´{ÿùæÒÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþýüÿóÉ ÿñÖÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿøÞÄÿﺅÿúìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþöÿÿÿùïé0üòéÿûðæÿûîàÿúêÚÿùæÔÿùâÍÿøßÇÿ÷ÝÃÿ÷Ú¾ÿöÕ·ÿôϬÿóÉ¡ÿñĘÿð¿ÿð¼Šÿﺆÿ︂ÿï·€ÿï¶~ÿîµ~ÿï¶~ÿï¶ÿï·€ÿ︃ÿð»‰ÿñ¿ÿòÄ—ÿóÉ ÿôͧÿõЮÿõÕ¶ÿ÷ÚÀÿøáÊÿùèÖÿøáËÿî¶~ÿöعÿýùôÿýùõÿþüûÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿííîÿ^^]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿQQQÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿFFFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿPPPÿêêêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿðÀ‘ÿòÉŸÿþýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøäÎÿîµ|ÿúìÝÿÿÿÿÿÿÿÿÿûÿÿÿELbÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ+*'ÿDA>ÿVVTÿfedÿsqqÿz{zÿ…ÿ›ÿ¯«ªÿ¼»¹ÿÈÇÆÿÒÑÑÿÛÛÚÿáááÿèèèÿîîîÿíïïÿìëëÿðððÿòòòÿõõôÿëÜÿíÙÿùñéÿüüüÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿ÷ÞÄÿî´|ÿûîáÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿûûûÿúúúÿûûûÿùùùÿøøøÿøùùÿ÷÷÷ÿöö÷ÿôôôÿñññÿðððÿîïïÿìììÿêêêÿçççÿäååÿãããÿâââÿÝÞÞÿÚÚÛÿÖÖÖÿÒÒÓÿËËËÿÅÂÁÿ³iÿ¯—€ÿ®¯±ÿ¤¥ªÿ——˜ÿƒƒƒÿº£ÿøîìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿþú÷ÿõÕ´ÿñ½‹ÿüôíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÓÿÿÿ0ÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþþÿþþýÿþüúÿýúöÿý÷òÿüõîÿüóêÿüñçÿûðäÿûíßÿúéØÿùäÐÿøàÉÿ÷ÝÃÿ÷Ú¾ÿöعÿõÓ±ÿôͧÿòÇœÿñÁ’ÿð½‹ÿï¹…ÿï·€ÿîµ}ÿî´|ÿï´{ÿîµ|ÿî´{ÿí®pÿî´zÿð»†ÿð½Œÿñ”ÿòÇœÿóË¥ÿôЭÿõÔ³ÿ÷Ù¼ÿ÷ßÇÿùæÓÿúìÞÿüòèÿüõîÿý÷òÿýùõÿþüùÿÿþþÿÿÿÿÿýýýÿ¸¸¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÆÆÆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚÚÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿﺆÿõЬÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÝÄÿî¶~ÿüñæÿÿÿÿÿÿÿÿÿÿÿÿÿ_|•ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿšxlÿúñíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿýøñÿóË£ÿòÖÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýýý£ÿÿÿ4þþþÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿþþýÿþýüÿþýûÿþüúÿþú÷ÿýùôÿýöðÿüôìÿüòéÿûñæÿûïäÿûìßÿúçÖÿùãÍÿøÞÆÿôÒ®ÿí°sÿóÈŸÿõÒ¯ÿóÉ¢ÿò×ÿñ¾ÿðº„ÿî¶ÿî´zÿî²xÿî²xÿî²yÿî´zÿîµ~ÿï·€ÿ︄ÿð¼‰ÿñÀÿòÅ™ÿóÊ¢ÿÛ¹šÿ% ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÒÒÒÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞÞÞÿ"""ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðððÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúõÿîµ~ÿöÙºÿþþþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿþüûÿöÖ¶ÿ﹃ÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿ“¥¼ÿ#ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ{nÿùñíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿñ“ÿóͦÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýþÿÿÿÿþþþpÿÿÿ@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþýüÿúéÙÿî³yÿùæÑÿþüúÿýøòÿýöïÿüôìÿüòéÿüñçÿûðäÿûìÞÿúæÔÿøàÊÿ÷ÛÁÿö×¹ÿõÓ³ÿõÑ®ÿóÌ¥ÿòÅ›ÿñÀ‘ÿã°ÿ]G2ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿPPPÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿhhhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿí±xÿøàÈÿþþþÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿþüùÿôΨÿkÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿ¼Óðÿ$-9ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¬Žyÿü÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿúìßÿﻈÿöغÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûûûEûûûPÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿùçÖÿî´zÿûìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþýüÿþüûÿþûùÿþûøÿþú÷ÿýùôÿý÷òÿ÷ðéÿ˜“Žÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿl]Nÿ÷ؼÿ÷ÞÆÿøâÍÿùèÖÿúíàÿüóëÿþùöÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇÇÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìììÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿí°tÿùçÕÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþú÷ÿòÆ›ÿòÕÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿîÿÿÿ9ARÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿA/ÿãÞÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùåÑÿ﹂ÿùãÏÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÿÿÿ"ÿÿÿÿÿÿ`ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøãÎÿîµ|ÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ½cÿî²wÿî°sÿí®qÿí®pÿí°rÿî±vÿî³zÿï·€ÿðº…ÿñ¾ŒÿòÖÿóÉ¡ÿõÑ­ÿö×¹ÿøÞÆÿùäÏÿùçÖÿúìÞÿûòçÿ~{xÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿœœœÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿí°uÿûíàÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿýøòÿð¿ÿóÊ¢ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿSc‰ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿIJ›ÿÿþúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÝÃÿ﹄ÿûîâÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÑÿÿÿ þþþpþþþÿÿÿÿÿþþþÿúúúÿ÷÷÷ÿôôôÿòòòÿñññÿðððÿïïïÿïïïÿðððÿðððÿòòòÿóóóÿõõõÿøøøÿûûûÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷߯ÿï¶ÿüóéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿ¾¾¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ'&%ÿüòéÿüðæÿüïãÿûìÞÿúçÕÿøßÉÿöؼÿõÒ°ÿôÌ¥ÿóÇžÿñÖÿð¾ÿﺅÿï¶ÿî³yÿí°tÿí®qÿí®pÿí®qÿí°tÿQ<(ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿnnnÿÿÿÿÿÿÿÿÿÿÿÿÿùãÏÿí²wÿüóéÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýõìÿﺅÿõÒ¯ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒ¢ºÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿoU9ÿñìæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿõÓ²ÿð½‹ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ§ÿÿÿ ÍÍÍŒÞÞÞÿÒÒÒÿ¸¸¸ÿ   ÿŠŠŠÿvvvÿhhhÿaaaÿXXXÿTTTÿUUUÿVVVÿZZZÿdddÿqqqÿ}}}ÿŽŽŽÿ¥¥¥ÿ¼¼¼ÿÒÒÒÿÝÝÝÿäääÿêêêÿðððÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿöÚ½ÿ︂ÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿ½½½ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ’’’ÿÿÿÿÿÿþÿÿÿþþÿþþþÿþþýÿþýüÿþüûÿþüúÿþûøÿþûøÿýú÷ÿýøóÿýöîÿüòéÿûðåÿûíàÿúëÝÿúè×ÿùâÎÿ÷ÛÁÿF<3ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ]]]ÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÃÿî´{ÿýöîÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüñæÿî¶ÿ÷Ú¾ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÀÚõÿ")5ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ' ÿÝÑÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýøòÿóÉ ÿñÄ—ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýý‡ÿÿÿ (Fw¤é ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ(((ÿHHHÿjjjÿ“““ÿ»»»ÿÖÖÖÿàààÿìììÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿõÕ·ÿÿýúôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿ®®®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïïïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿþþþÿþþýÿþýýÿþýüÿGGFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[XVÿýùöÿþüúÿÿÿÿÿõÖ·ÿﺅÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúìÞÿî´{ÿøâËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúÿÿÿ8BXÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ£†dÿúöòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüôíÿð¿ŽÿóΨÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿüüüeÿÿÿ:v¶îÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ///ÿ___ÿÿ¼¼¼ÿ×××ÿæææÿ÷ôñÿôÓ±ÿð¼Šÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîîîÿ•••ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿtttÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿU@,ÿï·ÿð¼Šÿò•ÿ︀ÿí³zÿôЬÿöغÿøßÇÿúæÖÿûïâÿüôíÿý÷ñÿýøôÿýúöÿþüùÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùçÔÿî´zÿúèØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ`|™ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;'ÿëåÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîãÿ﹃ÿöÙ»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúú9 0k½ÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿUUUÿŒŠˆÿ³˜~ÿÌ¡xÿïîíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞÞÞÿkkkÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿâââÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXK?ÿóË£ÿòÄ—ÿñ½‹ÿî°tÿì®qÿí°tÿì­pÿì¬nÿí¬lÿí«lÿí­oÿí®qÿî²wÿï¶ÿð»ˆÿñÁ’ÿòÇÿóͨÿõÒ±ÿö×¹ÿ÷ÝÄÿùåÒÿûìßÿüóëÿýøôÿþûøÿþüùÿþüûÿÿýüÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿ÷߯ÿî´|ÿûïäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¡µÒÿ!ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÇ´™ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿúçÕÿî¶€ÿøãÎÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿ5…äÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ.%ÿqqqÿªªªÿÏÏÏÿíííÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿ½½½ÿ;;;ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿtttÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[[[ÿþþþÿÿÿÿÿþþþÿð¾ÿóͦÿýúöÿýöïÿûïãÿùèÙÿøãÎÿ÷ÞÆÿöÙ¾ÿõÓ²ÿô̧ÿòÆšÿñ¾Žÿ︃ÿî´{ÿí°tÿí®pÿì¬mÿì«lÿí«lÿì¬mÿí­pÿí±uÿîµ|ÿﺅÿñÀÿòÆ›ÿô̧ÿõÓ³ÿöØ»ÿ÷ÝÃÿøãÎÿùêÛÿûðæÿýøñÿþüúÿþüûÿõغÿî¸ÿý÷ïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâùÿÿ%0>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿkM0ÿõòîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿ÷ÝÂÿ︃ÿûîãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÑþþþ&yåÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ&&&ÿlllÿ¨¨¨ÿÐÐÐÿ÷÷÷ÿÿÿÿÿÝÝÝÿŠŠŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæææÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿýüùÿÿõÕ³ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþÿÿþýÿÿþýÿþýûÿýøóÿüòéÿúëÝÿùäÐÿøÝÅÿöؼÿõÔ³ÿôΩÿòÇÿñÀ’ÿð»‡ÿïµ~ÿî²vÿí¯qÿí¬nÿí¬lÿí¬kÿì«mÿì­pÿí°tÿí³yÿí±vÿí°tÿòÄ–ÿôÌ¥ÿôÓ±ÿöÙ¼ÿøÝÄÿùâÌÿúçÖÿûîáÿDZxÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿãÕÂÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿôÑ®ÿð½Œÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýý¢¿¿¿J¿ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ222ÿ|||ÿŸŸŸÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ’’’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿýøòÿí³zÿ÷ÜÀÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþþýÿþýûÿþüúÿþûøÿýùôÿüõìÿûîàÿùæÔÿøÞÆÿöØ»ÿõÓ±ÿôΨÿîµ|ÿî²wÿð½‹ÿï·ÿî³yÿî¯tÿí­pÿí¬nÿí¬mÿì­nÿ€yvÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿž‚]ÿûùøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿýøóÿòÆ™ÿòŘÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿlÿÿÿ lëÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ999ÿôôôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿüóêÿí±vÿùãÍÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþüÿñÁ‘ÿòÇÿÿÿÿÿýú÷ÿýøóÿýöñÿüôíÿûïäÿúè×ÿøàÊÿÉÉÈÿ&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ2 ÿôíãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿð¼‰ÿôΪÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýþþþþÿÿÿÿ9 €÷ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÂÂÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿûîáÿí±uÿúéØÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþùõÿðº†ÿôΩÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>ÿ733ÿݼ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿüôëÿð¼ŠÿôÑ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿ9ÿÿÿ ­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿj]PÿïïïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿþþþÿÿÿÿÿñ¿ÿòÉŸÿþüúÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿôЬÿðº„ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿF\xÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ™}eÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷Ú¾ÿð¿ŽÿúëÛÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþüùÿý÷ñÿüñçÿúêÜÿùåÑÿøàÉÿ÷ÜÁÿö×¹ÿõѯÿóË¥ÿòÆœÿñ“ÿñ¾ÿð¼‰ÿî²xÿí¯qÿî³{ÿî³yÿî²xÿî³yÿîµ|ÿï¶€ÿðº‡ÿñ¿ŽÿòÄ—ÿóÉ ÿôΨÿôЭÿõÓ²ÿö×»ÿ÷ÝÄÿøãÍÿùèÖÿúìÜÿûíßÿûïâÿüñæÿüóëÿýöðÿýøôÿýúöÿþûøÿþüùÿþýüÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿê«mÿøïåÿùùùÿ÷÷÷ÿõõõÿóóóÿðððÿíííÿêêëÿçèçÿàããÿÝÞÞÿÝÝÝÿÜÜÜÿÛÛÛÿÛÛÛÿÙÙÙÿØØØÿÕÕÕÿòæåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûíßÿï·€ÿ÷ÞÅÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþïõõõEØÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWD1ÿÜÄ­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿﺆÿôÏ«ÿþýûÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿòÇÿñ¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ›Áßÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿpP1ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÒ°ÿñ”ÿüñæÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþüúÿþýüÿôϪÿ(ÿùãÏÿùçÕÿøàÊÿ÷ÜÁÿöغÿõÓ²ÿôΩÿòÉ ÿòÄ—ÿñÀÿð½‹ÿð»‡ÿ﹄ÿï¶€ÿïµ}ÿî´{ÿî´{ÿîµ}ÿï¶€ÿ﹄ÿñ½‹ÿò”ÿóÇžÿô̦ÿôЬÿõÒ±ÿõÕ¶ÿöÚ¾ÿ÷ßÇÿøäÏÿúéØÿúëÜÿûíàÿûïäÿüóêÿøÞÅÿí¯rÿýöðÿþûùÿþüúÿþýüÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿùåÑÿïµ}ÿúêÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÊìììzùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿOHBÿΡvÿøáÉÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿþþÿÿî¶ÿõÖ·ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿñÁ‘ÿòÄ—ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÿÿÿ&Fÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ9 ÿÿÿôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿòˤÿòÇÿýöðÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÈžÿòÅ™ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿþüúÿþú÷ÿýùôÿýöñÿüóëÿûîáÿúèÖÿøâÌÿ÷ÝÃÿöØ»ÿöÔµÿôЭÿóË£ÿòÆ›ÿñÁ“ÿñ¾ÿð¼‰ÿðº‡ÿð¹ƒÿï·ÿïµÿîµ}ÿïµ~ÿï·ÿ﹄ÿð¼‰ÿñÁ’ÿﻇÿí¯rÿõЭÿõÒ°ÿöÕ´ÿö׺ÿ÷ÜÂÿøàÊÿùæÒÿúéÙÿûìÝÿûîáÿûðæÿüóëÿýöñÿþúöÿþüúÿþýüÿþþýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷ÜÁÿï¸ÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþþ¤ååå žÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿNNNÿѼ©ÿð¼‰ÿùåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿýùõÿí³zÿ÷ÝÃÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþüùÿð»‡ÿó̤ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿbžÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúãÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿñÆšÿóͧÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿñÀ‘ÿóͧÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿýúöÿý÷òÿýõîÿüóêÿûïãÿúéÙÿøãÏÿøÞÅÿ÷Ú½ÿõÖ·ÿôÒ°ÿôΨÿóÉ¡ÿî²wÿï¶~ÿð½‹ÿð»ˆÿﺆÿð¹ƒÿï·ÿï·€ÿï·€ÿï·ÿð¹„ÿð»‡ÿð¾Žÿñ•ÿóÇžÿôͨÿõѯÿõÔ³ÿö׸ÿöÚ¾ÿ÷ÞÆÿùâÎÿúçÕÿúëÛÿûíàÿûðäÿüòéÿýöïÿýùõÿþüúÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿôЮÿð¾Œÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿÿÿÿ…ßßß²ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿQQQÿØØ×ÿ÷ÜÂÿð½ŠÿúéØÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿüòèÿî²xÿøäÏÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýøòÿï·ÿõÓ±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍéøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿϪÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿñ”ÿõÓ²ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿ(ÿö׸ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿð»ˆÿôЮÿýõîÿüòéÿûïäÿúëÛÿùåÒÿøàÉÿ÷ÜÁÿö×¹ÿõÔ³ÿõÑ­ÿô̤ÿóÇœÿñ•ÿñ¾Žÿð¼Šÿð»ˆÿðº…ÿ︃ÿï·‚ÿï·ÿ︂ÿ﹄ÿðº‡ÿð½‹ÿñÀ‘ÿòÅ™ÿóÊ¢ÿôÏ«ÿõÓ²ÿõÖ·ÿ÷Ù¼ÿ÷ÜÃÿøàÊÿùåÒÿùåÓÿñÀÿñÁ’ÿüñèÿüõîÿýøôÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿ`¿¿¿"½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿßßßÿþýûÿöÙ¼ÿð½ŒÿûìÞÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿúêÚÿî²yÿúéÙÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüòèÿî´{ÿöÜÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ9Rfÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ‘{^ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúíßÿñ¿ÿöÙ½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìÞÿ︂ÿ÷àÈÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿýùôÿî±wÿøâÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿýøôÿüõîÿüòéÿûðåÿûìÞÿùçÖÿùãÍÿ÷ÞÅÿöÚ¾ÿöÖ·ÿõÓ²ÿõϪÿóÊ¢ÿòÅ™ÿñÁ’ÿð¾Œÿð¼Šÿð»‡ÿð¹„ÿ︃ÿ︂ÿ︃ÿ︃ÿí°sÿî²wÿñ¿ÿñ•ÿóÆÿóÌ¥ÿõÑ®ÿöÕµÿöغÿ÷Ú¿ÿøÞÆÿùãÎÿúçÕÿûëÜÿûîâÿüñçÿüôìÿý÷òÿþûùÿþÿþÿÿÿÿúÿÿÿ9(Áÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ@@@ÿÔÔÔÿÿÿÿÿþüúÿõÖ·ÿð¿ŽÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿøâÌÿî´|ÿûïâÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúêÛÿí³xÿøåÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ˜»Ûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿe<%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿùçÕÿð¾ŒÿøàÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÎÿï·ÿùè×ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïâÿí­nÿüñåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿýúöÿýöðÿüóêÿûðæÿûíàÿúéÙÿùåÑÿøàÉÿ÷ÜÁÿôÏ©ÿí°tÿòÆ›ÿôΪÿóÈŸÿò×ÿñÀÿð½‹ÿð¼ˆÿﺆÿ﹄ÿ︃ÿ︃ÿð¹„ÿðº†ÿð¼ˆÿð½‹ÿñÀ‘ÿòÄ—ÿóÉ ÿóΨÿõÓ´áöÛÁ#¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿbbbÿêêêÿþûøÿõÔ²ÿñÀ‘ÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿöÚ¾ÿï·ÿüóêÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿøãÍÿî³yÿúíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÿÿÿ#Gÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ#ÿÿùâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøßÈÿð½‹ÿùæÔÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿöÚ½ÿï¹…ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÑÿí®qÿþû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùèÕÿîµ|ÿúìÞÿÿÿÿÿþû÷ÿý÷ñÿüóëÿûðæÿûîáÿúêÛÿúæÔÿùâÍÿ÷ÞÆÿöÚ¿ÿö×¹ÿõÔ´ÿõЭÿôÌ¥ÿóÆœÿñÁ”ÿñ¾ÿ¾á´x³ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXXXÿâÞÛÿôЭÿñ”ÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿõÓ±ÿð¼ˆÿý÷ðÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ÷Ú¿ÿîµ|ÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿj޳ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ寥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöØ»ÿñ¿ÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЬÿð½ŒÿüóêÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿöÚ¾ÿîµ~ÿþþýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿþýüÿöØ»ÿï¸ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþûùÿýøóÿüôíÿüñçÿùëÝ’ççÐ ¡ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿUSQÿÙ¶”ÿòÅ™ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\[[ÿÿÿÿÿóÌ¥ÿðÀ‘ÿþùôÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿôÒ±ÿ︂ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿáõþÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¨ŒtÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿôÑ®ÿñÕÿüóëÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿòÈžÿòĘÿýöïÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿóͧÿñÀ’ÿþþýÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþüúÿóÌ¥ÿð¾ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþeÿÿÿ~ûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXH9ÿÛ¶ÿþû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[\\ÿÿÿÿÿòÅ™ÿòÆ›ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþþÿòË¢ÿð¼ŠÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿSjÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿuW7ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿóÊ£ÿòÈžÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿñÁ’ÿôΨÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ¿ŽÿôϪÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþûøÿñÀÿòÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿ=JÛÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿfVEÿëêéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿð¾ŽÿóͧÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿþÿòÄ•ÿñ”ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇâôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ5%!ÿÿÿèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿòÆšÿôΩÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿð¼‰ÿõ×¹ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿï´{ÿøÝÄÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿý÷ðÿ︂ÿõÓ±ÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ÷÷÷$ ³ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‚‚‚ÿóóóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿþüûÿ﹄ÿôÔ´ÿþüúÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð½‹ÿóÊ¡ÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ:Xqÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçŧÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðåÿñ“ÿõÔ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿ﹃ÿ÷àÉÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòêÿí®qÿúêÜÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûîáÿî´{ÿøàÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãõõõnïÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¡¡¡ÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿü÷ñÿïµ}ÿ÷ÛÀÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿï¸ÿõÒ¯ÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ«Ðéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¤ˆsÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿúëÜÿð¿ÿ÷ÛÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÊÿ︂ÿúèØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùèØÿí¯rÿüôíÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøâÍÿî´{ÿûíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ´ÿÿÿ¶ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¿¿¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿûñèÿî²yÿøâÌÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿîµ|ÿ÷Ú¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ(Hiÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿmF6ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿùåÑÿð½‹ÿøâÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿöØ»ÿ﹄ÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÜÂÿïµ~ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿõÕ¶ÿ︂ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýççç Qßÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ$$$ÿÛÛÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿúìÝÿí³xÿùé×ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíßÿí³xÿùãÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ§Âàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ)'"ÿÿïÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÅÿð½ŒÿúêÙÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЭÿð¾ÿüòèÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΪÿñÀ’ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿòÉŸÿð¿ŽÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿÿÿÿTÿÿÿƒôÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿYYYÿîîîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿùèÕÿî´zÿûíàÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÒÿî³xÿûìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúþýÿ'Bfÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ˦ŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿöÖ¸ÿñ¿ÿûðåÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿóÉŸÿñÅ™ÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿñÁ“ÿôͨÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð¾ŒÿóÉ¡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúú3›ùÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ™™™ÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿøáÊÿî¶~ÿüñæÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÅÿî´zÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ¥·Úÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿjLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿôÏ«ÿñÖÿýöïÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿñ“ÿôΩÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿï·ÿöÙ½ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýöïÿî¶€ÿõÖ¸ÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþî÷÷÷$  ÷ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÓÓÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿ÷Ù½ÿ﹄ÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÖ¸ÿï·€ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöüûÿ+:gÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿD.+ÿÿøåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿóÊ¢ÿóÉ ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñæÿð½Šÿõ×¹ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿí°tÿøãÎÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúíßÿî³yÿøäÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÉÿÿÿìÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿLLLÿôôôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿõѯÿð¾ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿôΩÿð»‡ÿþúøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýþÿ§ºÙÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ%ÿÖ´ŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿñÅ™ÿôÏ«ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùèØÿï¹…ÿøàÉÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿî°tÿûíàÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿøáËÿî´zÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿÿÿÿ¢ÿÿÿmÐÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ###ÿMMMÿmmmÿ444ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ§§§ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿóÊ¡ÿñÖÿýøóÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿòÇ›ÿñÁ“ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôùùÿ2Npÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ‡t_ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿñÁ’ÿö׸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÈÿ﹃ÿùèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÈÿîµ~ÿüõîÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþþþÿõÕ´ÿ︃ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþ~ÿÿÿ 4¢âÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ!! ÿCCBÿxxxÿ½½½ÿÿÿÿÿÿÿÿÿÒÒÒÿbbbÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ!!!ÿëëëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿñÕÿóÊ¢ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿðÀÿóÉ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýÿÿ®ÅÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿN61ÿÿûèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿúéØÿð¾ÿøÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöغÿﻇÿûîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЮÿñÀÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþýûÿòÈŸÿñÁ’ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüZ¿¿¿W«ßÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ)ÿH6%ÿpV=ÿ¨ƒ_ÿæ·ˆÿñÖÿòÇÿóÌ¥ÿõÑ®ÿõ×¹ÿöÝÄÿ’†yÿ1-*ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ†††ÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[[ZÿkÿõÑ®ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿ﹄ÿõÒ¯ÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó÷øÿ@c~ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ+"ÿÕ¼¢ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùãÏÿð¼ŠÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЬÿðÀÿûñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿòÕÿôË¥ÿþüúÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿð½‹ÿóΧÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿñÿÿÿ:Q—Èóÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ=2(ÿ[E/ÿ‡vfÿº ˆÿêÆ¤ÿòÊ¡ÿñŘÿðÀÿð¼ˆÿ︂ÿïµ~ÿî´zÿî²xÿî²wÿí±vÿºŒ]ÿK8&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèççÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[ZXÿÿöعÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòêÿîµ}ÿ÷Û¿ÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýþÿÿ¹Ïßÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ†rcÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÃÿð½ŠÿúìÞÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿóÉ ÿòÇœÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ﹃ÿõÖ·ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿï¶~ÿöÛÀÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÑøøø%1jšÀãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ---ÿKKKÿhhhÿ‰‰‰ÿ°¯®ÿÒ´–ÿð¾ŒÿþÿþÿÿÿÿÿÿÿÿÿÿýüÿþüùÿþúöÿýøóÿýöðÿýôëÿûïäÿùêÚÿøåÑÿ÷߯ÿöÚ½ÿàçÿl\Mÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ}ÿþüúÿþýûÿþýüÿþýüÿþýüÿþþýÿþþýÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZXVÿî¶}ÿ÷ÞÅÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿí²xÿùãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõ÷ùÿ`z˜ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿO94ÿÿñáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿõÕ¶ÿð¿ÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿñ”ÿôϪÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿî³yÿ÷ßÇÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÛÿí³yÿùè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿ±ôôô*Qv&&&±MMMÿ222ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ---ÿ@@@ÿVVVÿpppÿŠŠŠÿ¤¤¤ÿÁÁÁÿâââÿÿÿÿÿÿÿÿÿþûùÿòˤÿðÀ’ÿÿþýÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿˆˆˆÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿå½–ÿóͧÿôÑ®ÿõÖ·ÿöÛÀÿ÷áÊÿùçÔÿúìÞÿüïãÿüñæÿüóêÿýõîÿý÷òÿþúöÿþüúÿþüúÿþüûÿþýûÿþýüÿþýýÿþþýÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZVSÿî´|ÿøäÏÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿî²xÿúëÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍÛåÿ7ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ+ÿʯ–ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿôÏ«ÿñĘÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñåÿð¾Œÿö×¹ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿí±uÿúêÚÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøàÊÿî´zÿûðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿ“ðððñññLßßßÿÅÅÅþ²²²ÿŸŸŸÿÿ~~~ÿpppÿcccÿZZZÿTTTÿMMMÿJJJÿKKKÿLLLÿOOOÿVVVÿ___ÿfffÿrrrÿÿÿÿ¯¯¯ÿÂÂÂÿÔÔÔÿèèèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿñÆœÿñŘÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿ˜˜˜ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ–uTÿî·ÿî¶~ÿî´{ÿî³yÿî²yÿî²xÿí³zÿîµ|ÿî¶€ÿðº…ÿð¾Œÿñ”ÿòÇœÿôˤÿôЭÿôÔ´ÿöÙ¼ÿøÞÅÿùãÎÿúéÙÿFC?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿYTOÿîµ|ÿúè×ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿøãÌÿï³yÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷úüÿ€™«ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€mZÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöïÿòÉ ÿóË£ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùé×ÿﺇÿøßÈÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÐÿï´|ÿüóêÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõÔ³ÿðº„ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿüüüpÿÿÿÿÿÿKÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿïïïÿèèèÿãããÿÞÞÞÿÜÜÜÿÜÜÜÿÝÝÝÿßßßÿåååÿìììÿòòòÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿñÖÿòÈŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿœœœÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ421ÿüóëÿüñæÿúìÞÿùçÕÿøáÊÿ÷Û¿ÿõÖµÿôÑ­ÿóͦÿòÈžÿñÄ—ÿñ¿ÿð¼‰ÿ﹄ÿî¶ÿîµ~ÿî´{ÿî³zÿî³yÿî³yÿC2"ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿYQJÿï¶~ÿûîàÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿöÚ¾ÿî¶~ÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛäìÿ-@XÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿJ9/ÿóâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿñÄ–ÿõѯÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿøàÉÿﺆÿùæÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÕ¶ÿð¼‰ÿýøóÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿòÇ›ÿñÕÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿûûûNûûûNÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþú÷ÿñÀÿóÌ¥ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ•••ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔÔÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿýú÷ÿý÷ñÿüôìÿüñèÿûîâÿúéÙÿùäÏÿ÷ÞÅÿöغÿE;1ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXNEÿ︃ÿüñèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôÑ®ÿﻇÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüþÿÿ¡°Âÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"ÿµ—…ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûíßÿñ¿ÿöÙ¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöغÿð¼ŠÿûìÞÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿÿÿÿÿóÈÿóÆœÿþú÷ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿﻇÿóϪÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýòúúú4üüüZþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþúöÿð½‹ÿôЬÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿ€€€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ{{{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWH:ÿ﹃ÿúçÖÿüòèÿüóëÿýõîÿýöðÿýùóÿýúöÿþûøÿþûùÿþüúÿþýüÿþþýÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿòÉŸÿñÁ‘ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåïöÿMf‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿn\Lÿÿýëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿùè×ÿ)ÿøáÊÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЬÿñ“ÿûñçÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ½ŠÿõÓ²ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûòéÿî´{ÿ÷ÜÁÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐøøø'ÿÿÿjÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿﺆÿõÔ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìììÿWWWÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ)))ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿU?)ÿí¯qÿî·ÿð»†ÿð¾ÿñ•ÿòÇÿôÍ¥ÿõѯÿöÕ¶ÿöÙ¼ÿ÷ÝÄÿùáËÿúåÒÿúêÚÿûîáÿüðæÿüòèÿüôìÿýöîÿý÷ñÿýùôÿýúöÿþûøÿþüùÿþýûÿþýýÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿñÁ’ÿòÉŸÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¸ÉØÿ":ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ8,ÿÖìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÍÿﻇÿúè×ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿóÉ ÿòÈŸÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿîµ|ÿøßÈÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéØÿî²xÿúéÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþ¤ôôôþþþ{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüõîÿï·‚ÿöÙ¼ÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕÕÕÿ"""ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÚÚÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVB/ÿÿó̤ÿóË¢ÿòÇšÿñÔÿñ¿ÿð¼‰ÿﺅÿ﹃ÿï·€ÿî¶ÿï¶~ÿî¶}ÿî¶ÿï·€ÿ﹃ÿð¼‰ÿñÀÿòŘÿóÊ¡ÿôΪÿõÓ²ÿö×¹ÿöÛ¾ÿ÷߯ÿùâÍÿùçÔÿúëÛÿûïâÿûñæÿüòèÿüôëÿýöîÿý÷òÿýùõÿüõîÿﺆÿôЭÿþýýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöûÿÿ}’£ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿymÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿöÛÁÿð¼ŠÿûïäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöñÿñÖÿôϬÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿî±vÿúêÛÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÜÂÿïµ|ÿýôíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿxÿÿÿ ÿÿÿ‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüòéÿîµ~ÿ÷ÞÅÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ¨¨¨ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ———ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVE5ÿóͦÿþýûÿÿÿÿÿþþüÿýû÷ÿý÷ñÿüóêÿûïäÿûíßÿúéØÿøäÏÿøßÇÿöÚ¾ÿõÔµÿõЭÿô̧ÿóÉ ÿòÆ™ÿñÁ“ÿð¾Žÿð¼‰ÿﺅÿ︃ÿï·ÿï¶ÿî¶ÿî¶ÿî·€ÿ﹂ÿﻆÿð¾Œÿñ“ÿòÇ›ÿóˤÿôЭÿôѯÿî²wÿòÆ›ÿøàÈÿøãÎÿúçÖÿûëÜÿûîâÿûðåÿüòèÿüôëÿýöïÿý÷òÿýùöÿþûøÿþüùÿþýûÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓßìÿ:JcÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿP@1ÿèÚÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿõÕ´ÿðÀÿüöîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðäÿð¾ÿö×¹ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùè×ÿî³yÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿôϪÿﺆÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýþÿÿÿÿÿÿÿVÿÿÿ—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûðäÿí´zÿøãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëëëÿSSSÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXXXÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVC1ÿõÒ¯ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþüùÿýøóÿýôìÿûñæÿúíáÿúêÛÿùæÔÿøâÌÿ÷ÝÃÿöغÿõÓ²ÿôϬÿóÌ¥ÿóÈŸÿñŘÿñÁ’ÿð¾Œÿð¼‰ÿï·ÿì­oÿî´|ÿï·€ÿî·ÿï·ÿ﹂ÿ﹄ÿð¼‰ÿñÀÿñÄ–ÿóÈžÿóͧÿõÒ¯ÿõÕµÿöØ»ÿ÷ÜÁÿøàÈÿùäÏÿùè×ÿúìÝÿûîáÿûðäÿüòèÿüôìÿýöðÿýøôÿýú÷ÿþûùÿþüúÿþýüÿþþþÿÿÿÿÿÿÿÿÿ¡±Äÿ(ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ«•~ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿóΨÿñÅšÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿúè×ÿð¼‰ÿ÷ÝÅÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÛÀÿð¹„ÿý÷ðÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿñÔÿñÄ–ÿÿÿÿÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿCÿÿÿ›ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûíàÿí²xÿùçÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÁÁÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ!!!ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVB/ÿöغÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþýûÿýùöÿüõïÿüòéÿûïäÿ÷ÝÃÿí±uÿöÖ¶ÿøàÈÿ÷ÛÀÿöÖ·ÿõÒ°ÿôÏ©ÿóË£ÿòÈžÿñÄ—ÿñÁ‘ÿð¾Œÿð»‡ÿﺅÿ﹃ÿ︂ÿï¸ÿï¸ÿ︂ÿ﹄ÿﻇÿñ¾ŒÿñÁ’ÿñÆšÿóÊ¢ÿôϪÿôÓ±ÿõÕ¶ÿöؼÿ÷ÝÃÿøáÊÿùäÑÿúèØÿëçÞÿev…ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿgRBÿ÷åØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿòÇœÿó̦ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÉÿð¼‰ÿùåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôΩÿñÕÿýøôÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿ﹃ÿôЬÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿëÿÿÿ7ÿÿÿœÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúìÝÿí²vÿúëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿéééÿSSSÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëëëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVB.ÿ÷ÞÄÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÓÿî³yÿûðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþýüÿýûøÿý÷òÿüôëÿûðåÿûíßÿúêÚÿùæÔÿøâÌÿ÷ÞÄÿöÙ¼ÿöÕµÿôÑ®ÿôΨÿóË£ÿòÇÿñÖÿñÀÿð½‹ÿﻇÿﺅÿ﹃ÿÿ︂ÿ︂ÿ﹄ÿﺆÿ½¢„ÿ/58ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ# ÿ¹¢•ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðåÿñÁ’ÿõÔ³ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöغÿð¾ÿúìÝÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò“ÿôϪÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿî´zÿ÷ÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÃÿÿÿ&ÿÿÿ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúêÙÿí±vÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯¯¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÂÂÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVA-ÿùäÏÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿ÷ÛÀÿîµ|ÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþþýÿþüúÿýùôÿýõîÿüñèÿûîáÿúëÜÿùé×ÿùåÑÿøáÊÿ÷ÜÁÿöغÿõÔ²ÿôÑ­ÿôͨÿ†}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿpYIÿùæØÿþýüÿþþþÿÿÿÿÿúíàÿð½‹ÿøÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿôЬÿñÖÿûñçÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿð¸‚ÿ÷ÝÂÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÓÿí²yÿúëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿšÿÿÿÿÿÿ³ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùæÕÿí±wÿûñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×××ÿ$$$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿžžžÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿUB.ÿúéÙÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿõÒ°ÿ﹄ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþýüÿþüúÿïóñÿ[`bÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ% ÿ·Žmÿö×¹ÿöÛÀÿøàËÿõÔµÿï·€ÿõÖ¶ÿûðãÿûðäÿüóéÿüöîÿýøôÿþûøÿþýûÿþþüÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿóÉ ÿóÉ¡ÿüöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿî²xÿùèØÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöØ»ÿîµ}ÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþwþþþÿÿÿÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøâÍÿî³zÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿêêêÿbbbÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVB/ÿúîáÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóÉ¡ÿð¿Žÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿ¾§“ÿ39AÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿrH(ÿì«qÿ﹃ÿ﹄ÿîµ}ÿí®qÿî·ÿð¾ŒÿñÀÿñÕÿòÇœÿóË£ÿôΪÿõÒ¯ÿõÕ´ÿöØ»ÿ÷ÝÂÿøàÊÿùåÑÿúè×ÿúëÝÿûîáÿüñæÿüôìÿý÷òÿþú÷ÿþüûÿþýýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿñÄ—ÿôЫÿýúöÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéÚÿî²xÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿóˤÿð¼‰ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿYÿÿÿÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÝÃÿîµ}ÿý÷ðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿ”””ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿiiiÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVC1ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿñ”ÿòÆ›ÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýøóÿ﹄ÿ’™ÿ +ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ! ÿº›‚ÿøáÊÿ÷ÜÁÿòÅšÿî´|ÿôΩÿôЬÿóˤÿòÇÿñÖÿðÀÿð¼Šÿﺆÿﺄÿ﹃ÿ﹃ÿ︃ÿ﹄ÿﺆÿð¼‰ÿð¾ŒÿñÁ‘ÿòÄ—ÿóÈžÿó̤ÿôЫÿõÒ°ÿõÖ¶ÿöÚ½ÿ÷ÞÄÿøâÌÿùæÔÿúêÚÿúìßÿûïãÿüóêÿüöðÿýùõÿþþþÿûïãÿñÀÿö×¹ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøßÈÿ︂ÿüôìÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿñÁÿóÇœÿÿÿÿÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýêþþþ?ÿÿÿæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿöØ»ÿ︂ÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ···ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWWWÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHGHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVD3ÿüôìÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð»ˆÿóΩÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýôëÿî³zÿ÷åÒÿl|‹ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿv[KÿõåÛÿýûøÿôÓ²ÿñÀ‘ÿýöïÿþûøÿýøòÿüõîÿüòèÿûïäÿúìßÿúêÛÿùèÖÿøäÏÿ÷àÈÿ÷ÜÁÿöغÿõÔ´ÿôѯÿôΩÿóÊ¢ÿòÆšÿñ“ÿð¾ÿð¼ˆÿﺅÿ﹃ÿ︂ÿ︂ÿ︃ÿﺅÿð»‡ÿð¼‰ÿð¾ÿñÁ’ÿñÅ™ÿóÉŸÿôΨÿòÈžÿîµ|ÿòÆšÿöÛ¿ÿ÷àÇÿùäÏÿúèÖÿúìÜÿûîâÿüòçÿüõíÿýøóÿþûùÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿþÿþÿÿÿÿÿÿÿõÓ²ÿñÁ’ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿ︂ÿõÕ´ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿËÿÿÿ-ýýýóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿõÓ²ÿð»‡ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÄÄÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿMMMÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVG6ÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþøóÿï·€ÿõÖ·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûîâÿí°tÿûïäÿÙäüÿ?HYÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ»«œÿý÷ñÿóˤÿòÇÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþýÿþýûÿþûùÿþúøÿýùôÿýöñÿüôìÿüñçÿûïâÿûìÞÿúêÛÿúçÕÿøãÎÿ÷ßÇÿöÛÀÿö×¹ÿõÔ³ÿõÑ®ÿôͧÿòÉŸÿòÄ—ÿñÀÿð¾Œÿîµ}ÿí®qÿîµ{ÿ︃ÿÿ﹃ÿ﹄ÿﻇÿð½Šÿñ¿ŽÿñÔÿòÆšÿóÉ¡ÿôͧÿõЭÿõÔ³ÿõØ»ÿ÷ÜÂÿøáËÿúæÒÿúêÙÿúíßÿüðåÿüôëÿý÷ñÿýú÷ÿþýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÇœÿó̦ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñæÿî³zÿøâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿ³ÿÿÿ"ýýýúþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿôЫÿð¾ŒÿÿýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÈÈÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWH:ÿýøóÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿî´{ÿøÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùçÖÿí°uÿýøóÿÿÿÿÿ¨ÄÖÿ-:ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿcR<ÿæÖÂÿñÄ—ÿóϪÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþüúÿþûøÿþúöÿýøóÿüõïÿüóêÿûñæÿûïãÿôΨÿð»‡ÿ÷Ú¾ÿùäÐÿ÷ÞÅÿöÚ¿ÿö׸ÿõÔ³ÿôЭÿó̤ÿòÇœÿñÕÿð¿Žÿ(ÿﺄÿ︂ÿî·ÿî·€ÿï¸ÿð¸‚ÿﺅÿﻇÿð½‹ÿðÀÿñÕÿòÆ›ÿóÊ¢ÿôΨÿôѯÿõÕ¶ÿöÚ¾ÿøßÆÿùãÎÿúè×ÿúìÝÿûïãÿûòéÿðº…ÿöÖ¶ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøåÑÿí³xÿûíÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ™ÿÿÿÿÿÿúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿô̦ÿðÁ’ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇÇÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿIIIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXK>ÿýúöÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìÞÿî³xÿùæÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøßÈÿî³{ÿþþýÿÿÿÿÿÿÿÿÿ‹£ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¯š~ÿð¾Œÿõ×¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿõѯÿòĘÿüòéÿÿÿÿÿþþýÿþüûÿþüùÿþû÷ÿýùõÿý÷ñÿüõíÿüóéÿûðæÿûïãÿûíàÿúéÚÿùåÒÿøâÌÿ÷ÝÄÿöÙ½ÿõÖ¸ÿõÓ²ÿôϪÿòÊ¡ÿòÆ™ÿñÁ‘ÿð½Šÿﺆÿ︂ÿï·€ÿî·€ÿï·€ÿï·ÿ︂ÿ﹄ÿð»‡ÿð½Œÿí¯qÿﻇÿòÆœÿóË£ÿôϪÿôÒ±ÿö׸ÿöÜÁÿøáÊÿùæÒÿúêÛÿúíáÿûñæÿüôìÿýøòÿþûøÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöغÿï¶ÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿüüüwÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþüûÿòÈŸÿñĘÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÁÁÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿPPPÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXMBÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÏÿí³yÿûíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿõÕ·ÿﺅÿÿÿÿÿÿÿÿÿÿÿÿÿûÿÿÿPh{ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿS7ÿÕžjÿ÷àÇÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿóÊ¡ÿòÊ ÿü÷ðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþüúÿþûøÿþúöÿýøóÿýöðÿüõíÿüóéÿüñæÿûïäÿûíßÿùéÙÿùåÑÿøáÊÿ÷ÝÃÿöÙ½ÿöÖ·ÿõÓ±ÿòÆ›ÿí°sÿð¿ÿð¿ÿð»‡ÿ﹃ÿî·ÿî·ÿî¶ÿî¶ÿî·€ÿ︂ÿ﹄ÿð»‡ÿð¾ŒÿðÁ’ÿòĘÿòÈžÿóÌ¥ÿõЫÿõÔ³ÿöÙ¼ÿ÷ÞÅÿøãÎÿúè×ÿûíÞÿûðäÿüóêÿýöðÿþú÷ÿÿýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóˤÿñÀÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿ÷üüüVÿÿÿ þþþöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûúÿñŘÿòÉŸÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ«««ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ^^^ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿYOEÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÛÀÿîµ|ÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿóˤÿñ”ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿØåýÿ7@Lÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿšj<ÿøâÊÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿòÅ™ÿôϪÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþüûÿþûùÿþûøÿþüúÿøÞÄÿð¹ƒÿúéÙÿüôìÿüñèÿûðäÿúìÞÿùé×ÿøäÐÿøàÈÿ÷ÜÁÿöØ»ÿõÕ´ÿôЬÿòÌ£ÿòÆšÿñÁ’ÿð½‹ÿﺅÿï¸ÿî¶ÿî¶}ÿîµ~ÿî¶~ÿï·ÿï¸ÿ﹄ÿﻈÿð¾ÿñÂ’ÿòÅ™ÿóÉ ÿóͧÿôÑ®ÿõÖ·ÿöÛÀÿ÷àÊÿðº…ÿòÄ–ÿúîáÿüòèÿüõíÿýùôÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþßúÿÿ>ÿÿÿ0ÿÿÿ÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿñÀ‘ÿóͦÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôôôÿ‚‚‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿrrrÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿYQIÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÓ°ÿÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿñÁ“ÿó̦ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿ®ÇÙÿ(5ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ*ÿκ¤ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûðäÿñÁ’ÿöÕµÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÖ¸ÿñÁ’ÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿþþýÿþýüÿþüúÿþûùÿþú÷ÿýùõÿýøóÿýöðÿüõíÿüôëÿüòèÿûïäÿúëÝÿùçÕÿøãÎÿ÷ÞÆÿ÷Û¿ÿö×¹ÿõÓ±ÿóͨÿòÉŸÿòÄ–ÿñ¿Žÿﻇÿ﹂ÿï¶ÿî¶~ÿîµ}ÿîµ}ÿí®pÿî°tÿï¸ÿﺅÿ)ÿñ¿ŽÿñÔÿòÆ›ÿóÊ¢ÿóϪÿõÓ²ÿöØ»ÿ÷ÞÅÿøäÏÿúéÙÿûíàÿüðæÿýôëÿý÷òÿýûùÿýüûÂÿùù+þþþ?ýýýùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿþùõÿ*ÿõѯÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäääÿKKKÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒŒŒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿYSLÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóË¢ÿð½Šÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþûøÿï¹…ÿõغÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‚²ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ{\Fÿôêãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúè×ÿð¾ÿ÷ÝÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿóÊ¢ÿóÉ ÿý÷òÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþüûÿþüúÿþûøÿþú÷ÿýùôÿý÷òÿýöïÿýõíÿüôìÿûòèÿûîâÿúêÚÿùçÔÿõ×¹ÿí°tÿôͧÿõÖ¶ÿôÑ®ÿóˤÿóÆ›ÿñÁ‘ÿð½Šÿ﹄ÿî·€ÿîµ}ÿîµ|ÿîµ{ÿî´|ÿîµ}ÿï¶ÿï¸ÿﺅÿð¼ŠÿñÀÿòÄ—¢ôÉŸÿÿÿJþþþüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýøóÿÿöÖ·ÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÌÌÌÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ«««ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZTOÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿñÖÿñÕÿþþýÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿýøóÿî²yÿøãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿav…ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ»¨–ÿÿýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÉÿð¾‹ÿùäÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ¿ÿõÒ°ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿùãÎÿî´zÿúëÝÿþûøÿþú÷ÿýøôÿý÷òÿýöïÿýõîÿüôëÿûñçÿûîàÿúéØÿøäÐÿ÷àÈÿ÷ÜÁÿöØ»ÿõÓ²ÿôΨÿñÇžþñÕÿᅫ„ÔªUÿÿÿQÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿý÷òÿíµ}ÿ÷Û¿ÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿ’’’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÒÒÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZUQÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿð½‹ÿóÊ¢ÿþþýÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüôëÿí¯rÿûìßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿéþÿÿBMlÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿC#ÿâÑÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿöØ»ÿñ¿ÿúìÝÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿ﹄ÿ÷Û¿ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö×¹ÿ︃ÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþþýÿþýüÿþýûÿþüûÿþüúÿþûøÿþúöÿýùôÿýøñÿüõîjÿÿÿPÿÿÿþÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿý÷ñÿí²yÿøßÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿßßßÿ000ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZVRÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýûøÿ︄ÿõÒ°ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûíßÿí¯qÿüôíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕä÷ÿ2=Hÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‚dRÿøñëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿôЭÿñÕÿûòçÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñçÿï·ÿùäÐÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿóÉ ÿñÁ“ÿþûøÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúÿÿÿVÿÿÿTÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýöðÿí°uÿùãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿžžžÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ444ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZWTÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿî¶}ÿ÷Û¿ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùäÏÿí±vÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿºÏßÿ':ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¹¡ŒÿÿýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿóË£ÿòÉŸÿü÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúåÑÿð¹†ÿúìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿð¾ŒÿôΧÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëïùÿËÊËÿÍÌÊÿÕÓÔÿÝÙÙÿëééÿôóòÝÿû÷Aüüübÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüóêÿî°tÿùçÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚÚÚÿ(((ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿpppÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[XVÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíáÿî´{ÿùäÎÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿ÷Ù¼ÿï·‚ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ”¬Ëÿ#ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ3ÿ×̽ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿòÆ›ÿôΪÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöØ»ÿñÀ‘ÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿî¶ÿ÷Ú¾ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‡—¶ÿ((-ÿ-*)ÿ<;;ÿLDDÿeaaÿifdÝ-)%ˆeY Eÿÿÿÿÿsÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûîâÿí°uÿúëÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøøøÿrrrÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ±±±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[YWÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÓÿî´yÿúëÝÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿôΨÿñÁ‘ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‡•«ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[C4ÿôéÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿûïãÿñÁ‘ÿõÕ¶ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿóͧÿóÇžÿýöïÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÞÿî´{ÿùçÔÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚîøÿ)7Hÿÿÿÿÿÿÿÿÿÿêb)bÿÿÿ‚ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúêÙÿî±vÿûïâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¬¬¬ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðððÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[ZXÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÝÃÿí´|ÿüòèÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿòÖÿôÊ£ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿxˆ—ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‡tXÿÿüöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿñ¾Œÿ÷ÝÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÄ—ÿôΩÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿøàÈÿî´|ÿüñçÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿg„™ÿ ÿÿÿÿÿÿÿÿþÿÿê™]Dÿÿÿ’ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿùåÑÿí±xÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÑÑÑÿ$$$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿCCCÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[ZYÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿõÕµÿï·€ÿý÷óÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿðº…ÿöÕ·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùÿÿÿ`zŽÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ´•‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷áÉÿð½ŠÿùäÑÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð¾‹ÿõÕ¶ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿõÓ±ÿﺄÿýùôÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÂÕéÿ,;ÿÿÿÿÿÿÿÿÿÿþÿÿ3Ò½ZýýýÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøàÉÿî³{ÿýõðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäääÿCCCÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[[Zÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿóͨÿð»ˆÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿî²yÿøàÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿéøÿÿSe‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ%ÿп¨ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿöÙ¼ÿð¾ŽÿúëÜÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõíÿﺆÿ÷ßÇÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÆšÿñ“ÿþüúÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÿÿÿVg€ÿ ÿÿÿÿÿÿÿÿÿÿÿþÿÿD®ÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ÷ÜÁÿîµ}ÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîîîÿUUUÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿîîîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[[[ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÆšÿñÂ’ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýøôÿí®qÿúéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãëúÿM[uÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ9-ÿé×ÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿôÒ°ÿñÕÿûòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúèØÿðº†ÿúèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿjÿôΨÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ²Ëÿ*ÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþK.Šýýý ýýýþÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿêêêÿØØØÿÈÈÈÿ¹¹¹ÿ°°°ÿªªªÿ¤¤¤ÿ¡¡¡ÿ£££ÿ¤¤¤ÿ§§§ÿ¯¯¯ÿ·¸¸ÿÁÁÁÿÏÏÏÿàßàÿññðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ÷Ù¼ÿï¸ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñññÿXXXÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWWWÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGGFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[[[ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿð¿ÿòÈ ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüñçÿí­oÿüðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÜæðÿEVbÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿY:1ÿûíÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøôÿô̤ÿóÈžÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÜÂÿð¾ÿûïâÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿî¶€ÿ÷Û¿ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãðþÿCNaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿït/gä×Ȯ·­þ ™’ÿ|xtÿb_\ÿNLJÿA@>ÿ766ÿ..-ÿ%%%ÿ ÿÿÿÿÿÿÿ!!!ÿ&&&ÿ+++ÿ333ÿ<<<ÿFFFÿPPPÿaaaÿ{{{ÿ“““ÿ°°°ÿÐÐÐÿñññÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿõÕµÿﺆÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèèèÿRRRÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇÇÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGFEÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýûøÿﻆÿôЮÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúçÖÿí°tÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×áéÿ>P`ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿmZ:ÿÿýòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôëÿòÆšÿôϪÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿôÑ®ÿòĘÿüóëÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùêÙÿî´{ÿúçÖÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ{‘¥ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ# Ý—W@5o -!î(ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ...ÿ???ÿRRRÿwwwÿ£££ÿÍÍÍÿî˧ÿヒÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿ×××ÿCCCÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ999ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGFDÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõïÿî·€ÿöÙ½ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ÷ÜÁÿï¶ÿÿüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓÝåÿ7K\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿwjZÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûîâÿñÁ‘ÿõÖ¶ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÈžÿóÌ¥ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿöÜÁÿî¶~ÿüòéÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¿Íâÿ%3Gÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ$ÁÿZ'y»×íÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ)('ÿ90&ÿZH6ÿ–•”ÿÐÍÌÿþüúÿþýûÿþýüÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯¯¯ÿ000ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ³³³ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGECÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿî´|ÿøâÌÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿôЭÿñ¾ŽÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÑÚãÿ7J]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ…sdÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿùè×ÿð¼‹ÿ÷ÝÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÀ‘ÿõÔ³ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿôÏ«ÿﻈÿþùôÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìôÿÿYdzÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþD§ÿÿ>£Öðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ#ÿ;5.ÿodYÿ³£”ÿóàÎÿúêÙÿûíßÿûðäÿüòçÿüôëÿýõîÿýøòÿýùõÿþú÷ÿ~}|ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ555ÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGDAÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùèØÿî´zÿúêÙÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿòÄ™ÿóÈ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐÙâÿ7J^ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿšvjÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáËÿð¼‰ÿùäÐÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿð¼‰ÿ÷ÝÂÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòĘÿñÅ™ÿþûøÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ“£±ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿöD,©áüÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ+!ÿ_I3ÿ¬…^ÿﻆÿð¾ŒÿñÂ’ÿòÅšÿóÊ£ÿÌ­ÿH>4ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿFC?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÌÿîµ|ÿûðäÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþýÿð»ˆÿõÔ³ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÒÚâÿ8M_ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿŸwmÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿöÚ¾ÿð¾‹ÿúëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìßÿðº‡ÿùåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð¼‰ÿôѯÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÅÔåÿ.@Rÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ é‚9fÝüÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ,%ÿlZIÿÉ¥‚ÿñÕÿ‚hMÿ"ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿMLLÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿFB=ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÚ¾ÿï·ÿüóìÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþýÿî³zÿøÞÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔÜäÿ@Rcÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿŸvmÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿõÓ±ÿñÁ“ÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøáËÿð¼ŠÿúìÝÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿï·€ÿ÷ÞÅÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëøÿÿ`s„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿЋS7¶ôÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿ###ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿϼªÿùåÒÿúèØÿûëÝÿûîáÿûðæÿüóêÿýöïÿýøóÿýúöÿþûùÿþüúÿþýüÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿFA<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôѯÿð¼ˆÿý÷òÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿí¯rÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×ßæÿFXhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ’shÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿó̤ÿòÈÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöÖ¸ÿòÁ“ÿûðåÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿùèÖÿîµ}ÿúé×ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ–§´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ2 µþQ2Îýÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ{_Cÿëµÿÿ﹄ÿﺆÿð½‹ÿñÀÿñ×ÿòÈžÿóÌ¥ÿôЬÿõÓ²ÿöÖ·ÿöÚ¾ÿ÷ÞÅÿøâËÿùåÑÿúè×ÿúëÜÿûîáÿûðæÿüôëÿýöïÿýùôÿþýûÿF?9ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÉ ÿñ“ÿþúöÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýôìÿì­oÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛâèÿO`oÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿvnaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿòÅ™ÿôΪÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿô̦ÿóÉ ÿýõïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿ÷ÛÀÿï·ÿûðäÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿºÈÜÿ,Iÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ÿG)šÿÿ6Ôÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ2.+ÿèÕÃÿ÷àÈÿöÛÀÿö×¹ÿõÕ´ÿôЭÿôÌ¥ÿòÇžÿñÄ—ÿñÁ‘ÿð¾ÿð½‹ÿð¼‰ÿðº†ÿ﹄ÿ︃ÿ︃ÿ﹄ÿﻇÿð½‹ÿðÀ‘ÿñÄ—ÿòÈžÿóÌ¥ÿôÑ­ÿD7*ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿñ”ÿòÉ ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÛÿí¯rÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàçïÿYfƒÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿnaQÿÿüìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûîáÿðÀÿöÖ·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿòÖÿõÒ°ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÏ«ÿñ¿ŽÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÝçïÿK^nÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿõHq&ÌÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿËËËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþüúÿýùôÿýöïÿüóëÿûñæÿûîàÿúéØÿùäÏÿ÷àÈÿöÛÁÿöغÿõÕµÿôÑ®ÿóÌ¥ÿóÈžÿñĘÿñÁ“ÿð¿ÿC3#ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿð½ŠÿôÑ®ÿþüûÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ßÇÿï´|ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæî÷ÿa{‘ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXD2ÿòÝÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúéØÿð¼ˆÿ÷ÝÃÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöñÿð½‹ÿ÷ÜÁÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿñÄ—ÿòÊ¡ÿþúöÿÿÿÿÿþÿÿÿÿÿÿÿî÷ÿÿl€˜ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ*å=S²ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ”””ÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþûøÿýøòÿýöîÿüóéÿD:0ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[ZYÿþüúÿþýüÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõïÿ︂ÿöÙ½ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÓ²ÿñ½‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿï÷üÿwŒ›ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ4,%ÿÕÆµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùãÎÿﻇÿùäÏÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿð»‡ÿøãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùóÿﻈÿõÖ·ÿþüúÿÿÿÿÿÿþþÿûÿÿÿŽ£´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ"ÂM.~ôÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZZZÿðððÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿE;2ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWH:ÿôͨÿõÑ®ÿõÕµÿöÚ¼ÿ÷ÞÄÿøáÊÿùåÐÿúèÖÿúìÞÿûðäÿüóëÿü÷ðÿýùõÿýûøÿþüûÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñæÿîµ}ÿøàÉÿþýüÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÇÿòÇÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúþÿÿŒ™¥ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ# ÿ³—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ÷ÜÁÿð½‹ÿúëÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùæÓÿð¼ŠÿùèÖÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñæÿî·€ÿøàÈÿþýüÿÿÿÿÿþÿÿÿ¨¶ÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿD§ÿ£0Ïÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ,,,ÿâââÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿD:0ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVF6ÿñ“ÿð¿Žÿð¼‰ÿﺅÿÿï·ÿ︂ÿ﹄ÿð»‡ÿð½‹ÿðÀ‘ÿñÄ–ÿòÇœÿóÉ¡ÿô̧ÿõÑ®ÿöÕµÿöÙ¼ÿ÷ÞÄÿøáÊÿùåÑÿúéØÿúíßÿûñæÿüôìÿýøòÿýúöÿþüúÿþýüÿþÿÿÿÿÿÿÿúíàÿï¶}ÿùèØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð½‹ÿõÒ±ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿšªÁÿ-ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ}p`ÿúòçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÓ³ÿñÁ’ÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿ÷ÛÁÿñÀ‘ÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùçÖÿî¶ÿúèÖÿþþýÿÿÿÿÿ¶ÃÏÿ "ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ@$~ÿÿŽþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍÍÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿD9-ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿZXUÿüòçÿûîâÿúëÜÿùçÖÿøäÐÿøâÌÿøßÇÿöÛÀÿöÖ·ÿõÒ¯ÿóͨÿòÊ¡ÿòÇÿñÅ™ÿñÁ“ÿð¾ÿ(ÿ﹄ÿî¸ÿî·€ÿï·ÿ﹄ÿﺇÿð½‹ÿñÀÿñÔÿòÆšÿóÈ ÿôͦÿôЮÿõÖ·ÿó̦ÿî±vÿõÕµÿøåÑÿúêÚÿúîáÿüòéÿüöîÿýùôÿþû÷ÿþüúÿþþýÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿþþþÿÿÿÿÿîµ}ÿ÷ÛÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ­ÃÏÿ,5ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿN90ÿØÏÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿóË¥ÿòÇœÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÑ®ÿòÆ›ÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöÛÀÿﺅÿûðäÿþþþÿÁËÜÿ>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ#÷Z]$Äÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¶¶¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿD7+ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþüùÿýúöÿýøòÿüöïÿüôìÿûñçÿûîáÿúëÜÿùè×ÿùåÒÿøãÏÿøàÉÿ÷ÛÀÿöÖ·ÿôѯÿóͨÿòË£ÿóÈŸÿòÅ™ÿñÁ’ÿð¾Œÿﻇÿí´{ÿì­oÿîµ|ÿî·€ÿ︃ÿﺆÿð½‹ÿð¿Žÿñ”ÿñÅ™ÿóÈŸÿó̦ÿôÑ®ÿõÕµÿöÚ½ÿ÷ÝÄÿøâÌÿùæÓÿúëÜÿûïäÿüóëÿý÷ñÿýùõÿþûùÿþýûÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿí¯rÿùãÎÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýöðÿÄ¥†ÿ:ÿ×ÐÈÿýûúÿÿÿÿÿûîáÿñ¿ÿöÖ¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿñ¿ÿö×¹ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿñÕÿñʤÿÀÈÓÿAÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ6¶šI&Žÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ™™™ÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïäÿC6(ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóΨÿñ“ÿþúöÿÿÿÿÿþþýÿþüúÿýú÷ÿýùôÿý÷òÿüöïÿüóëÿûñçÿûïâÿúìÞÿúêÛÿùé×ÿøåÑÿ÷àÉÿöÛÀÿõÖ¸ÿôÒ¯ÿôΪÿóÌ¥ÿòÈžÿñÖÿð¿Žÿﻈÿÿî¶ÿîµ}ÿîµ}ÿî¶ÿî·ÿ﹄ÿﻉÿð¾ÿñ¾ÿì­nÿòĘÿôͧÿôѯÿöÖ·ÿ÷Ú¿ÿ÷߯ÿøäÏÿùéØÿûîáÿüòéÿýöïÿýùõÿþûøÿþýûÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿí³zÿúèÕÿûÿÿÿrŠÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‰{ÿìçàÿùéØÿð»‡ÿ÷ÝÂÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñæÿñ¼ŠÿøßÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿ鹉ÿ­¤šÿ !ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþ ÿO3šÌŒ©ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ”””ÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûíßÿC5(ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿòŘÿòÉŸÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþýüÿþûùÿýúöÿýùôÿý÷òÿüöïÿüôëÿûñçÿûïäÿûîáÿúìÞÿúêÙÿøåÒÿøàÈÿöÛ¿ÿõÖ·ÿõÒ°ÿôЬÿñÁÿí¯qÿñ”ÿlÿï¹…ÿî·€ÿîµ}ÿîµ|ÿîµ|ÿî¶}ÿî·€ÿ︃ÿﺇÿð½‹ÿñÀ‘ÿòĘÿòÈ ÿôͨÿõÓ°ÿö׸ÿöÛÀÿøàÉÿùæÒÿúëÜÿûïäÿüôëÿý÷ñÿýùõÿþüùÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùé×ÿî´{ÿüòçÿÿÿÿÿÿÿÿÿˆ›¸ÿ$1ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿA4%ÿ¼¤‰ÿâ®zÿùäÐÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéÙÿñ¾ÿùäÐÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèáÙÿˆ}nÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿG&kÿ™¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ———ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéÙÿC5'ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿð¾ÿôЬÿþûùÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþýÿþüûÿþûøÿýúöÿýúöÿôÒ°ÿðº†ÿüôíÿüòéÿûðæÿûïãÿûîáÿúêÙÿùäÑÿøßÇÿöÛ¿ÿöÖ·ÿõÓ±ÿôÏ«ÿóË¢ÿòÅšÿðÀ‘ÿ)ÿÿî¶~ÿî´{ÿî³{ÿî´{ÿîµ}ÿî¶ÿ︂ÿﺅÿð¼ŠÿñÁ‘ÿòŘÿòÉ ÿóΩÿõÓ±ÿöعÿ÷ÝÃÿøáÊÿôЬÿïµ~ÿúëÝÿýöðÿýøóÿýú÷ÿ·ÈØÿ2:Dÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ]B&ÿƵ£ÿðîëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿøàÉÿñÁ‘ÿúêÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûýÿÿÕÛàÿZcjÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ-ø]3Oÿÿ%Àÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ™‘ŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿùæÒÿC5'ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿﺅÿö׺ÿþüúÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÌ£ÿòÅ™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþüúÿþûøÿþú÷ÿýùõÿýøòÿýöðÿüõíÿüóêÿüòèÿüñæÿûïáÿúêÙÿùäÐÿøßÆÿöÚ½ÿõÖ·ÿõÓ±ÿóÏ©ÿòÉ ÿòÖÿð¿ÿÿî·€ÿî´|ÿí³zÿî³yÿí±uÿí­oÿî´|ÿî·ÿﺅÿð½‹ÿñÁ’ÿÑ´¤ÿMNTÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿkcVÿÈýÿíëçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÖ·ÿòĘÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâçìÿŸ¬¹ÿ!4ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿH%·D&Àÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ.$ÿ¶°ªÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÌÿC5'ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôëÿï·€ÿ÷ÞÅÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ‘ÿôϬÿÿÿÿÿÿþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþýÿþýûÿþüúÿþûøÿþú÷ÿýùõÿýøóÿý÷ñÿüöïÿüôíÿüóëÿüòéÿûîâÿùæÓÿð¿ÿð¾‹ÿöÜÁÿõÖ¸ÿõÓ°ÿóͦÿòÇÿñ“ÿ)ÿqa]ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿjbWÿÁ¼¶ÿèãÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿô̦ÿóÊ¢ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèëïÿºÁÈÿBVfÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿõbjâ8 ¹ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ%$$ÿ®®®ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÄÿC5'ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíàÿî¶~ÿùäÏÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿï·ÿöÙ½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿð¾ŽÿôÏ«ÿÿÿÿÿþûùÿþûøÿýúöÿýùôÿýøòÿý÷ñÿüöïÿ£¸Åÿ6:Cÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ]N:ÿ®¡–ÿÖÐÇÿùòêÿþüúÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿòĘÿôЭÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåéíÿºÁÆÿ^htÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ø@(w‘‘¬ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¨¨¨ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿöÚ½ÿC5(ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÒÿï¶}ÿúêÙÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþüÿî°vÿøáËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþÿÿÿÿÿÿÿÿÿÿýøòÿî¸ÿöÙ¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛäùÿ]lxÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ9)ÿ…cAÿ¸ŽgÿÙ¬ÿóÈžÿôΧÿõÒ°ÿöغÿ÷ÞÅÿùäÏÿúêÙÿûîãÿüóêÿýõîÿýøóÿþú÷ÿþýûÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿñÁ‘ÿöÙ½ÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûþÿÿØÛÞÿª²¹ÿWcmÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ üH&й\ ’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ©©©ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿõÖ·ÿD6)ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÝÃÿî·€ÿûïãÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿí®pÿúêÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿî²yÿøãÍÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿ‡š¯ÿ07=ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿU?'ÿnKÿ¸‹[ÿÕ jÿí³wÿí°uÿí°tÿí°uÿí°uÿí²xÿî´|ÿï·ÿ(ÿñÀÿòŘÿóÊ¡ÿôΪÿõÔ³ÿöÚ¾ÿøàÉÿùæÔÿúìÝÿûòèÿùãÎÿñ¾ÿ÷ÞÆÿþþýÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿýÿÿÿÜÞãÿ¹¼Äÿ‰—ÿ?ELÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ÿM+ªcgíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ°°°ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿõÒ°ÿD7*ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿõÕµÿﺆÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿí­pÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûìßÿí²xÿúëÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÈÔÝÿSapÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ# ÿXPEÿ„{ÿ²£˜ÿп®ÿïÙ¿ÿøàÉÿ÷ÝÄÿö×¹ÿôЭÿóË¡ÿòÄ–ÿð¾Œÿ﹄ÿî¶ÿî³zÿí±wÿí°tÿí¯sÿí¯sÿí°uÿí±uÿí®qÿï¶~ÿð½‹ÿñ“ÿòÆ›ÿóË£ÿôЭÿöÖ·ÿ÷ÝÂÿøãÍÿùè×ÿúíßÿûñæÿüóëÿý÷ðÿýùõÿþûùÿþýüÿÿÿþÿÿÿÿÿëíóÿÍÐÔÿ¬¯²ÿƒˆÿKOWÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ÿS3¬³z*Êÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ'''ÿ¾¾¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿóϪÿD7+ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿôΨÿð¿ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÏÿí±wÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøãÍÿîµ|ÿýõìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöþÿÿˆ–£ÿ08@ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ@<6ÿkf^ÿ‡ÿ±­¦ÿÊÇÄÿäáÜÿþûøÿþýüÿþýûÿþýûÿþüúÿýøòÿüóéÿûíàÿúèÖÿùãÎÿøâÌÿòÈžÿï·ÿòÈžÿòÈžÿðÁ’ÿð¼‰ÿî·‚ÿîµ}ÿî²yÿí°vÿì°tÿí¯rÿí¯sÿí°vÿî²yÿï¶€ÿç·…ÿϦÿ·–xÿ ‡pÿ‚paÿ[SMÿ522ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ÿN-¬£m–ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ555ÿÒÒÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿóË£ÿD8-ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿòÇœÿñÅ™ÿýùõÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÙ¼ÿ︃ÿÿýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿõغÿðº†ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÅÐÙÿ\kxÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ641ÿURNÿromÿ…ƒ‚ÿ žœÿ¶´³ÿÂÁÁÿÒÍÌÿæâàÿóñðÿüúúÿþþþÿÿÿÿÿôÒ°ÿòÅšÿýôíÿÿÿÿÿþþýÿþþýÿþýýÿöôòÿíèáÿÝÕÏÿÈ¿¸ÿ¾°£ÿ²¥˜ÿ£–ˆÿ~rÿuf[ÿdWIÿE;4ÿ)" ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ÿO/§¯i:ÙÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿJJJÿèèèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿýôíÿòÇÿD:/ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ’ÿóÌ¥ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΪÿñ”ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿóͧÿñ”ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôûÿÿ”¢¬ÿ;COÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ# ÿ.--ÿ?99ÿQNLÿ_]\ÿhffÿmmmÿqqpÿm[Iÿo\JÿsqoÿsssÿrrrÿonoÿijkÿbceÿZ[[ÿLMPÿ9:@ÿ///ÿ%&(ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ öF'”°u‡øÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿkkkÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿüñçÿñÄ—ÿD;1ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿð½ŠÿõÓ²ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿòØÿôͧÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþú÷ÿñ•ÿòË£ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐØãÿxƒÿ-ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ñ8 ªU»ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿœœœÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿð“ÿE<4ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿﺄÿöÛ¿ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð»‡ÿ÷Ö·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýúöÿﺅÿõÕ´ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúýÿÿ²¸ÆÿWbnÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ ìJj² 6×ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐÐÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúëÛÿñ¿ÿE>7ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿï·ÿ÷áËÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüüÿî³zÿøàÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿî´{ÿ÷ÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçíôÿ¦°ÿ;DQÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÔa5QÿDáÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿDDDÿ÷÷÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÖÿð¿ÿF?9ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÔÿî¶ÿùèØÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿí®qÿúéÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüòèÿí±vÿùèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×ÜäÿŒ–Ÿÿ .;ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ÿ=¼F+/?ÚÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøäÐÿð¾ŒÿF@;ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÞÆÿï·€ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿí­pÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿúè×ÿî²xÿûñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùüþÿÌÔÚÿxƒ“ÿ'ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿû:"†Œ4-ºÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞÞÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÉÿð½ŒÿFB=ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿö×¹ÿ﹄ÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÒÿî°uÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÝÅÿî¶ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôöùÿÇÌÖÿmy‰ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ Ý_+SsE yöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ***ÿ}}}ÿÇÇÇÿàààÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXXXÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ÷ÜÂÿð¾ÿFC@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿôЭÿð½Šÿýöïÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÜÂÿï·€ÿÿþýÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿôÒ°ÿð½ŒÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñóöÿÆÍÕÿgr~ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿC(©K)%ÿÿ 0¢ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿoooÿ½½½ÿâââÿôôôÿÿÿÿÿÿÿÿÿøøøÿÑÑÑÿAAAÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÃÃÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿö×¹ÿñ¿ÿGDBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÊ¡ÿñ”ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿõÒ±ÿñ¿ÿþþþÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿòÇÿòÆ›ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿòóõÿÆÈÉÿ`ZQÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ ça7af36Ÿýÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ000ÿ|||ÿÃÃÃÿæææÿóóóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïïïÿ„„„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ===ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÓ±ÿñ”ÿGFDÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÄ—ÿóÉŸÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿòÈŸÿóÈ ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþüùÿð½‹ÿóЫÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñæÿäµ…ÿɹ¤ÿox‹ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ ÿ9šU*Ìf !qÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ! ÿ`aaÿ¤¤¤ÿÚÚÚÿïïïÿöööÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿ···ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôΪÿñÅšÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿðÀŽÿõЬÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð¾ÿõÓ²ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿï¶~ÿöÙ¼ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÝÿﺅÿøàÈÿööøÿßäéÿƒ‘›ÿ'ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ0Üf6AL  #\\\£SSSýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿDDDÿwwwÿ¦‰mÿÔ­†ÿòòòÿöööÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÚÚÚÿ$$$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿBBBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿóÊ¢ÿòÉ ÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿﻈÿöغÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿîµ}ÿøÞÆÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüöïÿí²vÿùäÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùåÑÿ﹄ÿúéÙÿÿÿÿÿÿÿÿÿùùúÿîòóÿ¦¹ÿ4AOÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿîXm6$ÿôíçwôñìùóðîÿßÞÝÿ«««ÿ|||ÿUUUÿ111ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ--,ÿPPPÿrrrÿ•••ÿ»»»ÿæææÿöööÿ÷÷÷ÿúùøÿïÁ•ÿòÉ¡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçççÿ666ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÑÑÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿòÆœÿó̧ÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðåÿ﹃ÿøßÈÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿí¯tÿúéØÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûíáÿí±uÿúíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÝÃÿﻇÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüýÿùùùÿÈÒÜÿ`hoÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ÷4ƒmHóÆ˜„òÊ¡úôÏ«ÿõÓ³ÿõ×¹ÿôؽÿôÙÀÿóÛÅÿôßÊÿîÝËÿÛÎÁÿÅ»²ÿ¸°§ÿ°ª¤ÿ¨¤Ÿÿ¤¢Ÿÿ§¦¤ÿªªªÿ®®®ÿ¹¹¹ÿÆÆÆÿÓÓÓÿçççÿøøøÿùùùÿúúúÿûûûÿüüüÿýýýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýÿñ¾ŽÿôΩÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïïïÿ999ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿgggÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿüóéÿñ×ÿôЭÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéÙÿï¸ÿùæÔÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüîâÿì®pÿüòéÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿøäÏÿî´zÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿõÔ³ÿð¿ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿíòõÿ’š­ÿ4@Lÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ ö2j5UòÊ¡‘ñÄ™ûñÁ“ÿð¾ÿð¼Šÿð¼‰ÿð»ˆÿð»‡ÿð»ˆÿð¼‰ÿð½Šÿð¾ÿñ¿ÿñ“ÿòÅ™ÿóÉ ÿôΩÿõÒ°ÿöÖ¶ÿöغÿ÷Û¿ÿøÞÆÿùãÍÿúçÔÿúêÛÿûíàÿûïäÿüòêÿýöðÿýúöÿþýüÿþÿÿÿÿÿÿÿÿÿÿÿﺇÿöÕµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîîîÿ444ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿûðäÿðÁ’ÿõÕµÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÎÿ︂ÿúëÝÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÔÿí¯sÿþùöÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿöØ»ÿ﹄ÿþû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýøóÿóË£ÿòŘÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿÕßæÿi{‡ÿ-ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿë?9ýýý•ýúøûýøóÿüôìÿüñçÿûïãÿúëÜÿùæÔÿøâÌÿøÞÄÿöÚ½ÿö׸ÿõÔ³ÿôЬÿóË£ÿòÆœÿò•ÿðÀÿñ¾Žÿñ¾Œÿð¼Šÿð¼‰ÿð»ˆÿð»‰ÿð¼Šÿð½‹ÿñ¾ŽÿñÁ’ÿòĘÿóÈŸÿó̦ÿôЭÿõÒ±ÿöÔµÿí²yÿòÆ›ÿùâÍÿùæÓÿúéÙÿúìÞÿûïãÿüóêÿý÷ñÿþúøÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäääÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ§§§ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûíßÿð¿ŽÿöÚ¾ÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÜÁÿï¹…ÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÇÿîµ|ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþýüÿóͦÿñ“ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýõîÿñÕÿôΧÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýþþÿÅÌÙÿaezÿ*ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿËQ'a¢\ ÿÿÿ•ÿÿÿûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿþú÷ÿý÷ñÿüôìÿüòèÿûïäÿúëÝÿùçÕÿøâÍÿ÷ÞÇÿ÷ÜÁÿöÙ½ÿõÕ¶ÿôÑ®ÿóÌ¥ÿòÇÿñÄ—ÿñ“ÿñÁ‘ÿñ¾ÿì­oÿïµ~ÿð»ˆÿð»‡ÿð¼ˆÿð¼‰ÿð¾ŒÿñÀÿòÄ—ÿòÇÿóË£ÿôΨÿõЬÿõÓ²ÿöغÿ÷ÜÂÿøáÊÿùåÒÿùèÖÿúëÜÿûïãÿüóëÿýøòÿþüùÿþþýÿþÿÿÿÑÑÑÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿPPPÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéÙÿð½‹ÿøàÈÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõÔ³ÿð½‹ÿüóêÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÖ·ÿð¼‰ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿüüüÿûûûÿúúúÿùùùÿùùùÿñññÿÜÜÜÿÅÅÅÿ³³³ÿ£££ÿ‘‘‘ÿ………ÿ{{{ÿqqqÿiiiÿeeeÿbbbÿ___ÿ```ÿcccÿgggÿlllÿuuuÿÿŠŠŠÿ˜——ÿ bÿ±”wÿÏÏÏÿæççÿöööÿùùùÿúúúÿûûûÿüüüÿýýýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñæÿñ½ŠÿöعÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÄÍØÿes~ÿ%+5ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿgXIõªŽnfýýýÿÿÿûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿýùõÿýöðÿüôìÿüóéÿûíàÿí°sÿõÒ²ÿùäÐÿøàÉÿøÞÅÿ÷ÛÀÿö׸ÿõÒ°ÿôͧÿóÉŸÿòÅšÿòÄ—ÿñÔÿñÀÿð¾ÿð¼‰ÿð»‡ÿðº†ÿðº†ÿﺇÿð¼Šÿñ¿ÿñ”ÿòÆšÿóÈŸÿóË£ÿñ˦ÿš„oÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÓÿ*ÿùåÒÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿô̧ÿñ•ÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôˤÿòÅšÿþýüÿüüüÿùùùÿ÷÷÷ÿõõõÿêêêÿÊÊÊÿ¥¥¥ÿÿaaaÿCCCÿ&&&ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ333ÿPPPÿnnnÿ‘‘‘ÿµµµÿÛÛÛÿñññÿöööÿøøøÿúúúÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿúìÜÿﺄÿøâÌÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×ÝçÿˆŽ›ÿ?HNÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿKB8ÿ±¦™ÿùôìÿþþþÑÿÿÿÿÿÿ©þþþüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿí°tÿùæÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþûùÿýùôÿýöðÿýõîÿüóêÿûïäÿûëÞÿúè×ÿùåÑÿøâÍÿøàÉÿ÷ÝÃÿöغÿõÒ±ÿôΩÿóÊ¢ÿóÇžÿòÆ›ÿòÄ—ÿå¶‹ÿTC1ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¹¹¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÍÿ)ÿúêÛÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿòÆ›ÿòÉŸÿý÷òÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿ÷÷÷ÿä·‰ÿâÀ ÿÑÑÐÿ   ÿpppÿFFFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ...ÿXXXÿ………ÿµµµÿãããÿïïïÿôôôÿùùùÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùåÐÿ︃ÿúëÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷úþÿ²¿Æÿq}ƒÿ8>>ÿ:::ÿ999ÿ999ÿ:::ÿ;;;ÿ???ÿDDDÿHHHÿPPPÿbbbÿuuuÿ‰‰‰ÿ£££ÿ¾¾¾ÿÚÚÚÿ÷ööÿ﹆ÿöغÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŠŠŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¢¢¢ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþú÷ÿóÌ¥ÿñĘÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿóÉ ÿôͧÿþû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ”ÿöÕ¶ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿÿ÷ÞÄÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿî¶~ÿ÷ÝÅÿþþþÿÿÿÿÿÿÿÿÿ¾¾¾ÿ(((ÿÿÿÿÿÿÿÿÿÿ~~~ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¬¬¬ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕÕÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÖëëë ýýý¿ýýýþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôôôÿîîîÿçççÿäääÿåååÿæææÿéééÿñññÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüûÿî¶€ÿ÷ÜÂÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ888ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿòÆ›ÿòË£ÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿòÅšÿõÒ¯ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿð¾Œÿ÷ÜÃÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿîµ|ÿøæÒÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿî³yÿúéÙÿþþþÿÿÿÿÿßßßÿJJJÿÿÿÿÿÿÿÿÿÿcccÿöööÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôôôÿ{vqÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿTTTÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¨ÿÿÿ ÿÿÿÀÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿí´{ÿøàÉÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‡‡‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿØØØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿñÁ’ÿôÒ¯ÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûïäÿñÕÿö×¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõíÿð¼‰ÿùâÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÚÿî¶~ÿûìÞÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÎÿî´{ÿüóêÿþþþÿõõõÿwwwÿÿÿÿÿÿÿÿÿÿIIIÿèèèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÜ˼ÿG5#ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇÇÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿxÔÔÔýù÷Àýûùþÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿí³yÿøäÎÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿrrrÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ|||ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýöïÿjÿöÙ¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿñÀ‘ÿ÷ÝÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíàÿð¼‰ÿùçÕÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÎÿﺅÿûñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöغÿ︂ÿþû÷ÿþþþÿ¨¨¨ÿÿÿÿÿÿÿÿÿÿ///ÿÒÒÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ÷ÝÃÿ¶‹bÿ&&&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿDDDÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûûûOÿÿÿÄî¹…þð¾ÿñ•ÿòÇÿóͦÿôÒ¯ÿõÖ·ÿöÜÀÿ÷áÊÿùçÔÿúìßÿûñçÿüöíÿýøòÿþú÷ÿþüúÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿí²xÿùçÔÿþþþÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñññÿNNNÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ+++ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôëÿ﹄ÿøáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿùåÐÿðÀŽÿøãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÐÿð¾ŒÿúêÛÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÙ»ÿðÀÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿô̦ÿñ¿ÿþýüÿÔÔÓÿ555ÿÿÿÿÿÿÿÿÿÿ³³³ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿõЬÿòÅ™ÿ———ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÀÀÿÿÿÿÿÿÿÿÿÿÿÿÿþþþüùùù+ââÆ ô׺ÊõÕ¶ÿóϬÿòÊ¡ÿñÄ—ÿñ¿Žÿﻇÿï¸ÿîµ~ÿî³{ÿî³yÿí³xÿí³xÿí´zÿî¶}ÿ︂ÿð¼‰ÿðÀ‘ÿñÅ™ÿóÊ¡ÿôΩÿôÓ²ÿöÙ¼ÿøßÆÿøåÑÿúêÚÿûîâÿûòèÿüõíÿýøòÿþûøÿþþýÿüóëÿî²xÿúìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓÓÓÿ!!!ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞÞÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿüñæÿî¶€ÿùæÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ßÇÿðÀÿúé×ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÛÁÿñÁ“ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôΨÿóÇœÿýøòÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿñ“ÿóÉŸÿððïÿmmmÿÿÿÿÿÿÿÿÿÿ‹‹‹ÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþþþÿòÕÿöÓ³ÿñññÿihhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿBBBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛóóóïïïýûúÒþüúÿþûùÿþú÷ÿýúöÿýùõÿýøôÿýøóÿüöïÿüñçÿûìÞÿùçÕÿøãÎÿøàÉÿ÷ÝÃÿöغÿõѯÿó̤ÿòÆšÿðÁ’ÿð¾Œÿðº†ÿï·ÿî´|ÿî³yÿí±wÿí±vÿí±wÿî´{ÿî¶€ÿﺅÿð¾ÿð¾ÿí®pÿòÅ—ÿõЭÿõ×·ÿ÷ÜÂÿøâËÿùçÔÿúëÚÿûïâÿüóéÿýöðÿþùöÿþüúÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþþÿ¡  ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ˜˜˜ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûíáÿîµ|ÿúëÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿöÚ¾ÿñÁ’ÿûîâÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÓ³ÿòÆšÿüóéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÄ—ÿôЬÿýúöÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüûÿﻆÿôÓ²ÿªª©ÿÿÿÿÿÿÿÿÿÿ^^^ÿìììÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþýüÿï¶€ÿøàÈÿÿÿÿÿ×××ÿ>>>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¿¿¿ÿÿÿÿÿÿÿÿÿýýý°ìììÿÿÿÿÿÿÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþþþÿþþýÿþýýÿþýüÿþýüÿþýûÿþüúÿþüùÿþûøÿþûøÿþûøÿþùõÿýõïÿüòèÿûîáÿúëÛÿúé×ÿùæÒÿøáÉÿ÷Ú¾ÿõÕ´ÿóΪÿñ”ÿí¯rÿð½Œÿjÿ﹃ÿíµ}ÿí²xÿí°uÿí¯tÿî±uÿî³xÿîµ|ÿî¸ÿﻇÿñ¾ÿòÕÿóÈžÿôͨÿõÓ²ÿöÙ¼ÿ÷ÞÅÿøâÍÿùçÖÿúìÞÿüñæÿýöîÿýùõÿþûùÿþýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíííÿMMMÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿYYYÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿúéÙÿî´zÿûïäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿõÕµÿñÄ—ÿüóêÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿôͧÿôË£ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿð¼‰ÿ÷Ù¼ÿþüùÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿî¶}ÿ×îÿ222ÿÿÿÿÿÿÿÿÿ444ÿÏÏÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿí¯rÿúëÛÿÿÿÿÿÿÿÿÿ±±±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿFFFÿÿÿÿþþþþÿýýý”ÿÿÿ ñññÿÿÿÝþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþþþÿþþþÿþþþÿþþýÿþþýÿþþýÿþýüÿþýüÿþÿÿÿùäÏÿíµ~ÿüñæÿýúöÿý÷ñÿüôíÿüòéÿüñæÿûîâÿúêØÿùãÎÿ÷ÜÃÿö×¹ÿõÓ°ÿôΩÿóÉ ÿòÖÿð¾ÿ﹃ÿîµ|ÿí²wÿí°tÿì¯sÿí°tÿí±vÿî²zÿîµ}ÿ︂ÿð»ˆÿðÀ‘ÿòÅ™ÿóÊ£ÿôЬÿõÕ¶ÿµ¡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ###ÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿùãÏÿî´|ÿýöîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿôЭÿòÆœÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿòÇÿôϬÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿî·ÿøáËÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÞÿä¬vÿzskÿÿÿÿÿÿÿÿÿÿ¤¤¤ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìàÿî¯rÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÈÈÈÿÿÿÿÿÿÿÿrÚÚÚÿÿÿýýýÝÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâËÿî·ÿýõîÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþýÿþþýÿþþýÿþþýÿþýüÿþüûÿþûøÿþúöÿýùõÿýùôÿýöïÿüñçÿúëÝÿøæÒÿ÷àÈÿöÛÀÿõÖ¸ÿôÑ®ÿóÊ¢ÿñÄ—ÿð¾ÿÿîµ}ÿÙ£nÿI5#ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíííÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÝÄÿï¶ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿó̤ÿóË¢ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿñÕÿõÕ¶ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿï¶ÿúèÖÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáËÿ·‹aÿ ÿÿÿÿÿÿÿÿÿqqqÿôôôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÊÿï¶ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿîîîÿSSSÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿSSSÿÿÿÿÿûûûIÿÿÿþþþþþþßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÄÿﺅÿý÷òÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþüúÿ¥‘|ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ¹Ÿ„ÿõ×¹ÿ÷ÝÃÿùãÎÿúé×ÿûíßÿüðäÿüóêÿüôìÿôÔ³ÿ︃ÿþþüÿÿýýÿÿþýÿÿþþÿÿÿþÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿòÆ›ÿôϪÿþüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿñÀÿ÷ÛÀÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÕÿ﹃ÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçɬÿI8(ÿÿÿÿÿÿÿÿÿ<<<ÿÔÔÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÒ±ÿò”ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÏÏÏÿ---ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×××ðÿÿÿ(øøø)þþþâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöØ»ÿ)ÿýøôÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿγ˜ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ•sRÿï¶ÿî³yÿî±vÿí°tÿí°sÿí°uÿì³xÿí´|ÿí±wÿí¯tÿñÁ’ÿòĘÿóÉ¡ÿôϪÿõÕ¶ÿ÷Û¿ÿøàÈÿF@:ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïäÿñ”ÿõÕ´ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïäÿð¿ŽÿøâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿ÷ÝÄÿð½‹ÿüòçÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿüüüÿ¢‡lÿÿÿÿÿÿÿÿÿÿ   ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿñŘÿõЮÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ   ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ```çóóóúúú8ýýýåþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÒ±ÿð¿ÿþùõÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿß½œÿZG5ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€€ÿþú÷ÿý÷ðÿüòèÿûïãÿúíÞÿúèØÿøãÍÿöÛ¿ÿjÿî¶}ÿóͨÿòÆ›ÿñÁ’ÿð½Šÿÿí´|ÿí±wÿB1 ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÝÿð¿ŽÿöÚ¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúæÕÿñÀÿúèÖÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÓ²ÿñÖÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëëëÿ( ÿÿÿÿÿÿÿÿÿeeeÿôôôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ︂ÿ÷ÝÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿkkkÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÿÿÿGÿÿÿèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóͧÿñÕÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿìÅžÿ‹pVÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿjjjÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿóÈŸÿòÈžÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿþúøÿýùôÿý÷ñÿGDBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>>ÿþýûÿþýüÿþýýÿþþýÿþþþÿþþþÿÿþþÿþþþÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÖÿð½‹ÿøáÉÿÿÿÿÿþÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÆÿñ”ÿûíßÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÉ ÿóÌ£ÿýøóÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿŽÿÿÿÿÿÿÿÿÿ...ÿÃÃÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿí°rÿùæÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìììÿ<<<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿù nÿÿÿSÿÿÿêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÇÿòÆœÿþüùÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýÿñĘÿ¬ŽqÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXXXÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþùöÿñÁ’ÿóΩÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ<3*ÿö׸ÿöÝÂÿøâÌÿùçÕÿúëÝÿûîâÿüñæÿüôëÿüõïÿý÷ñÿþùôÿþû÷ÿþû÷ÿþüùÿþüúÿþýûÿþýüÿþýýÿÿÿÿÿùäÏÿð½ŠÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿö׸ÿòÅ™ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿðÀ‘ÿõÓ³ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèèèÿÿÿÿÿÿÿÿÿÿ‚‚‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿí®pÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÆÆÆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÆüüü]ýýýìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ”ÿóË¢ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿðÀÿ»ŸƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿMMMÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿð½ŠÿõÖ¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;-!ÿï·ÿîµ|ÿî³yÿí²xÿí²wÿî²xÿíµ|ÿï·€ÿﻆÿð¾ŒÿñÁ“ÿòÆ™ÿòÊ¢ÿôЫÿõÕµÿöÛ¾ÿøßÇÿøäÏÿúéÙÿõÒ²ÿﻇÿøàÉÿüõîÿýõîÿý÷ñÿýøòÿýùõÿþú÷ÿþûøÿþüúÿþüûÿþýûÿþýüÿþþýÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôÑ­ÿòÇÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿﻇÿ÷ÜÂÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿ„„„ÿÿÿÿÿÿÿÿÿCCCÿàààÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÒÿï³zÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿç>üüüaþþþíþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿð¾ŽÿôΩÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿﻇÿÀ§ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿüöïÿ︃ÿ÷ÞÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿþýûÿý÷òÿüòéÿûîâÿúêÜÿùèÖÿ÷âÌÿ÷ÜÁÿõÕµÿóϪÿòÊ¡ÿòÆ™ÿñ“ÿð¾Œÿï¹…ÿî¶€ÿí´|ÿí³yÿî³yÿí°sÿí¯rÿî¶ÿﺆÿjÿðÀÿñÄ—ÿòÉŸÿôͨÿôÒ°ÿõ×¹ÿöÛÀÿ÷ßÇÿøãÍÿùæÓÿúêÛÿúîáÿûðæÿüóêÿýõìÿýöðÿý÷òÿýùõÿýúöÿþûøÿþûùÿþüúÿþýûÿþýüÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÌ¥ÿóÊ£ÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿÿøäÏÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèèèÿ ÿÿÿÿÿÿÿÿÿ–––ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÕ¶ÿñ¿ŽÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿSSSÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿø˜ÿÿÿlýýýïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿð¼ˆÿõÒ°ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùöÿÿÀª”ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿIIIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüóëÿîµ~ÿøåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿþûøÿýøòÿüôíÿüòéÿúíßÿóˤÿð¼ˆÿöÙ¼ÿöÙ¼ÿõÓ²ÿôÏ«ÿóÊ¢ÿòÅ™ÿñÀ‘ÿð¼‰ÿ﹄ÿî·€ÿîµ~ÿîµ}ÿîµ}ÿî¶~ÿï¸ÿ﹄ÿﻈÿñ¾ÿñÔÿòÆšÿóË¢ÿôÏ©ÿõÓ°ÿõÖ·ÿöÚ¿ÿøàÇÿùäÏÿúèÖÿúëÝÿûîâÿûðåÿüòêÿýõîÿòĘÿôͧÿýõîÿýú÷ÿþú÷ÿþûùÿþüûÿþýüÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿúëÜÿ﹃ÿùéØÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿ€ÿÿÿÿÿÿÿÿÿNNNÿóóóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÆ›ÿóͧÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿêêêÿ(((ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÖÿÿÿzÿÿÿòþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ﹄ÿö׸ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷óÿïµ~ÿ»©—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿOOOÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûðåÿî³zÿúëÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýú÷ÿôÏ«ÿóÉ¡ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþüûÿþû÷ÿýùõÿý÷ðÿüòèÿúìÞÿùæÔÿøáËÿ÷ÝÂÿöØ»ÿõÓ²ÿôΨÿóÈžÿñÖÿð¿Žÿð¼‰ÿï¹…ÿ︂ÿï·€ÿî¶~ÿî·ÿî·ÿ﹃ÿﻆÿð½‹ÿñ¿Žÿî²xÿﻈÿóË£ÿóϪÿõÓ²ÿöØ»ÿ÷ÝÄÿøâÌÿùæÓÿùé×ÿúëÜÿûíáÿûðåÿüóéÿüôíÿýöïÿý÷ñÿýùôÿýúöÿþûøÿþüúÿþýüÿþþýÿþþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÍÿ)ÿûîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíííÿ ÿÿÿÿÿÿÿÿÿ£££ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿ﹄ÿöÚ½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¹¹¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿë_ýýý‰ÿÿÿõþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýüúÿï·€ÿ÷ÛÁÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõìÿî³zÿ¨š‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ^^^ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûíßÿí²xÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿòÉŸÿôͧÿÿþýÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿýøóÿüôëÿúîáÿùéÙÿùæÒÿøáÊÿöÜÁÿõ׸ÿóÊ¢ÿîµ}ÿð¼‰ÿñÄ–ÿñ¿ÿð¼‰ÿﺆÿÿï·ÿï·€ÿî¸ÿ︂ÿﺅÿ)ÿð¿ŽÿñÂ’ÿòŘÿóÉŸÿôͧÿôÒ¯ÿõ׸ÿöÜÀÿøßÈÿùãÍÿùåÒÿùè×ÿúëÜÿûîàÿüðäÿüòèÿüôëÿüöîÿý÷òÿýùõÿþþþÿö׸ÿðÀ‘ÿüñæÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿŠŠŠÿÿÿÿÿÿÿÿÿQQQÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿí°tÿøãÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿwwwÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý®ÿÿÿ—ýýýøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿîµ|ÿøáÊÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïäÿâ«sÿwnÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿpppÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿúèÖÿí³yÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿòŘÿõÓ±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿòÖÿúè×ÿÿÿÿÿÿÿÿÿþýüÿýùóÿüôëÿûïãÿúìÝÿùèÖÿùâÍÿ÷ÝÃÿõ×¹ÿôѯÿóͧÿòÉ¡ÿòÆšÿñÁ”ÿð¿Žÿð¼‰ÿ﹄ÿ︃ÿ︃ÿ︃ÿ﹄ÿﺆÿ)ÿð¾ÿñÁ‘ÿòÄ—ÿòÈÿóÌ¥ÿôЬÿö׸ÿð¿ÿðº†ÿöØ»ÿøáÌÿùäÐÿùèÖÿúëÜÿûíàÿûðäÿüñèÿüôëÿýöïÿýøòÿýùõÿýú÷ÿþûùÿþýûÿþþýÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöööÿÿÿÿÿÿÿÿÿÿ¨¨¨ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿí®pÿûïäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ===ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ×!ÿÿÿ¢ÿÿÿúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýôìÿî³zÿøæÒÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÛÿÔ lÿLHDÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‹‹‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøâËÿîµ}ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûîâÿñÁ’ÿöغÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùãÍÿòÄ–ÿúêÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýûøÿý÷ñÿüóëÿüñçÿûîâÿùêÚÿøåÐÿ÷߯ÿöÚ½ÿõÕµÿôÒ¯ÿôΨÿóÉ ÿòÅ™ÿñÁ’ÿð¾ÿí°sÿî´{ÿﺆÿﺇÿﺆÿð»‡ÿiÿð¾ÿñÀÿñÔÿñÆšÿóÈŸÿó̦ÿôЫÿôÓ°ÿõÖ·ÿ÷Ù½ÿ÷ÞÄÿøáËÿùåÐÿùçÖÿúêÚÿûìßÿûïäÿüòèÿüôìÿüöïÿý÷òÿýùõÿþûøÿþüûÿ  ŸÿÿÿÿÿÿÿÿÿLLLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéÙÿî²wÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿáááÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿílÿÿÿ¦ÿÿÿûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñæÿí²xÿùêÙÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÓÿÀbÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿªªªÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÛÀÿ︂ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúëÛÿð¿ÿ÷ÝÃÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿ÷ÜÂÿòÆšÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿþüúÿýøòÿð¾ŒÿõÒ°ÿûîáÿúìÞÿùçÔÿøáËÿ÷ÞÅÿöÛ¿ÿöÕ·ÿõѯÿó̦ÿòÈŸÿòÅ™ÿñ•ÿðÀ‘ÿð¿Žÿð½‹ÿð¼‰ÿð¼ˆÿ)ÿð½Šÿð½‹ÿð¾ŽÿñÀ‘ÿñÕÿñÅ™ÿòÈžÿóË£ÿôÏ©ÿõÓ±ÿôÕ¶ÿ/)$ÿÿÿÿÿÿÿÿÿ ›•ÿýöðÿýøôÿþûøÿþüûÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿöÙ½ÿð»ˆÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¥¥¥ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ°ÿÿÿ¦ÿÿÿûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿí²xÿûíßÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÛÅÿ‰gFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÑÑÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿõÕ´ÿð½‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÓÿð½‹ÿøãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöÖ·ÿóÇÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿﻈÿ÷àÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþýüÿþû÷ÿý÷ñÿüòéÿûíáÿúêÙÿùæÓÿøãÍÿ÷ÞÅÿöÙ½ÿõÕµÿôЬÿó̦ÿóÊ¡ÿòÇÿòÄ—ÿñÁ’ÿº”nÿÿÿÿÿÿÿÿÿ<0%ÿíÁ–ÿóÈŸÿó̦ÿôÑ­ÿõÔ´ÿöغÿöÛÀÿøÞÅÿøáËÿùäÑÿúç×ÿúëÜÿúíàÿûðåÿüóéÿýõîÿýøóÿþú÷ÿþüúÿþýüÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÉ¢ÿóÉ¡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿbbbÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÓ#ÿÿÿªÿÿÿûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìÞÿî´zÿûïäÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿØÀ©ÿ/$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿôΨÿñ•ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÉÿð½ŒÿúéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôϪÿóÉ¡ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðäÿﺅÿùäÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿýøòÿWURÿÿÿÿÿÿÿÿ ÿ‰vbÿóͨÿóÉ¡ÿòÆšÿñ”ÿðÀÿð¿Žÿð¾ÿð½‹ÿð¼Šÿð¼Šÿð¼Šÿð¾Œÿð¿ŽÿñÁ“ÿòĘÿòÇÿóË£ÿôΩÿôÑ®ÿõÔ³ÿö×¹ÿ÷Ú¿ÿ÷ßÅÿøâËÿùåÑÿúèÖÿúëÜÿûîáÿüôìÿﺆÿõÒ°ÿýùõÿþú÷ÿþüùÿþýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿ...ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿêfÿÿÿ²þþþüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿîµ|ÿüñçÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿüüüÿŠvÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ222ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþüúÿòÈžÿóÉŸÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿöÚ¿ÿð¿ŽÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿóÈŸÿôΩÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÔÿð»ˆÿúêÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíííÿÿÿÿÿÿÿÿÿ111ÿéééÿÿÿÿÿþþþÿþû÷ÿý÷ñÿüôìÿûòèÿûïãÿúëÜÿùæÔÿøâÌÿ÷ÞÅÿöÛ¿ÿöغÿõÔ´ÿôЬÿóˤÿòÈžÿñÅ™ÿñÖÿñ“ÿñÀÿð¾Žÿð¾Œÿð¾‹ÿð½Œÿð¾ÿð¿ÿñÁ’ÿñÆ™ÿí¯rÿjÿòÉ¡ÿó̦ÿôÏ«ÿõÔ²ÿö×¹ÿöÛ¿ÿ÷ÞÅÿøáËÿùäÐÿùè×ÿúìÝÿûïãÿüòçÿüôìÿý÷ðÿýùôÿþûøÿþýüÿÒÒÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¢ýýý¼ýýýþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùãÍÿï·€ÿüóëÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÜÜÜÿ("ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿmmmÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþûùÿñÕÿôÏ©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿöÖ¶ÿñ“ÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿòÄ—ÿõÕ´ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿ÷ÝÃÿð¾ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿpooÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿþú÷ÿýøóÿý÷ðÿüôìÿûñæÿûìÞÿùè×ÿùåÑÿøâÌÿ÷ßÇÿöÛÀÿö×¹ÿôÏ«ÿì­nÿòÉŸÿóÊ¢ÿòÈŸÿòÅ™ÿñÕÿðÁ‘ÿð¿ÿð¿ÿð¾Žÿð¿Žÿð¿Žÿñ¿ÿñÀÿñÁ’ÿñÕÿñÅ™ÿòÈŸÿóÌ¥ÿôЬÿõÔ²ÿŽ|jÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÉÿÿÿýýýÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÄÿﺅÿüõîÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöööÿ{{{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯¯¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿýùöÿï¾ÿõÕµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿõѯÿòÅ™ÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿò”ÿ÷ÛÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿõÔ³ÿñÄ–ÿüóêÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ000ÿÿÿÿÿÿÿÿ ÿÌÌÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿí°tÿüöïÿþûùÿýùõÿüöïÿüòéÿûïâÿúëÝÿùéÙÿùæÔÿøâÍÿ÷ßÅÿöÛ¿ÿö×¹ÿõÔ´ÿõÒ°ÿôϪÿóˤÿòÈžÿòÅ™ÿñÖÿñ“ÿP@0ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿáQýýýÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÙ¼ÿð½Šÿý÷ðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿµ¶¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîîîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿý÷ñÿﺅÿ÷ÜÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿóͨÿóÉ ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíàÿòÕÿøáËÿÿÿÿÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóˤÿòÊ¢ÿýöðÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔÔÔÿÿÿÿÿÿÿÿÿIIIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿøÝÅÿ﹃ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿþú÷ÿý÷ñÿüôìÿüñèÿûïãÿéÛÏÿ'$!ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿø‡ÿÿÿÒÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÕ´ÿðÀÿýøóÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔÔÔÿ###ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿAAAÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüôìÿï¶~ÿùäÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿüõíÿóÉŸÿôΩÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùçÖÿñ×ÿùæÔÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ×ÿôѯÿýùöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿtttÿÿÿÿÿÿÿÿÿžžžÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôͨÿòÄ™ÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÀÀÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ³¿¿¿ÿÿÿÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÑ®ÿñÕÿýúõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãããÿJJJÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ›››ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûñæÿî³yÿúëÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿûñæÿñÄ—ÿõÔ³ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿøàÊÿòÄ—ÿûìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúøÿð¿ÿöÙ¼ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ###ÿÿÿÿÿÿÿÿ'''ÿïïïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿñ¿ÿõÒ±ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ………ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÎ/ÿÿÿýýýÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿôͨÿñÆ›ÿýúöÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿêêêÿbbbÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿìììÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûíàÿí²wÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿûíßÿñÁ’ÿ÷ÛÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÙ¼ÿòÆ›ÿüñèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿð¼Šÿ÷ßÈÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿËËËÿÿÿÿÿÿÿÿÿ]]]ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿï´{ÿøàÊÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿOOOÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæ^ÿÿÿ ÿÿÿÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñññÿâââÿ×××ÿÍÍÍÿÄÄÄÿ¾¾¾ÿºººÿ¶¶¶ÿ´´´ÿµµµÿµµµÿ···ÿ¼¼¼ÿÂÂÂÿÇÇÇÿÏÏÏÿÙÙÙÿãããÿíííÿüüüÿÿÿÿÿóÉ ÿóÊ¢ÿþû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëëëÿiiiÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿUUUÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúéÙÿí±wÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùé×ÿð¿ÿøâËÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÒ¯ÿóÉ ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿð¼‰ÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿuuuÿÿÿÿÿÿÿÿÿµµµÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûúÿí®qÿûíàÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÜÜÜÿ$$$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýŠùùù0ýýýÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäääÿÉÉÉÿ±±±ÿ™™™ÿ‚‚‚ÿkkkÿUUUÿDDDÿ666ÿ'''ÿÿÿÿÿÿÿÿÿ$$$ÿ,,,ÿ999ÿGGGÿVVVÿfffÿ{||ÿ’’’ÿœ~bÿ¯”yÿÌÉÇÿäääÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâââÿeeeÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÂÂÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøäÏÿî³zÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿøäÏÿð¾Œÿúé×ÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿóÊ£ÿôͨÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâËÿð¾ŒÿúëÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ+++ÿÿÿÿÿÿÿÿ%%$ÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðæÿí¯rÿýöñÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯¯¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ¯ÿÿÿ@þþþâÿÿÿÿöööÿÉÉÉÿ¢¢¢ÿ}}}ÿUUUÿ333ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ887ÿUUUÿqqpÿÿ­­­ÿËËËÿëëëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÑÑÑÿSSSÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ444ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ÷ÝÄÿî·€ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿøßÇÿñ¾ÿûïâÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿòÅšÿõÓ²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöØ»ÿðÁ‘ÿûðäÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛÛÛÿ ÿÿÿÿÿÿÿÿ_^^ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÌÿïµÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿzzzÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÈ+ÿÿÿLÊÊÊê———ÿcccÿ555ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ777ÿXXXÿ|||ÿ£££ÿËËËÿôôôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ³³³ÿ===ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ®®®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿõÖ¸ÿ)ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷Û¾ÿñÀÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿñ•ÿöØ»ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿôÑ­ÿòÆšÿüôëÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ®®­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÒ°ÿñÀ‘ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿêêêÿIIIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿßRB333¯555ùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ666ÿ[[[ÿ†††ÿ···ÿêêêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöööÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ222ÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿôÏ«ÿñ”ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÕµÿñ”ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿñ”ÿ÷ÝÃÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÉ¡ÿóÌ¥ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿIIIÿÿÿÿÿÿÿÿÿôôôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿòÄ–ÿôΪÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÉÉÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøx7“Õÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ%%%ÿIIIÿxxxÿ²²²ÿðððÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍÍÍÿ___ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ´´´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþüûÿòÉŸÿòÉ¡ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿôΩÿòÆ›ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿñ”ÿùâÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿñÄ—ÿõÓ±ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿÿÿÿÿÿÿÿÿHECÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿð¸ÿ÷ÝÄÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿžžžÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ™ wÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"""ÿHHHÿ{{{ÿÅÅÅÿëëëÿÿ555ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿIIIÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþüúÿñÄ–ÿôÑ­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿòÉŸÿóˤÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùäÎÿò•ÿúèØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿñÀÿöÚ¾ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÃÃÃÿÿÿÿÿÿÿÿÿŒˆ…ÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿí±tÿúëÝÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòòòÿmmmÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ±'¦ôÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ,,,ÿ@@@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍÍÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþûøÿð¿ÿõ×¹ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿñÕÿôÒ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿ÷ÝÃÿòÖÿûïäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿð¾ŒÿøáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ………ÿ ÿÿÿÿÿÿÿ ÿÑÍÉÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿí®rÿüöðÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿØØØÿ@@@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÉ2;Àÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€€€ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýùôÿﺆÿöÝÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿð¿ŽÿöغÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÕ·ÿóÆ›ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÔÿð¾ÿúæÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿKKKÿÿÿÿÿÿÿÿÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÓÿî´{ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿµ´³ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿßP=Êÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ555ÿèèèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüöîÿî¶~ÿøãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûíßÿð½‰ÿøÞÅÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿôÏ«ÿóÊ¢ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÄÿð¿ÿúìÞÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ!!!ÿÿÿÿÿÿÿÿQH?ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö×·ÿð½ÿþûùÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøðèÿƒbCÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿók+ÄÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÃÃÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüñèÿî³yÿùëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúéØÿð»ˆÿùäÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿóÊ¢ÿôÏ«ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÕ¶ÿñ•ÿûðæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔÔÔÿÿÿÿÿÿÿÿÿ‹€vÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿóÈŸÿóʤÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéØÿÙ¤oÿ]YTÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ† «ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‘‘‘ÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûíàÿî±wÿûòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùãÏÿð»ˆÿûëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ðÿòÇœÿõÔ´ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÏ«ÿòÇÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¤¤¤ÿÿÿÿÿÿÿÿÿĺ°ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ»‰ÿ÷Ù½ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿ÷ÛÀÿï·€ÿǾÿ333ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿzôÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ___ÿìììÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿþþþÿùèÖÿí±vÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÝÄÿð½ŒÿûñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñçÿòÄ—ÿ÷Ù½ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÉ¡ÿóͨÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿuuuÿ ÿÿÿÿÿÿÿ ÿùðçÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüûÿí³yÿùè×ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôΨÿñÀÿþýüÿ£££ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ°0Ìÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ221ÿÛØÖÿþüùÿþüúÿþüúÿþýûÿþýüÿþýüÿþþýÿþþýÿþþþÿþþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÍÿî²xÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿþÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿö×¹ÿñÀÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿò“ÿøßÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿñÄ—ÿõÕ´ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿIIIÿÿÿÿÿÿÿÿ/&ÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýóëÿí¯sÿüôëÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÁ’ÿôΨÿÿÿÿÿøøùÿwwwÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÃ.‹ýÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ½•oÿñ”ÿòÆ›ÿóÊ¢ÿôЬÿöÖ·ÿ÷ÜÂÿøáÊÿøäÏÿùçÔÿúëÛÿûðãÿüôìÿý÷óÿýùõÿýùõÿýúöÿöÝÂÿîµ|ÿÿþýÿþüûÿþýûÿþýüÿþýüÿþþýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôѯÿñĘÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÒÿñÁ’ÿùæÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿñÀ’ÿ÷ÛÁÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ'''ÿÿÿÿÿÿÿÿ^N>ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿî³yÿýùôÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿ︂ÿ÷ÜÂÿÿÿÿÿÿÿþÿáááÿLLLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÖC#Âÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¬—‚ÿóЮÿó̦ÿòÈžÿñÖÿð¾ÿðº†ÿï·€ÿî´|ÿí³zÿí²xÿí³xÿî³zÿîµ}ÿî·ÿï¹…ÿð½‹ÿñ“ÿﺅÿî±wÿôÕµÿõغÿöÛ¿ÿ÷߯ÿøäÏÿúêÙÿûïãÿüôëÿý÷ðÿý÷ñÿGEDÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿó̤ÿóÉ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøàÈÿñÁ‘ÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿð¿ÿøâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåååÿÿÿÿÿÿÿÿÿ‰vdÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿ÷ÛÀÿð¼ˆÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿî³yÿúçÖÿÿÿÿÿÿÿÿÿÿÿÿÿ¸¸¸ÿ&&&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæU^çÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¤¤¤ÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþýÿþüúÿþûöÿýøóÿüõîÿûñæÿúëÝÿùæÓÿøáÉÿöÛ¿ÿõÖ¶ÿôЭÿóˤÿ︀ÿî²wÿð¾Œÿﺄÿï·ÿî¶}ÿí´{ÿí³yÿî²yÿî³yÿîµ|ÿï¸ÿC5&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüõíÿòÆ›ÿôϪÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿ÷ÛÁÿò“ÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÍÿðÀÿúé×ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÃÃÃÿÿÿÿÿÿÿÿÿµ¢ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôͨÿòÈžÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúèÕÿî³zÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒŒŒÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõfÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿšššÿúúùÿÿþÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóË¢ÿòÈÿÿÿÿÿÿýûÿþú÷ÿý÷ñÿüòéÿúîàÿúè×ÿøãÎÿ÷ßÅÿöÚ½ÿE;2ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿñ“ÿõÕµÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö×¹ÿòĘÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÚ¿ÿðÁ’ÿûíàÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ   ÿÿÿÿÿÿÿÿÿÝÌ»ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÀ‘ÿöÖ·ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿöÚ½ÿ﹄ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷÷÷ÿ```ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿx¨ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ–––ÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿÿÿþýüÿñÕÿôÏ«ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ=94ÿúìÝÿûïäÿûñæÿüòèÿüóêÿüõíÿýöðÿýøóÿýùõÿýúöÿþûøÿþüûÿþþýÿÿÿÿÿÿÿÿÿûðäÿð¾ÿ÷ÝÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþüÿõÒ¯ÿóÈ ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõÔ´ÿñÄ—ÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‚‚‚ÿ ÿÿÿÿÿÿÿ ÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿï¶ÿùãÏÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÌ¥ÿñÄ–ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔÔÔÿ999ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ‡¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ˜˜˜ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð½‹ÿö׸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ:-ÿï·ÿî·‚ÿï¹…ÿð¼‰ÿð¿ÿñÄ–ÿòÈžÿóͦÿôЭÿôÓ±ÿö׸ÿ÷ÜÁÿøáÊÿùæÓÿúêÛÿ÷ÝÃÿ﹄ÿöØ»ÿüôëÿüóêÿüõíÿýöðÿý÷òÿýùôÿþû÷ÿþüúÿþýýÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿýøôÿôË¥ÿôϪÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΪÿóÉŸÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿfffÿÿÿÿÿÿÿÿ'ÿüñçÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿí±vÿûðäÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþüÿð¿ÿôЮÿÿÿþÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¥¥¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ”%ÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŸŸŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿ﹃ÿ÷ÞÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ=:6ÿùæÒÿøáÊÿ÷ÝÃÿöØ»ÿõÓ²ÿôΩÿóÊ¡ÿòÆšÿñ”ÿñ¿ÿð½‹ÿðº†ÿ︃ÿî·€ÿî·€ÿî³zÿí®qÿ﹄ÿñÀÿñÖÿòÇœÿóÊ¢ÿôͦÿôЭÿõÕ´ÿöÙ¼ÿ÷ÝÄÿøáÊÿùãÎÿùåÒÿùèÖÿúëÛÿûíáÿûðåÿüòèÿüóêÿüõîÿý÷ñÿýùõÿþûøÿþüúÿþüûÿþýüÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôíÿóÈžÿö׸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿòÈ ÿôϪÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿIIIÿÿÿÿÿÿÿÿE8+ÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿî³xÿýöïÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿî·€ÿ÷ÞÅÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿtttÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¢'Áÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ111ÿÁÁÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿîµ}ÿøãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþüúÿýùõÿüõîÿûñæÿúíàÿùèÖÿôЭÿïµ~ÿõÕµÿöØ»ÿõÓ±ÿôΪÿóÊ£ÿòÇÿñÄ–ÿñÀ‘ÿð½Œÿﻇÿﺅÿﺅÿﺆÿﻈÿð½‹ÿð¾ŽÿñÂ’ÿñÖÿòÅ™ÿòÉŸÿôÌ¥ÿôЬÿõÔ³ÿõÖ·ÿöØ»ÿ÷ÛÁÿøàÈÿùäÏÿúèÖÿúëÛÿúìÞÿûðäÿùãÎÿñ“ÿöØ»ÿþû÷ÿýøôÿýúöÿþûùÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿòÄ—ÿöÖ·ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ333ÿÿÿÿÿÿÿÿcRBÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿøßÇÿﻇÿýøòÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüïäÿî´yÿúéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòòòÿIIIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯ºÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"""ÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôëÿí³yÿúè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿEEEÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ÷ÜÁÿð¾ÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿþúöÿý÷òÿüõìÿüòçÿûîáÿúêÚÿùåÒÿøáÊÿ÷ÜÁÿöغÿõÓ´ÿôЬÿóÌ¥ÿóÇžÿòÅ—ÿñÁ“ÿð¿ÿð¾Œÿð¼‹ÿ)ÿ)ÿð¼‰ÿjÿð¾ŒÿðÀ‘ÿð½Šÿî³yÿñ¿ÿôͧÿóΨÿôЭÿôÔ³ÿöØ»ÿ÷ÝÄÿøâÌÿùåÑÿùæÔÿúèØÿúëÜÿûîáÿûñæÿüôëÿüõîÿý÷ñÿýùöÿþüúÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðäÿñ“ÿ÷ÞÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ***ÿÿÿÿÿÿÿÿ|l[ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿõÒ±ÿòÆšÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùæÒÿïµ|ÿüñèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÅÅÅÿ***ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¸% ¬ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯¯¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿî±vÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿCCCÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿöÕµÿñÁ‘ÿýùöÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþüúÿþúøÿýùóÿýõîÿûòçÿûíàÿùèØÿøåÑÿøáÉÿ÷ÝÃÿöÚ¾ÿòÈžÿî´{ÿòÅšÿóÉ¡ÿòÆ›ÿñÖÿðÁ‘ÿð¾ÿð½Šÿð»ˆÿﺇÿﻈÿð¼‰ÿð¿ÿñÁ‘ÿñÄ—ÿòÇœÿòÉŸÿó̤ÿóϪÿõÓ±ÿöÖ¸ÿöÛ¿ÿ÷ÝÄÿøàÈÿøâÌÿùäÑÿúè×ÿúëÝÿûîáÿûðåÿüòéÿüõîÿþûøÿùåÑÿðÀ‘ÿøäÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîîîÿ&&&ÿÿÿÿÿÿÿÿ•…vÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÅ™ÿõÒ±ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöØ»ÿð»ˆÿþùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÂ.“ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ°°°ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéÙÿî±uÿýõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿBBBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿôϬÿñÅ™ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùâÌÿñ¿ÿûñçÿÿÿÿÿþýûÿýú÷ÿý÷ñÿüóëÿûðãÿúëÜÿùèÖÿùäÐÿøàÉÿ÷ÜÁÿöغÿõÔ´ÿôÑ­ÿóͧÿòÊ¢ÿòÆœÿòÄ–ÿðÀ‘ÿð¾ÿð½Šÿð½‹ÿkÿð½Œÿð¿ÿñÁ’ÿñ•ÿñÄ—ÿòÅšÿóÈžÿóͧÿñÖÿîµ~ÿòÉ ÿöعÿöÙ½ÿ÷ÝÃÿøáÊÿùåÑÿùçÕÿúéÙÿúìÞÿûïäÿüóêÿýöïÿýøòÿýùõÿþûøÿþýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÝÝÝÿ"""ÿÿÿÿÿÿÿÿ«ž‘ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿð¹…ÿøßÈÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÊ¢ÿñÆšÿþýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ___ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÊ6hîÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¸¸¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÍÿî²wÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ@@@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýöðÿóÉ ÿóˤÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿ÷Û¿ÿñÀÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþýüÿþúøÿýøóÿýõíÿüòèÿûïãÿûìÝÿùè×ÿùäÐÿøàÉÿ÷ÜÂÿöÙ¼ÿõÕ¶ÿõÒ¯ÿôΩÿó̦ÿﻇÿî³xÿðÀÿñ”ÿñÀ‘ÿñÀÿð¿Žÿð¿Žÿð¿ÿñ¿ÿðÀ‘ÿñÕÿòĘÿòÇÿòÉ ÿòÊ£ÿóͧÿôÑ®ÿöÕµÿöÙ½ÿ÷ÝÃÿøßÈÿøâÌÿùåÒÿúéÙÿûíßÿüðåÿÊüÿÿÿÿÿÿÿÿÿ¾µ¬ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿî³zÿúëÜÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýúÿð¾ÿôÒ²ÿþþþÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèèèÿ888ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÒ=.Ëÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ'''ÿÄÄÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÂÿîµ|ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿñÖÿõÓ±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿõÔ´ÿòĘÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿÿÿÿÿõÒ°ÿñÖÿúìÞÿüôíÿûïäÿûìÞÿùè×ÿùåÑÿøáËÿ÷ÞÅÿöÚ¾ÿö׸ÿõÓ±ÿôϬÿóͧÿóÊ¢ÿòÇÿòĘÿò”ÿðÀÿð¾ÿð¾Œÿð¾‹ÿð½Œÿð¾ŽÿñÀÿñ“ÿ¶“qÿÿÿÿÿÿÿÿÿɱ–ÿøäÐÿúçÕÿúëÜÿûîáÿüðåÿüôëÿý÷ñÿþú÷ÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿúìÞÿî³zÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöïÿî·ÿ÷àÈÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¶¶¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×B˜ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ:::ÿÔÔÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõ×·ÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüñæÿð¿Žÿ÷Ú¾ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôϪÿóË£ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôͨÿóË£ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþþÿþýûÿþûøÿýøóÿüõîÿüòèÿûîâÿúëÝÿúé×ÿùæÑÿøáËÿ÷ÞÅÿöÛ¿ÿö×¹ÿ¯˜€ÿÿÿÿÿÿÿÿÿÑ¥yÿð¿ÿñ¿ÿñÀ‘ÿñÁ’ÿñ“ÿñÖÿòÅšÿóÈžÿóË£ÿôͨÿôЬÿõÓ±ÿöÖ¸ÿ÷ÛÀÿøßÇÿøãÎÿùæÓÿúéØÿûíßÿüñçÿüõîÿýøóÿýúöÿþûøÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÐÿð»ˆÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿî´zÿúëÝÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€€€ÿ ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÝH@ÙÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVVVÿæææÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿôÑ«ÿlÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîàÿð¼‰ÿùâÌÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿóÊ¢ÿõÓ±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿòÈŸÿõÑ®ÿþüúÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ­®®ÿÿÿÿÿÿÿÿÿäѽÿùæÓÿùáÌÿ÷ÞÇÿ÷ÛÁÿöÙ»ÿõÕµÿõÑ®ÿóͨÿóÊ¢ÿòÈžÿòÆ›ÿòĘÿò”ÿñÁ“ÿðÀ‘ÿðÀÿð¿Žÿð¿Žÿð¿ÿñÀ‘ÿñ”ÿñÄ–ÿñŘÿñÇœÿòÊ¢ÿôΩÿõÓ±ÿö׸ÿöÚ½ÿ÷ÝÃÿøãÎÿóˤÿð¾ŒÿúéÙÿûòèÿüôëÿüöðÿýúöÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿùäÏÿî¶ÿüõíÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿPPPÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿáL‹úÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿyyyÿöööÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿóÊ ÿñĘÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ===ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿúêÚÿﺆÿúéÙÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðæÿóÇÿ÷ÛÀÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿñÄ™ÿöغÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¨¨¨ÿÿÿÿÿÿÿÿÿðïíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþüÿþüúÿýú÷ÿýøôÿý÷ðÿüôìÿüòèÿûïãÿûìÞÿúéØÿùçÔÿùäÏÿøàÉÿ÷ÝÂÿöÙ½ÿöÖ·ÿõÔ²ÿõЭÿóΨÿòË£ÿòÇÿòĘÿñ“ÿðÀÿð¾Žÿð¿Žÿî³zÿî²xÿð½‹ÿð¾ÿð¿ŽÿðÀ‘ÿñ×ÿòÇœÿóË£ÿôΩÿôÑ®ÿõÕ´ÿöÙ¼ÿ÷ÞÅÿøãÎÿùèÖÿúìÝÿûïãÿüóéÿý÷ðÿýûøÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÖ·ÿð½‹ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÜÜÜÿ###ùÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäN¼ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¤¤¤ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿþÿñÕÿóÌ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ<<<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùäÐÿðº†ÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿûìÞÿòŘÿøãÍÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìÞÿñ•ÿøßÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¤¤¤ÿÿÿÿÿÿÿÿÿöõôÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþüúÿþûøÿýùõÿý÷ñÿüôìÿüòèÿûïãÿûíàÿúëÜÿúè×ÿï·ÿóͧÿ÷ÝÃÿ÷ÜÀÿöØ»ÿõÔ´ÿôЭÿôÌ¥ÿòÈžÿñÅ™ÿñÕÿñÁ’ÿð¿ÿð¾ÿlÿð½‹ÿð½‹ÿð½‹ÿð¾ŒÿñÀÿñÁ“ÿñÄ—ÿòÆœÿòÉ¡ÿó̧ÿõÑ®ÿöÖ·ÿöÛÀÿ÷ßÇÿøãÍÿùæÔÿúëÜÿûðåÿý÷ðÿñÅ™ÿòÇœÿþû÷ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿ™™™ÕîþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåPB×ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐÐÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿð½‹ÿõÔ´ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ<<<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÞÅÿð¼ˆÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿúè×ÿñ”ÿúéÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÓÿñ”ÿùåÓÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ£££ÿÿÿÿÿÿÿÿÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿï¶ÿùæÓÿþþþÿÿÿþÿþýüÿþüùÿýúöÿýøòÿüöïÿüôëÿüòèÿûðåÿûîàÿúëÜÿúèÖÿùåÑÿøâÍÿ÷ßÇÿ÷ÛÁÿöغÿõÓ²ÿôЬÿôͦÿòÊ¢ÿñÇÿñŘÿñ”ÿñÁ‘ÿð¿Žÿð¾Œÿ)ÿ)ÿð¼‰ÿð¾‹ÿí±vÿí³yÿñÀ‘ÿñÄ—ÿóÈžÿóͦÿõѯÿõÕµÿöØ»ÿ÷ÝÃÿøâÌÿùçÕÿûìÞÿûðåÿüóéÿüöïÿýùõÿþýüÿÿÿÿÿÿÿÿ¨³üÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçQSßÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿMMMÿóóóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿ︂ÿ÷ÜÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿö׸ÿð¿ŽÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÍÿñ¿ÿûðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿøßÈÿñ“ÿúëÝÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ£££ÿÿÿÿÿÿÿÿÿøøøÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûïãÿîµ}ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýýÿþüúÿþûøÿýùõÿýøóÿýöðÿüõíÿüóéÿûðåÿûîáÿûìÝÿúéÙÿùæÔÿøãÎÿ÷àÉÿö׸ÿí±vÿóÊ¡ÿõÓ²ÿôÏ«ÿóÌ¥ÿòÈÿñÄ—ÿñ“ÿð¿ÿð½Šÿﻇÿﺆÿï¹…ÿ﹄ÿ﹄ÿﻇÿð½‹ÿñÀÿòŘÿײ“»ýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçQR×ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ–––ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿî³{ÿøâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿFFFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôЫÿñÕÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÛÀÿñÀÿý÷ðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöØ»ÿñÕÿûñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¥¥¥ÿÿÿÿÿÿÿÿÿõõõÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÒÿðº†ÿüóéÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿúëÝÿîµ|ÿúëÜÿýúöÿýøôÿý÷ñÿüõîÿüóëÿüòèÿûðäÿûíàÿúêÛÿùè×ÿøåÒÿøâÍÿ÷ßÇÿ÷ÛÀÿöÖ¸ÿõѯÿóË¥ö:0&¿ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåO@¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ...ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛÛÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿí²vÿùçÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿOOOÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿóÈŸÿòÉ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿöÔ´ÿò•ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿõÑ®ÿòÇœÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿªªªÿÿÿÿÿÿÿÿÿïïïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿ÷ÛÀÿñÖÿüõîÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÉÿï·ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþþÿþýüÿþüúÿþûøÿýúöÿ—”‘ë÷ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãN&„íÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ555ÿrrrÿ­­­ÿÈÈÈÿ„„„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ^^^ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñèÿì±tÿúìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿUUUÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿñ”ÿôÏ«ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôΩÿòÈŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿóˤÿô̦ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ°°°ÿÿÿÿÿÿÿÿÿçççÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôΩÿô̧ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿõÒ¯ÿð¿ÿþûøÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÒÒÒÿøÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàJH¡þÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ///ÿmmmÿ¥¥¥ÿÎÎÎÿöööÿÿÿÿÿÿÿÿÿûûûÿ»»»ÿIIIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÄÄÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÞÿí°uÿüñèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ]]]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüôìÿð½‹ÿõÖ·ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿôË£ÿôÏ«ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿòÇÿôÓ±ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÛÛÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿò”ÿöÖ¹ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿñÅ™ÿòÉ ÿþüùÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷÷÷ÿLLLÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛFœœœÊcccÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿAAAÿ|||ÿ­­­ÿÎÎÎÿðððÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÝÝÝÿ€€€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿBBBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÒÿí²xÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿeeeÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüñçÿﺅÿ÷ÝÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿóÉ ÿöÖ·ÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñæÿñÅ™ÿöÙ¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÄÄÄÿÿÿÿÿÿÿÿÿÎÎÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúøÿð¹„ÿøàÉÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿð¼‰ÿöÖ·ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ{{{ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕ@ýýý²èèèÿÅÅÅÿŽŽŽÿFFFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ666ÿjjjÿžžžÿÂÂÂÿÚÚÚÿõõõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõõõÿ©©©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¿¿¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÅÿîµ}ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿoooÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿúìÞÿ︃ÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûïäÿòÅ™ÿ÷ÝÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿñÄ—ÿøáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÒÒÒÿÿÿÿÿÿÿÿÿ½½½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñèÿï·€ÿúéÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõìÿî·€ÿùãÎÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¬¬¬ÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÏ:ÿÿÿ´ÿÿÿÿÿÿÿÿùùùÿßßßÿÅÅÅÿšššÿcccÿ,,,ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ---ÿSSSÿ}}}ÿªªªÿÉÉÉÿÙÙÙÿìììÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇÇÇÿ---ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿEEEÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö×¹ÿð¹„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ|||ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùçÔÿ︃ÿûíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúëÛÿñÁ“ÿúæÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿùäÑÿñ”ÿùçÖÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿáááÿ###ÿÿÿÿÿÿÿÿ©ªªÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéØÿð»‡ÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÙÿî¶~ÿûîãÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÜÜÜÿ777ÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇ3ÔÔÔÿÿÿ¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿëëëÿÚÚÚÿËËËÿ¯¯¯ÿ„„„ÿbbbÿDDDÿ(((ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ///ÿEFEÿZG3ÿyk\ÿš™—ÿ»»»ÿÐÐÐÿÚÚÚÿæææÿóóóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×××ÿ@@@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐÐÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÑ®ÿð¿ŽÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŠŠŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøáÊÿ﹆ÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÒÿñ¿Žÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÄÿñ”ÿûîáÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòòòÿ'''ÿÿÿÿÿÿÿÿ“’’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÞÇÿòÖÿüóêÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÛÁÿ﹃ÿýöñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¾*ÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõõõÿìììÿåååÿÞÞÞÿÙÙÙÿÕÕÕÿÎÎÎÿÄÄÄÿ»»»ÿ±±±ÿ®®®ÿ¯¯¯ÿ±±±ÿ´´´ÿ¾¾¾ÿËËËÿÑÑÑÿÖÖÖÿÛÛÛÿàààÿãàÜÿÝ«{ÿìÓºÿùøöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿáááÿBBBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿjjjÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿóÊ£ÿòĘÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ———ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿöÚ¿ÿð¼Šÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ÷ßÇÿñ¾Žÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿöÖ·ÿòŘÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ***ÿÿÿÿÿÿÿÿ{{{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿõÓ±ÿóË£ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿóΪÿñÀ‘ÿýùöÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŠŠŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ´!òòòýýýÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýýýÿýýýÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿ︂ÿùâÌÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâââÿ::9ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòĘÿóË£ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ©©©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÔ´ÿñÁ‘ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿöØ»ÿñÁ’ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿóϪÿòÈŸÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ999ÿÿÿÿÿÿÿÿ```ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÇœÿõÔ²ÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÄ—ÿóÌ¥ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿºººÿ'''ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ©óóèü÷òËþú÷ÿýüûþþýýÿþþýÿþþýÿþþýÿþþýÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿþþþÿÿþþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿï¸ÿùåÒÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛÕÑÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿªªªÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿð¾ŽÿõÒ±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ½½½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿýùõÿôΨÿòÆ›ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿõÒ°ÿòÅ™ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿòÉ¡ÿôΩÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿQQQÿÿÿÿÿÿÿÿ@@@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿð½‹ÿ÷ÚÀÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð¼‰ÿöÙ»ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçççÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿœ è±yî¶~Ë﹂ÿﻈÿñ¿ŽÿòÄ—ÿóÊ¡ÿôϬÿõÕ¶ÿ÷Û¿ÿ÷ÞÆÿøâÌÿùçÔÿúëÜÿûðåÿüóìÿýöïÿý÷ñÿýøôÿþúöÿþûùÿþüûÿþýüÿþýüÿþýüÿþýýÿþþýÿþþýÿþþþÿþþþÿþþþÿÿÿÿÿûîáÿï¶€ÿúèØÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõíÿ½dÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿRRRÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿ﹄ÿ÷Û¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐÐÐÿ!!!ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýøòÿòÇœÿó̦ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿôͨÿóÊ¢ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿòÇœÿõÔµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿmmmÿÿÿÿÿÿÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõíÿð¹„ÿùäÐÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿî¸ÿùåÑÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿpppÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿõÚÈöÙ¾ÍöÖ¶ÿõÑ­ÿóͦÿòÉžÿñÖÿð¿Žÿﻇÿ︃ÿï·ÿîµ|ÿî´{ÿî³zÿî´{ÿî´|ÿî¶€ÿ﹄ÿð½‹ÿñÂ’ÿñÆšÿòÊ¢ÿôΩÿõÓ°ÿõ׸ÿ÷ÜÂÿøáËÿùæÓÿúêÛÿûíßÿûïãÿüôìÿùåÑÿî·€ÿúéØÿþûùÿþüùÿþüúÿþüúÿþýûÿþýüÿþýüÿþþýÿþþýÿþþþÿþþþÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüñçÿê²{ÿŸ“†ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿí´|ÿøãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåååÿ&&&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõíÿñÁ‘ÿõÔµÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿóÉŸÿõÑ®ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûïãÿòÅšÿ÷ÛÀÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŠŠŠÿ ÿÿÿÿÿÿÿÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÝÿð¼ˆÿûìÝÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÓÿï·€ÿûïâÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ%þþþÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿþýûÿýûøÿýùõÿý÷òÿüõíÿûðåÿúëÜÿøçÓÿøâËÿ÷ÝÅÿöؼÿôÔ²ÿóΨÿòÉŸÿñÖÿð¿ÿ)ÿï¹…ÿï·€ÿîµ}ÿî´|ÿî´{ÿîµ|ÿï¶~ÿÿî¶ÿí®qÿ)ÿñÖÿòÇÿóÌ¥ÿôÒ¯ÿöعÿ÷ÞÃÿøâËÿøåÐÿùèÖÿúìÝÿûðåÿüôìÿý÷òÿýùõÿýùöÿþú÷ÿþûøÿþûùÿþüúÿþüúÿþýûÿþýüÿþýüÿþþýÿþþþÿþþþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿî´}ÿêÚÊÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ»»»ÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿí±vÿúéÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ,,,ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñçÿð¼‰ÿ÷ÝÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿòÖÿ÷Ù½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúéØÿñ•ÿøâÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿªªªÿÿÿÿÿÿÿÿÿØØØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿøâÌÿòÕÿûðæÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöؼÿﻈÿýõîÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÊÊÊÿ555ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþpùùù2ÿÿÿÖþþþÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþüùÿýøóÿüóëÿûðäÿúìÞÿùèØÿøãÏÿøàÇÿóÊ¡ÿî´zÿòÆ›ÿòÈžÿòÄ—ÿñÁÿð¼Šÿï¹…ÿï·ÿî¶~ÿîµ|ÿîµ|ÿï¶}ÿî¶ÿî¸ÿ﹄ÿð¼‰ÿð¿ÿòŘÿóÉ¡ÿôÏ«ÿõÔ´ÿöÙ»ÿ÷ÜÂÿ÷àÈÿøäÐÿùéØÿúíàÿûðåÿüòèÿüóêÿýôíÿý÷ðÿþúöÿùçÕÿï´|ÿúéÚÿ×ÔÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿxxxÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿì°tÿûîàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ888ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúíßÿ﹄ÿùåÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûíáÿñ¿ÿøãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÌÿñ“ÿúëÛÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÌÌÌÿÿÿÿÿÿÿÿÿ­­­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿö׸ÿóÉ¡ÿüôíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóͦÿòÄ—ÿýùôÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðððÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿï_úúú?ýýýÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷áÊÿð¾ŒÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿýùôÿýõîÿüóéÿûðåÿûìÞÿùæÔÿøáÊÿ÷ÛÀÿö׸ÿõÓ±ÿôΪÿóÊ¡ÿòÅ™ÿñÁ’ÿñ¾Œÿð»ˆÿ﹄ÿï¸ÿî¶ÿî¶~ÿî¶~ÿï·€ÿ﹃ÿﻇÿð¾ÿð“ÿòÇœÿñÁ‘ÿí°sÿóˤÿíίÿ‡whÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>>ÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿí±uÿüòçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿSSSÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùèÖÿï·‚ÿûíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúêÛÿð¼‰ÿûìßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÛÀÿñÔÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñññÿ ÿÿÿÿÿÿÿÿ‚‚‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóˤÿõЬÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÕÿôÏ«ÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿˆˆˆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿßMÿÿÿJþþþßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÚ½ÿð¿Žÿüóêÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿþüùÿýû÷ÿýøóÿüôíÿûïåÿúëÜÿùçÕÿøãÎÿøßÇÿöÚ¾ÿõÔ´ÿôÏ«ÿó̤ÿð»‡ÿí°tÿð½‹ÿð½ŠÿÏ¢tÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿýúöÿþûùÿùæÓÿî²xÿýõìÿþþþÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿrrrÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøãÍÿ︂ÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÓÿð»‡ÿüöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿôÔ³ÿñÅ™ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ...ÿÿÿÿÿÿÿÿSSSÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ’ÿöÖ·ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿð¼‰ÿ÷ÛÀÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ³³³ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍ9ûûûOýýýáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÖ¶ÿñ“ÿüôíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÛ¾ÿð»†ÿý÷òÿþûùÿòíçÿ~zvÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÍ®ŽÿõÒ°ÿöÖ·ÿóÊ¢ÿí²wÿøßÅÿøåÑÿúè×ÿúëÛÿúìÞÿûîâÿüðæÿüóêÿüõîÿýöðÿý÷ñÿýøóÿýúöÿþûøÿ‘ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÝÃÿﺅÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÊÿð¼‰ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùõÿôΨÿòÊ¡ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿVVVÿÿÿÿÿÿÿÿ"""ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿúúúÿúúúÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿð¼‰ÿøÞÆÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿ︂ÿùåÒÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙÙÙÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ»$ÿÿÿUýýýãþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿõÒ±ÿñŘÿüöïÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÓ°ÿð½‹ÿþúöÿÿÿÿÿÿÿÿÿÊÊÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ§‡hÿñ“ÿñÀÿí´{ÿí°sÿﻆÿ﹄ÿ﹄ÿﺅÿﻇÿð½‹ÿñ¿ÿñÓÿòÅ™ÿòÈÿóË£ÿôΩÿõÒ°ÿõ׸ÿ«˜…ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ?>>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿõÖ¶ÿñ¾ŒÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿöÚ½ÿñÀ‘ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿóÉ¡ÿôÏ«ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ„„„ÿ ÿÿÿÿÿÿÿ ÿîîîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙÙÙÿ………ÿTTTÿiiiÿÁÁÁÿ÷÷÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüïãÿð½‹ÿùèÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÐÿ︃ÿûíàÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõõõÿtttÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ¨ÿÿÿaÿÿÿèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôÏ«ÿòÈÿý÷ðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿôͨÿñÀ‘ÿþûøÿÿÿÿÿÿþþÿáááÿBBBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŽÿþýûÿþýûÿôЬÿð¾ÿûðæÿúìÞÿúèØÿùåÑÿ÷áÊÿ÷ÝÂÿö×¹ÿõÓ°ÿôΩÿóË¢ÿóÈÿòÄ—ÿñÁ’ÿð¿ŽÿÉžsÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿôΨÿòÄ–ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùöÿõÒ±ÿòÇœÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿòÇœÿõÖ¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿ²²²ÿÿÿÿÿÿÿÿÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿŸŸŸÿÿÿÿÿÿÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÒÿñ”ÿûîàÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿö׺ÿð¾Œÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ   ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ“ÿÿÿoýýýíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÌ¥ÿóˤÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóÉ ÿñĘÿþûøÿÿÿÿÿÿÿÿÿñññÿyyyÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿtttÿÿÿÿÿÿÿÿÿóͧÿòÆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýÿþûøÿý÷óÿøñéÿ$#!ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>;9ÿüóêÿüôíÿýöðÿýøôÿþú÷ÿþûúÿþýûÿþýüÿþþþÿÿÿÿÿÿÿÿÿþûùÿòÈÿóÌ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöðÿóˤÿôÏ«ÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿúíßÿñÖÿ÷ÞÄÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿãããÿÿÿÿÿÿÿÿÿ|||ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåååÿmmmÿÿÿÿÿÿÿÿ³³³ÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿöÚ¿ÿóÈŸÿüòéÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÌ¥ÿòÇžÿýøóÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÅÅÅÿ***ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿzÿÿÿ|ÿÿÿòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÈžÿôÏ«ÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÅ™ÿòÉ ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿ¦¦¦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿaaaÿÿÿÿÿÿÿÿÿñÆ›ÿó̦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ:::ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;0%ÿòÅ™ÿòÈÿóË£ÿôϪÿõÒ±ÿöÕ·ÿöØ»ÿöÚ¿ÿ÷ÞÅÿøáÌÿùæÓÿùåÐÿ)ÿóË¢ÿüòèÿûòèÿüôìÿýöñÿýøôÿýúöÿþûùÿþýûÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿüóêÿòĘÿöÙ¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúçÕÿñÁ’ÿùæÓÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ'"ÿÿÿÿÿÿÿÿ@@@ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿÃÃÃÿ???ÿÿÿÿÿÿÿÿÿbbbÿïïïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÏ«ÿôͧÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ•ÿõÓ±ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäääÿYYYÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿê_ÿÿÿˆýýý÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÄ–ÿôÒ±ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿðÀ‘ÿôϪÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÀÀÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿRRRÿþÿÿÿÿþþÿðÀÿõÓ²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿeeeÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ<4+ÿõЬÿóͦÿòÊ¡ÿòÇ›ÿñÄ—ÿò“ÿñÁ‘ÿñ¿Žÿð¾Œÿð½‹ÿð½Šÿ'ÿí¯rÿî·ÿñ”ÿñĘÿòÈÿóˤÿôΩÿôЭÿõÓ²ÿö׸ÿöÛ¿ÿ÷߯ÿøâÌÿùåÑÿùçÕÿúêÚÿûíßÿûïäÿüòèÿüôìÿýöïÿýøóÿþúöÿþüúÿþþýÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿñ¿ŽÿùãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÊÿðÀÿûîâÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿYM@ÿÿÿÿÿÿÿÿÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñññÿ™™™ÿÿÿÿÿÿÿÿÿÿÿEEEÿêêêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÆšÿõÒ¯ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿð¼‰ÿ÷ÜÂÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿøøøÿ‰‰‰ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕCýýýÿÿÿúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÀÿõÖ·ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿð½‹ÿöÕ´ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÆÆÆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿJJJÿÿÿÿÿÿýûÿﺆÿöÚ¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ“““ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿþÿÿÿþýûÿþú÷ÿýøòÿüõîÿüóéÿûïãÿúëÜÿùçÔÿøãÍÿöغÿî²xÿóË£ÿõÖ·ÿôЭÿôͧÿóÊ¡ÿóÇÿòÆšÿñÖÿñÁ’ÿð¿Žÿð½Œÿð½‹ÿð½‹ÿð¾ÿðÀÿñÁ’ÿòÖÿòÅšÿòÈÿóÉ ÿóÌ¥ÿôϪÿõÒ±ÿöÖ·ÿöÙ¼ÿ÷ÛÀÿ÷ÞÅÿøáËÿùåÑÿúèØÿúëÜÿûïãÿøâÌÿ﹄ÿøãÏÿýúöÿýúöÿþûøÿþüûÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿöÚ¾ÿñ“ÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþúöÿ‘ybÿ ÿÿÿÿÿÿÿ ÿ»»»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙÙÙÿjjjÿÿÿÿÿÿÿÿÿÿÿÿ???ÿèèèÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿñÀÿöÚ¾ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿ﹄ÿùäÑÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿ´´´ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ¾#ýýý‘ÿÿÿúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð½ŒÿöÙ¼ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿðº…ÿ÷Û¿ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÈÈÈÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGGGÿÿÿÿÿþû÷ÿîµ~ÿøâÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÀÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>??ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿï·ÿûìßÿÿÿÿÿÿÿÿÿþýüÿþûøÿýùöÿýøóÿüõîÿüòçÿûîáÿúëÛÿùèÖÿùåÑÿøáËÿøÝÄÿ÷Ú½ÿöÖ·ÿõÓ²ÿôЬÿôͧÿóÊ¢ÿòÇÿñÅ™ÿñÕÿñ“ÿñÁ‘ÿðÀÿð¿ÿð¿Žÿð¿ÿð¿ÿñÁ’ÿð¾‹ÿí°tÿñÕÿóË£ÿôͧÿôÏ«ÿõÒ°ÿõÕ¶ÿöÙ¼ÿ÷ÝÂÿøàÉÿøãÎÿùæÓÿúéØÿûìÞÿûðäÿüóêÿýöïÿý÷òÿýùõÿþüùÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿõÔ³ÿñÅšÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿ̧ƒÿ ÿÿÿÿÿÿÿÿvvvÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿ¸¸¸ÿ<<<ÿÿÿÿÿÿÿÿÿÿÿÿÿ:::ÿçççÿÿÿÿÿÿÿÿÿÿÿÿÿüòéÿñ¾ŽÿøãÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿùâÍÿð»‡ÿúíßÿþÿÿÿÿÿÿÿÿÿÿÿÖÖÖÿ777ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ§ÿÿÿ‘ÿÿÿúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ*ÿöÜÁÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöðÿï¸ÿøßÈÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÅÅÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿLLLÿÿÿÿÿý÷òÿí±xÿùéÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïïïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùçÔÿî¶€ÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþþÿþýüÿýû÷ÿýøóÿüõîÿüòéÿüñåÿúíàÿúêÚÿùçÔÿùãÍÿøàÈÿ÷ÝÃÿ÷Ú½ÿòÉŸÿí²wÿóΨÿóÌ¥ÿóÉ ÿóÇÿòÅ™ÿñ•ÿñÀÿð¿Œÿkÿð½Šÿð¾‹ÿð¿ÿñÀÿñ”ÿòŘÿóÇœÿóÈŸÿóË£ÿôΩÿõÒ¯ÿõÕµÿ÷Ù¼ÿ÷ÜÁÿ÷ÞÅÿøâÌÿùæÒÿúéÙÿúíßÿûðäÿüòèÿýöîÿûòèÿòÌ¥ÿóÊ¢ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿñ“ÿ#ÿÿÿÿÿÿÿÿ555ÿÿÿÿÿÿÿÿÿêêêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ333ÿæææÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿñ”ÿúêÛÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõ׸ÿñÁ’ÿüóêÿÿÿÿÿÿÿÿÿïïïÿhhhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒÿÿÿ˜ÿÿÿûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿð»ˆÿøÞÆÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôëÿï¶ÿùâÎÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿUUUÿÿÿÿÿüóëÿí°tÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ444ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ßÇÿ﹃ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøßÈÿð¼Šÿþûøÿýû÷ÿýøòÿýöïÿüóëÿûðåÿúíßÿúêÙÿùçÔÿùäÐÿøáËÿ÷ÞÄÿöÚ¾ÿöÖ·ÿõÓ±ÿõЭÿôΩÿóË£ÿòÈžÿòÅ™ÿñÔÿñÁ’ÿñÀÿñ¿Žÿñ¿Žÿñ¿ÿðÀÿñÀ‘ÿñÁ’ÿñÔÿñŘÿñĘÿï·€ÿﺄÿôЬÿõÒ¯ÿöÕµÿöÙ¼ÿ÷ÝÂÿøàÉÿùäÏÿùçÔÿúêÚÿûíàÿûñæÿüôíÿý÷òÿýùõÿþûøÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿðÀÿ_VNÿÿÿÿÿÿÿÿÿÞÞÞÿÑÑÑÿcccÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ)))ÿäääÿÿÿÿÿÿÿþÿÿÿÿÿ÷ÞÄÿòÇÿûðåÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóˤÿóË£ÿý÷òÿÿÿÿÿûüüÿ™™™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿígÿÿÿ¡ÿÿÿþþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿð»‡ÿøáËÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðåÿî¶~ÿùæÔÿþþýÿÿÿÿÿÿÿÿÿüüüÿ›››ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿfffÿÿÿÿÿüïãÿì°tÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿhhhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿö׺ÿ)ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿþû÷ÿöÖ·ÿòĘÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþýÿþýûÿþüùÿþú÷ÿýøóÿýõïÿüóêÿûðåÿûîáÿûìÞÿúéÙÿùåÒÿùâÍÿ÷ßÇÿ÷ÜÂÿ÷Ú¾ÿö×¹ÿõÔ´ÿóÉ¢ÿîµ|ÿð¾‹ÿòÊ¡ÿòÆ›ÿñÄ–ÿñÂ’ÿðÀÿð¾Œÿð½‹ÿð½Šÿð¾‹ÿð¿ŽÿðÁ‘ÿñÕÿòÅ™ÿòÆœÿóÊ ÿô̦ÿôЬÿõÔ³ÿöغÿ÷ÛÀÿøÞÅÿøâÌÿùæÓÿúëÛÿûïãÿüòéÿüõíÿýøñÿýú÷ÿþýûÿÿÿÿÿøâÌÿðÀ‘ÿ¦œ’ÿÿÿÿÿÿÿÿ ÿbbbÿ===ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâââÿÿÿÿÿþþþÿÿÿÿÿõÔ³ÿóÊ¢ÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿò”ÿõÕ´ÿýú÷ÿÿÿÿÿÄÃÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕ@ýýý¬þþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôêÿﻆÿùäÐÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûëÜÿî¶~ÿùëÛÿþþýÿÿÿÿÿÿÿÿÿíííÿkkkÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ|||ÿÿÿÿÿùéÙÿí²xÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŸŸŸÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿôЭÿñÁ’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿôϪÿôͨÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿúéØÿð¿Žÿ÷ÜÁÿýøóÿüóêÿûðåÿûíàÿúêÛÿùèÖÿùæÓÿøãÎÿøàÇÿ÷ÜÀÿöعÿõÔ³ÿôÑ®ÿôΪÿóÌ¥ÿòÈžÿñŘÿñ“ÿñÀÿñ¾Œÿð½‹ÿð½‹ÿð½Œÿð¾ÿñ¿ÿñÁ‘ÿð“ÿñÄ–ÿòÆšÿòÉŸÿôͨÿñÁ‘ÿï¶~ÿâ¿›ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿßßßÿþÿÿÿÿÿÿÿÿÿÿÿôÊ£ÿôͨÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüöïÿð½Šÿ÷ÝÂÿþüúÿåååÿAAAÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ½ÿÿÿµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïäÿð»‡ÿùçÕÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÒÿî¶ÿûïãÿþþþÿÿÿÿÿÿÿÿÿÝÝÝÿ,,,ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ™™™ÿÿÿÿÿ÷âÌÿîµ~ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛÛÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþûøÿòÉŸÿòÇœÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿóÈŸÿö×¹ÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÖÿð¾ÿúêÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþýüÿþüùÿýúöÿýùôÿý÷ñÿüõíÿüòéÿûðäÿûîáÿúìÝÿúêÙÿùæÔÿøâÍÿ÷ßÇÿ÷ÜÁÿöÚ½ÿö׸ÿõÔ²ÿôϬÿô̦ÿóÈŸÿ﹃ÿî´{ÿñÁ‘ÿ=1%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÜÜÜÿÿÿÿÿÿÿÿÿÿÿÿÿòÄ™ÿö×¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúíßÿﻇÿùåÐÿùùøÿsssÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿÿ·ÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÝÿﻈÿúêÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÈÿï·ÿüóêÿÿþþÿÿÿÿÿÿÿÿÿ···ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ»»»ÿÿÿÿÿ÷ÛÀÿﻇÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ&&&ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþùöÿñ”ÿôΩÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüóêÿò”ÿøàÉÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáËÿð¾Œÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþýÿþýüÿþüúÿþû÷ÿýùôÿýøóÿûñæÿòÈŸÿòÈžÿûíàÿ‘‰‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÆ¥…ÿôϪÿõÓ²ÿõÓ²ÿï·ÿôÌ¥ÿùæÓÿúêÚÿûîáÿüñæÿüôìÿýøòÿþúøÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿþþÿÿÿÿÿøâÌÿð½‹ÿúìÞÿ¦¦¦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôxÿÿÿ¹ÿÿÿÿýýýþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúè×ÿð¼ŠÿúìÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÚÀÿðº…ÿýöñÿÿÿÿÿÿÿÿÿïïïÿcccÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿççæÿÿÿÿÿõÓ³ÿðÁ’ÿþýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿð¼‰ÿöÖ¸ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüðæÿð¼Šÿùè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿöÛ¿ÿñÀ‘ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿòÈžÿõÔ´ÿÿÿÿÿæææÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¯qÿñ•ÿñ“ÿð¼‰ÿí°vÿï·ÿ)ÿð»‡ÿð»‡ÿð»ˆÿð¼Šÿð¿ÿñÀ‘ÿñÖÿòÆœÿóÉ¡ÿôΨÿõÒ°ÿö׸ÿ÷ÛÀÿøàÈÿøãÎÿùçÕÿúëÝÿûïäÿüôìÿý÷òÿýùõÿþûøÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö×¹ÿñĘÿÑÊÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛIÿÿÿÿÿÿ¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÐÿð½‹ÿûîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÖ¸ÿð¼‰ÿýøôÿÿÿÿÿþÿÿÿÉÉÉÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿóͧÿòÈžÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŸŸŸÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüòéÿ︂ÿøßÈÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûëÝÿ︃ÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÔ³ÿòÅ™ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿûïãÿñÕÿöÛ¿ÿÿÿÿÿÿÿÿÿ,--ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿž™•ÿ÷ïæÿüõîÿöغÿñ”ÿøÞÆÿùêÙÿùæÒÿùãÎÿøàÉÿöÜÂÿöغÿôÓ³ÿõЭÿôΨÿóË¢ÿòÆœÿñÖÿðÀÿð½Šÿﺆÿð¹„ÿ﹄ÿ﹃ÿﺅÿﻇÿð¼Šÿñ¾ÿñÀ’ÿòĘÿòÈžÿóÌ¥ÿôЬÿõÔ³ÿöغÿ÷ÞÃÿùäÐÿñ”ÿ输ÿFB=ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÃóóóÿÿÿÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ßÈÿð¿ÿûðäÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿõÒ¯ÿñÀÿýùõÿÿÿÿÿôóóÿbbbÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿMMMÿþÿÿÿÿÿÿÿòÆ›ÿôϪÿþþþÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåååÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúíàÿî¶~ÿúè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùäÐÿï¸ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿóͦÿóÌ¥ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿúé×ÿðÀÿøáÊÿþþþÿŠŠ‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ………ÿ÷÷÷ÿÿÿÿÿöØ»ÿóÈŸÿüóêÿÿÿÿÿþþþÿþþýÿþýüÿþüúÿþûùÿýúöÿýùõÿýøóÿý÷ñÿüöîÿüóëÿüòèÿüñæÿûïäÿúíàÿúéÙÿùåÒÿøáÊÿ÷ÝÄÿöÚ¾ÿõ׸ÿõÒ±ÿóͨÿòÉŸÿñÄ—ÿñÀÿð¾‹ÿﻇÿﺅÿ﹄ÿí±tÿqT8ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¡ÿÿÿ%ýýýËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÚ¿ÿðÀ‘ÿüñèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôͦÿñÅ—ÿýúöÿþþþÿ¶¶¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒŒŒÿÿÿÿÿþÿÿÿðÁ’ÿõÕ´ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ///ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùèÕÿï¶}ÿûðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÜÂÿð»‡ÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿñÆšÿõÔ²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáËÿð¿Žÿ×ȸÿ___ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿeeeÿñòòÿÿÿÿÿôЫÿóÊ£ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþýüÿþüûÿþüùÿþûøÿýúöÿýùôÿý÷òÿýöðÿüõîÿüôíÿûóéÿûñåÿùäÏÿ¨‚]ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîpÿÿÿ2ÿÿÿÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÕ¶ÿñ”ÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÈžÿòÉ¡ÿýú÷ÿèèèÿ///ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÒÒÒÿÿÿÿÿþýüÿ)ÿöÚ¿ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿuuuÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿùâÌÿï·ÿýõïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÕµÿñÁ’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿðÀ‘ÿ÷ÜÂÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÚ¾ÿ£‚cÿ:74ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿCCCÿíííÿÿþþÿóÇžÿõЭÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿßÓÆÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÖ7ÿÿÿ<ÿÿÿÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÑ®ÿñĘÿüôíÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿñÄ–ÿôÏ«ÿûøõÿaaaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"""ÿÿÿÿÿÿÿÿÿýûøÿî·ÿøáËÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÃÃÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÜÂÿï¹…ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿõЭÿóÈ ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿúëÛÿð½ŠÿùåÑÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûù÷ÿwgVÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿéééÿýøòÿòĘÿ÷Ù½ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿJD<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ»úúú>ÿÿÿ×þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóͧÿòÇÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿð¿ÿöÕµÿŽ‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿkkkÿÿÿÿÿÿÿÿÿü÷ñÿî³zÿúèØÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿõÕ´ÿñ¿ŽÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿóʤÿõѯÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿùèÖÿﻇÿûîàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×××ÿQPNÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿâââÿûîâÿò×ÿùâÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ„„„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö‰ÿÿÿ@ÿÿÿØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿóÊ£ÿóÊ¢ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿð½‰ÿ¨”ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÊÊÊÿÿÿÿÿÿÿÿÿüóêÿí±uÿüðäÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ___ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþüúÿôÍ¥ÿòÆ›ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýöïÿò×ÿ÷ÛÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÌÿð¼‰ÿýõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ§§§ÿ000ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÀÀÿøäÐÿòÆšÿúêÛÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÂÂÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿàIÿÿÿJÿÿÿÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÈžÿóΧÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿ®‡aÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ)))ÿÿÿÿÿÿÿÿÿÿÿÿÿüïâÿí°tÿüöîÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿñĘÿôϪÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüóêÿñ½‹ÿùæÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷Ú¾ÿñÀ‘ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøøøÿvvvÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ“““ÿñÕ»ÿòÇœÿûðåÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóóóÿ***ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÈüüüVýýýâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòŘÿôÑ®ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¹µ¯ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒŒŒÿÿÿÿÿÿÿÿÿÿÿÿÿúéØÿí±vÿýùôÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþùõÿkÿöعÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿ︂ÿûðæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿôѯÿòÇœÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔÔÔÿIIIÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿfffÿëˬÿòÇÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWWWÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿø’ÿÿÿaýýýçþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿñÁ’ÿõÕ¶ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¦¦¦ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿïïïÿÿÿÿÿÿÿÿÿÿÿÿÿøãÎÿíµ}ÿþú÷ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ___ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿý÷ñÿ﹂ÿøáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúèÖÿïµ~ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõïÿóÊ¢ÿôϪÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¥¥¥ÿ%%%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ222ÿäÀœÿó̦ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ”””ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿãJüüüiýýýëþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿð¿ÿöÙ¼ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ………ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿmmmÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÜÂÿﺆÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ»»»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüòéÿï¶}ÿúèØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøáÊÿ︂ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿñÖÿöعÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿܵŽÿõÕµÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÒÒÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿËÿÿÿiÿÿÿëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþùôÿð¼ŠÿöÝÄÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùùùÿUUUÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäääÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÔ´ÿðÀ‘ÿþýúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúìÞÿîµ|ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿ÷Ú¾ÿð¼Šÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿûîâÿð½‹ÿ÷àÈÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ½½½ÿ)))ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ²pÿõÜÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿ777ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõ‹üüúkýüûìþþýÿþþþÿþþþÿþþþÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿﻈÿøàÈÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÌÌÌÿ***ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿnnnÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóͨÿòÇÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿsssÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùåÐÿî¶~ÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÓ±ÿòÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìÝÿﺆÿùéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ|dNÿôáÐÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿiiiÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿã:öÛÃt÷áÊðùçÔÿúëÜÿûîáÿüðæÿüóêÿüõíÿý÷ðÿýøóÿýúöÿþú÷ÿþûøÿþûùÿþüúÿþýûÿþýüÿþýüÿþþýÿþþýÿþþþÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿð»ˆÿøâÍÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ………ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿêêêÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿòÈœÿôΫÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×××ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿ÷ÜÂÿÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿóÊ¡ÿô̧ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÔÿï¹…ÿûñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ=2'ÿñäØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¨¨¨ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÂï·€îµ}õî´{ÿí³yÿî³zÿîµ{ÿî¶€ÿﺅÿð½‹ÿðÀ‘ÿòÅ™ÿòÉ ÿóͧÿõÒ°ÿö×¹ÿ÷ÜÁÿøáÉÿùãÎÿúæÓÿúêÚÿûíàÿüðäÿüòêÿýôíÿýöðÿý÷òÿýøôÿýúöÿþú÷ÿþûøÿþýüÿûðæÿﻈÿøäÏÿþþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÈÇÈÿ221ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‹‹‹ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ’ÿõÖ¶ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ777ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿõÔ²ÿð½Šÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿñ“ÿö׺ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýýÿøßÈÿð½Šÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ™™™ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿêáÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàààÿ'''ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿñnÿù÷ŽüøóüüõíÿûñçÿûïâÿúëÛÿùæÒÿ÷àÇÿöÚ½ÿõÕ´ÿôЮÿóÌ¥ÿòÇÿñ”ÿð½Œÿ﹄ÿï·€ÿîµ~ÿîµ}ÿî¶~ÿî·ÿ︃ÿﻆÿð½ŠÿðÀÿñÖÿòÇœÿóË£ÿôΪÿôÓ°ÿöغÿôÒ°ÿî¶~ÿõÕµÿúéØÿúìÞÿûîâÿûñæÿüóéÿüõíÿýöðÿý÷òÿýøóÿýùõÿýú÷ÿþûùÿþüúÿþýüÿþþýÿþþýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿäääÿfffÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ+++ÿöööÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿjÿ÷Ú¿ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿôˤÿòÕÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýöïÿðº†ÿøãÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿö×¹ÿñ”ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕÕÕÿCCCÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿµ²¯ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿLLLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿßÿÿÿ›ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿýüÿþûùÿý÷ñÿüòèÿúíßÿùçÖÿøãÎÿ÷ÞÆÿöÙ½ÿõÓ²ÿó̧ÿòÇÿñÕÿð¿Žÿð¼‰ÿî¶ÿí°rÿî´{ÿî¶~ÿîµ~ÿï·ÿ﹄ÿð¼ˆÿð¿ÿð”ÿòÅšÿóÉ ÿôΨÿõÒ°ÿöعÿ÷ÜÁÿøàÉÿøäÏÿùæÓÿúéØÿûëÝÿøëÞÿæÜÓÿ‡‚}ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÄÄÄÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýûùÿ︂ÿøàÊÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôôôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿòÄ–ÿóË¡ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüôìÿïµ|ÿûîáÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿôÏ«ÿòÊ¢ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ­­­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿpooÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€€€ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿùŸþþþ¤þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÕÿð¾ÿøäÎÿûñåÿúìÝÿúéÙÿøãÏÿ÷ÞÅÿõغÿôÒ±ÿóΪÿóË£ÿòÇœÿòÕÿð¿ÿð»ˆÿÿ︂ÿ︂ÿé³ÿÖ¦wÿ…hKÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿuuuÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿî´|ÿùçÕÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿqqqÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿð½‹ÿôÒ°ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿî²xÿýöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿòÇžÿõÓ±ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŒŒŒÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ###ÿöööÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿºººÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿë<ýýý¨þþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþÿÿÿÿÿÿùãÏÿñÀ‘ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþüùÿûøôÿðëåÿÒËÅÿ{uoÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ10/ÿîêåÿþú÷ÿþûùÿþüúÿþýüÿþþýÿÿÿÿÿÿÿÿÿüôìÿî²xÿûðãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×××ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýøôÿ︃ÿ÷Û¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúêÚÿî´|ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿüòéÿñÁ’ÿöÛÀÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿkkkÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓÓÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçççÿ999ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÆýýýªÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÉÿñÁ“ÿûïäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿòòòÿãããÿ³³³ÿSSSÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÅ¥†ÿôЭÿõÔ²ÿõÖ·ÿöÙ¼ÿ÷ÜÁÿøàÈÿùãÎÿùçÕÿ÷ÞÅÿí°sÿùäÑÿûðäÿüòèÿüôëÿüõîÿý÷ñÿýùôÿýú÷ÿþüúÿþýýÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿLLLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüôëÿîµ}ÿùäÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøàÉÿðº…ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿð»ˆÿøäÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæææÿOOOÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ‚‚ÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿcccÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿô\¿¿¿ÿÿÿ°þþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÛÂÿòÄ–ÿüñæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿîîîÿßßßÿ½½½ÿqqqÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ›ƒlÿñÈ ÿòÆ›ÿñÄ–ÿñÁ“ÿñ¿ÿñ¾Žÿð¾Œÿð¾Œÿð¿Žÿï¹…ÿì®oÿñ¿ÿñÔÿñÄ—ÿñÆ›ÿòÉŸÿóˤÿôϪÿôÒ±ÿõ׸ÿöÛ¿ÿ÷ÞÄÿøàÉÿøãÎÿùæÓÿúéØÿúìÝÿûîâÿûðåÿüòéÿüõìÿý÷ñÿýùôÿþûøÿþüúÿþýüÿþþýÿýþþÿ¼¼¼ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûíàÿî´zÿúíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿöÖ·ÿò•ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿ﹃ÿûíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐÏÏÿ;;;ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ---ÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ–––ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÙÿÿÿþþþ¶ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö×¹ÿòÅ™ÿüóéÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿòòòÿÕÕÕÿ¬¬¬ÿgggÿ###ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿwwwÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿýøóÿüóëÿûïãÿúíàÿõÔ³ÿí³yÿ÷ÜÂÿöÚ½ÿõÔ´ÿôЭÿôͧÿóÊ¢ÿòÇœÿñÄ–ÿðÁ‘ÿð¿ÿフÿð½Œÿð¾Œÿð¾Œÿð¾ŽÿðÀÿñ“ÿòÄ–ÿòÆ›ÿóÉ ÿóÌ¥ÿôϪÿôÒ¯ÿõÔ´ÿö×¹ÿöÚ¾ÿ÷ÝÃÿñÙÃÿ0,(ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿþþþÿúçÖÿîµ{ÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿô̦ÿôͧÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøâÍÿï¹…ÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ¹¹¹ÿ(&$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔÔÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇÇÇÿ+++ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿúvôôôÿÿÿ½þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÒ±ÿòÇÿüôìÿÿÿÿÿÿÿþÿÿÿÿÿýýýÿÌÌÌÿyyyÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWVVÿïððÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÅÿﺅÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýúÿýùôÿüõîÿüòéÿûðåÿúíÞÿùèÖÿøãÎÿ÷ßÇÿ÷ÛÀÿöÙ»ÿõÕ´ÿôЭÿó̦ÿòÉŸÿòÆ›ÿñĘÿñÕÿñ“ÿñÁ’ÿî¾ÿž_ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÌÿî·€ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùõÿòÖÿöغÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿöÛ¿ÿð¾ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¡–‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿwwwÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿêêêÿOOOÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþãþþþÿÿÿÁÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóΩÿóÉ¡ÿýöïÿÿÿÿÿÿÿÿÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿEEEÿäääÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿõÕ¶ÿð¿ÿþûùÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþüúÿýùöÿýöïÿûòèÿûîáÿìÞÎÿ'$!ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ<5-ÿöÛ¿ÿøÞÅÿøáËÿùäÑÿùèÕÿúêÛÿûíàÿûðåÿõÔ³ÿï¹…ÿý÷ñÿþúöÿþûùÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýøóÿð»ˆÿøáÊÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿõÔ³ÿñÅ™ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâÌÿrTÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿ|||ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý…þþþýýýÂþþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿóË£ÿôˤÿý÷ñÿÿÿÿÿòòòÿ|||ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ===ÿÙÙÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΩÿòÆ›ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;0%ÿñÖÿñÔÿñ”ÿñÕÿñÕÿñÕÿò×ÿñÄ—ÿÿí²vÿòÈŸÿóÊ¢ÿóͧÿôÑ®ÿõÔ´ÿöغÿ÷Û¿ÿ÷ÝÄÿøáÊÿùäÐÿùèÖÿúëÛÿûíáÿüñæÿüôëÿý÷ñÿýúöÿþüúÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿïµ}ÿúè×ÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿôͧÿóͨÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷ÛÀÿñÀÿŒ‡‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¹¹¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿªªªÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþèÿÿÿÿÿÿÃÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóÈŸÿôͨÿýøóÿýýýÿ~~~ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ===ÿÓÓÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿòÈžÿóΨÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëëëÿ'''ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ><:ÿûñæÿûíàÿúêÛÿúèÖÿùåÑÿøáÊÿ÷ÝÃÿöÙ»ÿ﹄ÿð¼ŠÿôÓ²ÿôΪÿóÌ¥ÿòÉ ÿòÆœÿòÅ™ÿòÅ—ÿñÕÿñ“ÿðÀ‘ÿð¿ÿð¿ÿñÀ‘ÿñÁ“ÿñÄ–ÿòÆ›ÿóÉ ÿóÌ¥ÿôΩÿôÑ®ÿõÔ´ÿöغÿöÜÁÿ÷ßÈÿøãÎÿùæÓÿúéÙÿúíßÿüðæÿüôìÿý÷ñÿûïáÿí²wÿûïäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüöïÿòÆšÿõ׸ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÕµÿòÖÿþúöÿˆˆˆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿMMMÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓÓÓÿ:::ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ‰øøø'ÿÿÿÇþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÆšÿôЭÿýùõÿ©©©ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿAAAÿÑÑÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñ“ÿõÔ´ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿñ“ÿôÔ³ÿÿÿÿÿþþþÿþûùÿýøóÿüõíÿüòéÿûðåÿûíßÿúéÙÿùåÒÿøâÌÿ÷ßÇÿ÷ÝÃÿöÚ¾ÿõÖ·ÿõÒ°ÿôΩÿóˤÿóÊ¡ÿòÈ ÿòÆ›ÿñŘÿñÄ–ÿñ”ÿñ”ÿñ”ÿñ“ÿñ”ÿñ”ÿñÖÿñÄ—ÿñÁ“ÿí®pÿòÈÿôΩÿõÒ¯ÿõÕµÿöØ»ÿ÷ÜÁÿøßÇÿøãÏÿùçÕÿúëÛÿûîáÿûñæÿüôìÿý÷òÿþú÷ÿþýüÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿð¿ŽÿøáÉÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿôÏ«ÿóÉ ÿÿÿþÿÿÿÿÿŠŠŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿãããÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîîîÿcccÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿéùùù2ýýýÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿòÕÿõÓ³ÿëçäÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿKKKÿÕÕÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð½‹ÿöÙ½ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçççÿ,($ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿýùõÿðº…ÿ÷ÜÂÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþûùÿýùõÿýøóÿýöðÿüôëÿûñæÿûîáÿúëÛÿúé×ÿùæÔÿøãÎÿøßÈÿ÷ÜÁÿöÙ½ÿõÖ·ÿòÅ™ÿî³yÿõÑ­ÿóÌ¥ÿòÊ¡ÿòÈžÿòÆœÿñĘÿñ”ÿðÀ‘ÿð¿Žÿð¾ÿð¾Œÿð¿ŽÿñÀ‘ÿñÕÿòÅšÿóÈŸÿóˤÿôΨÿõѯÿõÕ¶ÿöÚ½ÿ÷ÞÄÿøâËÿùåÒÿúéØÿúíßÿüòçÿüõîÿýùôÿþûøÿþýüÿûíßÿﺆÿúìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüõíÿòÉŸÿõÑ®ÿÿÿÿÿÿÿÿÿÿÿÿÿŒŒŒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿzzzÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿ’’’ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿúúú=ÿÿÿÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿñÀ‘ÿö×¹ÿ‹Šˆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÝÝÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿ﹄ÿ÷ÞÅÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿž|ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿï¶}ÿùåÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿöÚ½ÿñÀÿþþüÿýøòÿüõîÿüóêÿüñçÿûîâÿúëÜÿùè×ÿùåÒÿøãÎÿøáÊÿ÷ÞÅÿöÚ¾ÿõÕ¶ÿôÑ®ÿóΨÿóÌ¥ÿóË£ÿòÈžÿñÆ™ÿñÕÿñÁ’ÿðÀ‘ÿñ¿ÿð¿ŽÿðÀÿðÀÿñÁÿðÁ’ÿñÕÿñÅ™ÿñÁ“ÿí±vÿòÈŸÿõÔ´ÿö׸ÿ÷Û¿ÿ÷߯ÿøãÎÿúçÕÿúëÜÿûïâÿûòèÿüõîÿýøôÿþüùÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðäÿñÕÿöÚ¿ÿÿÿÿÿþÿÿÿÿÿþÿÿÿÿÿ“““ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôôôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ½½½ÿ"""ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿãÿÿÿFÿÿÿÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ñÿð¾ÿöÛÀÿ###ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿvvvÿçççÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿî¶~ÿùäÏÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÝÀ£ÿ:.#ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñåÿï´zÿúëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿôѯÿóˤÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿþûøÿýùôÿý÷òÿýöðÿüôìÿûñçÿûîãÿúìÞÿúêÛÿúéØÿùåÒÿøâÌÿ÷ÞÆÿ÷ÜÁÿöÙ½ÿõ×¹ÿõÓ²ÿò•ÿî²xÿóË£ÿòÉ¡ÿòÇÿñŘÿñ”ÿð¿ÿð½‹ÿﻈÿﻈÿ)ÿð¾ŒÿñÀÿñ•ÿñÆšÿóÈ ÿóˤÿôЫÿõÓ³ÿöØ»ÿ÷ÜÂÿ÷àÉÿùäÑÿúéÙÿûíáÿûòéÿü÷ðÿþúöÿþýûÿþþýÿþÿÿÿÿÿÿÿúìÝÿð¿ÿùçÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¡¡¡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿšššÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿßßßÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿnÿÿÿHÿÿÿÚþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿkÿϺ¦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ•••ÿóóóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿî´zÿúëÛÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòˤÿ¦‰mÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿî´zÿüñåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþûøÿóÉ ÿõÕµÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿþþþÿþþýÿþýüÿýøóÿõÕµÿð¾ÿýöïÿüôìÿüòèÿûðäÿûíáÿúëÜÿúéÙÿùçÕÿùåÒÿøâÌÿ÷ÝÄÿöÙ¼ÿõÔ´ÿôÑ®ÿôΪÿóÌ¥ÿóÈŸÿñÅ™ÿñ”ÿð¿ÿð¾Œÿð¼Šÿ)ÿð¼‰ÿ*ÿkÿð¾ÿð¿ÿñ”ÿñÆšÿóÊ¢ÿòÄ—ÿî´|ÿóÌ¥ÿ÷ÜÁÿ÷àÇÿùäÏÿúèØÿúíßÿûðæÿ«¦ ÿ"! ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ---ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóóóÿvvvÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÔ ÿÿÿNýýýÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿjÿ—‰{ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;;;ÿ¸¸¸ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿî²xÿüñçÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿñÕÿâÀ ÿXXWÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøâËÿîµ}ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿþúöÿñÀÿ÷߯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿôÒ¯ÿòÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýûÿþûøÿýùõÿýøóÿýöðÿüõíÿüóéÿûñæÿûïãÿûíàÿúìÞÿùèØÿùåÑÿøáÊÿ÷ÝÅÿ÷ÛÀÿöÙ¼ÿõÖ·ÿõÒ°ÿôͨÿð¿Žÿî²xÿñÄ—ÿñÄ–ÿñÁÿð½‹ÿﺇÿ﹄ÿ︃ÿ﹄ÿ³Œeÿ6*ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ§§§ÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿþþýÿ§§§ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿPüüüYÿÿÿäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðæÿð½‹ÿxmcÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿnnnÿØØØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùéØÿî³zÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿﻈÿöÙ¼ÿ½½½ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿBBBÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöØ»ÿï¹…ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ðÿï·ÿúéØÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýøóÿóÊ¡ÿôÑ­ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþýüÿþýûÿþüúÿþûøÿýúöÿüôìÿôÒ¯ÿñÀÿûñæÿüóéÿûðäÿûîáÿúìÞÿúëÜÿúéØÿùåÒÿøáÊÿ˵žÿPF<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ333ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÑÑÑÿ(((ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ¸ÿÿÿgÿÿÿìþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìßÿð¾‹ÿne]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ$$$ÿ£££ÿðððÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÎÿîµ}ÿýùôÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿîµ}ÿøáÊÿôôôÿwwwÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ,,,ÿÞÞÞÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôϪÿñ¿ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüñçÿî²yÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýõîÿñÂ’ÿöÛÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿôÏ«ÿóÉŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿþüúÿàÝÚÿtrpÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ‚fÿóÉ¡ÿôΩÿõÔ±ÿâǬÿOG>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿü3ÿÿÿuýýýóþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùèØÿð¾ÿwnfÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿeeeÿÒÒÒÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÄÿ﹄ÿýùõÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþüÿí²wÿùè×ÿÿÿÿÿÎÎÎÿ,,,ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ///ÿQQQÿ“““ÿÙÙÙÿÿÿÿÿÿÿÿÿÿÿÿÿòÇ›ÿóÇÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúéÙÿí±wÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûñçÿﻆÿùçÓÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿüõíÿòÇžÿõѯÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðððÿ™™™ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ1*#ÿóͧÿòÈžÿê¼ÿ€eKÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿŠüüüÿÿÿùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÑÿð¿ÿ•‹‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ,,,ÿ¯¯¯ÿîîîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿõÖ¸ÿð¾ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿí°uÿûíàÿÿÿÿÿýýýÿ–––ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ)))ÿJJJÿŽŽÿ×××ÿñ¿ÿôЫÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿøáÊÿî´|ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúëÜÿï·€ÿûðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüñåÿñÁ’ÿ÷ÛÀÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿ¹¹¹ÿ,,,ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ—•“ÿýøóÿ¼¸³ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿßÿÿÿ„þþþüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøáÊÿñÁ’ÿÍ·ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ………ÿáááÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЫÿñŘÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüðåÿí±wÿüòêÿÿÿÿÿÿÿÿÿãããÿTTTÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ#""ÿ@1#ÿ…tdÿ×××ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷Ù½ÿﻈÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøäÏÿî·ÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÛÿð½‹ÿùæÒÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕÕÕÿaaaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ---ÿÔÔÔÿ...ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿTÿÿÿ„þþþüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÆÿñÕÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿeeeÿÖÖÖÿöööÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÉ ÿóË¥ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúèÖÿî¶}ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿµµµÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿ>>>ÿ………ÿÖÖÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿõÒ°ÿñĘÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿ÷ÜÁÿﻈÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿùäÐÿð¼‰ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿëëëÿ•••ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"""ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ¨ýýý‡ÿÿÿûþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿ÷ÛÀÿòŘÿûðæÿ~~~ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿPJCÿÇÇÆÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿñÕÿôÓ±ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ßÇÿﺆÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿ999ÿ‚‚‚ÿÖÖÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿóÈ ÿôÏ«ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÔ´ÿñÁ“ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÝÃÿð½‹ÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿÃÃÃÿ<<<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿð,ÿÿÿŽÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö׺ÿòÇœÿüòèÿíííÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿKGCÿ¼‘iÿìÛÊÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð¾ÿöغÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÖ¸ÿðÀÿþüùÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÙÙÙÿFFFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿ333ÿ~~~ÿÔÔÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿþüúÿð¿ŽÿöÛÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿóˤÿóË£ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÖ·ÿñ“ÿýúøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæææÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿbÿÿÿ—ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÓ³ÿóÉ ÿüôìÿÿÿÿÿ   ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ\\\ÿÍÍÍÿïÞÎÿÿúêÚÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýüÿﻆÿ÷ÛÁÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЬÿòÆœÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿªªªÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ...ÿ{{{ÿÑÑÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿþûøÿï¶ÿúçÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿýøóÿñ”ÿöÕ¶ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿôΩÿóÈŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûûûÿ¿¿¿ÿ555ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿ®ýýý¡þþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÏ«ÿóˤÿüöïÿÿÿÿÿüüüÿeeeÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿtttÿßßßÿùùùÿÿÿÿÿøãÎÿð»‰ÿûíßÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúõÿï·ÿøáÊÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿòÈžÿóͧÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿwwwÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ(((ÿxxxÿÏÏÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿý÷ñÿî°uÿýòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷ðÿﻇÿøáËÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿüõîÿòÆšÿõÒ°ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíííÿ‡‡‡ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿì0ÿÿÿ¦þþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóÌ¥ÿóͧÿý÷òÿÿÿÿÿÿÿÿÿ÷÷÷ÿZZZÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ>>>ÿ§§§ÿòòòÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÄÿð½‹ÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿîµ}ÿúçÕÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÀÿõÕ´ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÞÞÞÿHHHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ###ÿvvvÿËËËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿüóéÿí®rÿÿûúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûóéÿîµ~ÿúìÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿðÀÿ÷ÝÃÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÑÑÑÿLLLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ_ýýý¦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÉ ÿôϪÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿ‚‚‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ(((ÿ€€€ÿÛÛÛÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöØ»ÿñ¿ÿüòéÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïäÿî´{ÿûîáÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿﺅÿöÝÂÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ§§§ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿsssÿÇÇÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûéÚÿî±wÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúìÞÿíµ{ÿüõïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìÞÿð¼ˆÿùèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ°°°ÿ,,,ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿýýýªþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÇÿõÑ®ÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÐÐÐÿFFFÿÿÿÿÿÿÿÿÿÿÿ+++ÿwwwÿÐÐÐÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿõÔ³ÿñ“ÿüôíÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÙÿî´|ÿüóêÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿîµ}ÿùäÐÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿnnnÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿpppÿÄÄÄÿýýýÿþþþÿÿÿÿÿÿÿÿÿþþýÿøßÇÿ︃ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøäÏÿï·€ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùæÒÿðº‡ÿûñåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöööÿŒ‹‹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÔ+ÿÿÿ ÿÿÿ²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿñÅšÿõÓ³ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿØØØÿ}}}ÿ>>>ÿÿÿ ÿÿMMMÿÿÝÝÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿôÏ«ÿòŘÿýöîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøäÏÿï¶ÿý÷ñÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôíÿí²xÿúëÝÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèèèÿKKKÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿnnnÿÁÁÁÿøøøÿûûúÿõÒ²ÿñ•ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷Ú½ÿð½Šÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÞÄÿð¼‰ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿìììÿuldÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿùMõõìüøô»ýúöÿþûøÿþûùÿþüúÿþüûÿþýüÿþþýÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿþüúÿñÖÿö×·ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿô̤ÿóÈžÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÄÿï¹…ÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïãÿî²vÿûñçÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍÍÍÿ444ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿiihÿ¶•wÿçßÿùùùÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûùÿôϪÿòÅšÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþú÷ÿõÕµÿñÁ‘ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùâÌÿÖ¨{ÿljhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿxò¿™(ñÉ ÄôͧÿôÒ°ÿö×¹ÿöÛ¿ÿ÷ÝÃÿøáÊÿùåÒÿúëÛÿûïäÿüóêÿüóëÿüôíÿüõïÿý÷ñÿýøóÿýùôÿýúöÿþú÷ÿþûùÿþüûÿþýüÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøôÿñÁ“ÿ÷Ú¾ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÈžÿóͦÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿõ×¹ÿï¾ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÚÿî³yÿüõíÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¦¦¦ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿhhhÿ»»»ÿìììÿöööÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿñÅ—ÿôЭÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿýøóÿó̦ÿóÉ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿöÙ¼ÿò–ÿÿÿÿÿèèèÿwwwÿÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿ¥ôÑ­2óÌ¥ËóÈžÿñÖÿð¿Žÿ)ÿï¹…ÿÿî·€ÿîµ~ÿîµ~ÿï¶ÿ︂ÿﻇÿðÀÿòĘÿòÉ ÿôΩÿõÒ¯ÿõÕµÿöÙ»ÿ÷ÝÄÿøâÌÿùçÔÿúéÙÿúëÛÿúìÞÿûïâÿüñçÿüóëÿýöïÿúíßÿð¾ŒÿöÙ½ÿýùôÿþûøÿþûøÿþüúÿþýûÿþþýÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþþüÿñ×ÿõÑ®ÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÑ®ÿñÄ—ÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÎÿï·€ÿýøóÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ}}}ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿeeeÿ···ÿåååÿóóóÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿýùõÿð»ˆÿ÷Ü¿ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿýöïÿòŘÿõÓ³ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿõЬÿôͧÿÿÿÿÿþÿÿÿÿÿÿÿðððÿ‹‹‹ÿ###ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÎ1ÿÿÿ6ÿÿÿÍÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþüúÿýùôÿýôíÿüðåÿúëÝÿùèÖÿùãÎÿ÷ÞÆÿöÙ½ÿõÔ´ÿôϬÿóˤÿòÇÿñÄ—ÿñÀ‘ÿð½‹ÿﺅÿÿî·€ÿî·ÿ﹄ÿð¼ˆÿð¾ŒÿðÀ‘ÿñÖÿð”ÿî²xÿñÁ’ÿôÑ®ÿõÕµÿõعÿöÚ¾ÿ÷ÝÃÿøáËÿùæÓÿûëÛÿûîáÿûïãÿûðåÿüòèÿüóëÿüõîÿý÷ñÿýøóÿýùõÿþú÷ÿþüúÿþýüÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿñÁ’ÿöÖ·ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿòÊ¢ÿóË£ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÚ¾ÿð¼‰ÿýú÷ÿþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿ]]]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿaaaÿ²²²ÿßßßÿïïïÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýøóÿîµ|ÿùæÓÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿð¾ŒÿøßÆÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿóÈÿöÙ¼ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿœœœÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿçLÿúÿ7ÿÿÿÎþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþüúÿýúöÿýøòÿüõíÿûñçÿûíßÿúèÖÿøâÍÿ÷ÝÄÿöÚ½ÿóͧÿîµ}ÿñÀÿòÇÿñÕÿðÀÿð½‹ÿﻈÿﺆÿ﹄ÿ︂ÿ︄ÿﺆÿjÿñÀÿñÄ—ÿòÈžÿóͦÿôЬÿôÒ°ÿõÖ·ÿöÚ¾ÿøÞÅÿøâÌÿùåÑÿùæÔÿùè×ÿúëÛÿûíàÿûïäÿûñçÿüòéÿüõîÿüñæÿð½‹ÿöعÿýøòÿþûùÿþüúÿþýýÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñĘÿôÑ®ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôѯÿñ”ÿþüùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçççÿAAAÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ^^^ÿ­­­ÿÙÙÙÿìììÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýôëÿî³yÿüðåÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíàÿðº…ÿúéÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿûîâÿñÀ‘ÿùäÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÎÎÎÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿökÿÿÿ>ýýýÓþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðäÿðÀ‘ÿùæÕÿÿÿÿÿÿÿÿÿþþþÿþüûÿþùõÿüõîÿûñçÿúíßÿùèØÿùåÑÿøàÉÿ÷ÜÁÿö×¹ÿõÓ±ÿôΪÿóË£ÿòÇžÿòÄ—ÿñÀ‘ÿð¾Œÿð»ˆÿﺇÿﻇÿ)ÿð¾Œÿð¿ÿð“ÿñÄ–ÿñÅšÿòÈžÿòÈŸÿî³yÿñÕÿõÓ²ÿõÖ·ÿöÙ¼ÿ÷ÜÄÿøáËÿùæÓÿúéØÿúêÛÿúìÝÿûîáÿûðåÿüóéÿüõíÿýöðÿýøòÿýúöÿþûùÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÀÿõ׸ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÉŸÿòÉ ÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÉÉÉÿ---ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[[[ÿ¦¦¦ÿÓÓÓÿèèèÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿúëÛÿî´{ÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùæÔÿ﹄ÿûñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿÿÿÿÿúêÛÿð»‡ÿûîâÿÿÿÿÿÿÿÿÿÿÿÿÿðððÿ222ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿý‰ ûûûHÿÿÿÙþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùè×ÿðÀÿúçÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿþüûÿýú÷ÿýøòÿýõîÿüòèÿûîáÿúéÙÿøäÐÿøßÈÿ÷ÜÀÿõغÿõÔ³ÿóÉ ÿí³xÿð¾ŒÿñÄ–ÿð“ÿñÀÿð¾ÿð¼Šÿﻈÿð»ˆÿð¼‰ÿð¾ÿðÁ‘ÿñÄ–ÿòÇÿóË£ÿóͧÿôϪÿôÒ°ÿõÖ·ÿöÚ½ÿ÷ÝÄÿøàÈÿøáËÿøãÏÿùæÔÿúéÙÿúìÞÿûîáÿûïäÿûòèÿüôëÿýöðÿýøóÿﻇÿöÙ»ÿýúöÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿðÁ’ÿôÑ­ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ­­­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿWWWÿŸŸŸÿÍÍÍÿåååÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿøàÈÿï¹…ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÞÅÿð¼ˆÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÓÿðº…ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿiiiÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ£þþþRþþþàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøäÐÿñÀÿúêÙÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿð»‰ÿùåÑÿþþýÿþýûÿýúöÿüöðÿüòèÿûîáÿúêÚÿùæÔÿøãÍÿ÷ÞÆÿ÷Ú¾ÿöÖ·ÿõÒ°ÿôϪÿóÌ¥ÿòÈžÿòŘÿñ“ÿðÀÿñ¿Žÿð¾ÿð¿ÿñÀÿñÁ’ÿñÕÿòÄ—ÿñÅ™ÿñÇœÿòÉ ÿóË¥ÿóΨÿî²wÿñÖÿõÔ³ÿöØ»ÿ÷ÝÂÿ÷áÊÿøäÏÿùåÒÿùçÖÿúêÚÿûíßÿûðåÿüóéÿüôíÿýöðÿýùôÿþûùÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿﻇÿö׺ÿþýýÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ’’’ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿTTTÿ———ÿÆÆÆÿáááÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿõÔ´ÿð“ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÔ³ÿñÁ’ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿ÷ÞÅÿñ¿ÿÿÿÿÿÿÿÿÿÿÿÿÿ£££ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¹(ÿÿÿXÿÿÿäþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÉÿñÁ’ÿúìÞÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿúéÙÿﺇÿùèÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþÿþýúÿýû÷ÿýøóÿýöïÿûóêÿûïãÿúëÛÿùæÔÿøâÍÿøßÆÿöÛ¿ÿö׸ÿõÒ±ÿôÏ«ÿòÇÿí°sÿð¿ÿòÄ—ÿñ“ÿðÀÿð¾Žÿð¾ÿð¾Žÿð¿ÿðÁ’ÿñÖÿòÆ›ÿòÈŸÿòÊ¢ÿóË¥ÿôϪÿõÒ¯ÿõÕµÿöØ»ÿöÚ¿ÿ÷ÜÂÿ÷߯ÿøâÌÿùåÒÿúè×ÿúëÛÿûíßÿûïãÿüòèÿüõíÿý÷òÿýùõÿþýûÿî¶ÿ÷ßÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿ€€€ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿQQQÿÿ¿¿¿ÿÞÞÞÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿþüùÿòÉ¡ÿóˤÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿóÊ¡ÿóÊ¢ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýúöÿõÓ³ÿóÉ ÿÿÿÿÿÿÿÿÿÑÑÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÊ8üüüZþþþåþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÃÿñ•ÿûîáÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÑÿﻈÿúëÝÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóéÿî¶ÿúéÙÿýúöÿý÷ñÿüóêÿûïäÿûìÞÿúéØÿøåÒÿøâËÿ÷ÞÅÿ÷Ú¾ÿöÖ·ÿõÔ²ÿôЬÿó̦ÿóÉ ÿòÆ›ÿñÄ—ÿñÕÿñ”ÿñ”ÿñ”ÿñÕÿñÄ–ÿñÄ—ÿñŘÿñÅ™ÿòÇœÿòÉŸÿóÊ¢ÿóË¥ÿóΪÿí°sÿòÇÿöعÿ÷ÜÁÿ÷ÞÆÿøàÉÿøãÎÿùæÔÿúêÚÿûíàÿûñæÿûóêÿüõîÿýøóÿþûùÿÿþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿpppÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿMMMÿˆˆˆÿ¸¸¸ÿÚÙÙÿüüüÿþûøÿð¿ŽÿõÖ¶ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿý÷òÿñ“ÿõÕµÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýõîÿóÊ¢ÿõÔ´ÿÿÿÿÿñññÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÚGÿÿÿ\ýýýæþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÚ¾ÿñĘÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÈÿð¼‰ÿûïãÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿúëÜÿî¶ÿüðæÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþüúÿþûøÿýùõÿý÷ðÿüôëÿûðåÿúìÞÿùéØÿùåÒÿøâÌÿ÷߯ÿöÛ¿ÿö×¹ÿõÓ²ÿôЭÿóΨÿòÆšÿí¯rÿñÁ’ÿñÄ–ÿñ“ÿñÁ‘ÿðÀ‘ÿðÁ‘ÿð“ÿñÖÿñĘÿòÆ›ÿòÇœÿòÈŸÿóË¢ÿôͧÿôЬÿôÒ°ÿõÕ´ÿö׸ÿ÷Ú¾ÿ÷ÝÄÿóÜÇÿc[SÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿGHHÿÿ¯¬ªÿÈškÿõÝÅÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿﻈÿøáÊÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüñçÿòÁ’ÿøàÉÿÿÿÿÿzzzÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùUüüücÿÿÿëþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿö׺ÿòÇ›ÿûòçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿ÷ÜÂÿð¾ÿûñæÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÑÿ︂ÿüôìÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÞÿîµ|ÿúêÜÿüôìÿüñæÿûîáÿúëÜÿùè×ÿùåÐÿøáÊÿ÷ÝÅÿ÷Û¿ÿöغÿõÔ´ÿôѯÿôͨÿóË£ÿòÉŸÿòÇœÿòÆ›ÿòÅšÿòĘÿñÄ—ÿåºÿXH7ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ?/ ÿvogÿ©©©ÿÔÔÔÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿûïãÿ︂ÿúëÜÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿûîáÿðº†ÿúëÝÿ­­­ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ………ÆÿÿÿnÿÿÿóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõÔ³ÿóÉ ÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿöغÿñÁ’ÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÞÆÿﻇÿüõîÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÕÿÿüöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþüûÿþûøÿýùõÿý÷òÿüôíÿüòèÿûîâÿúëÜÿùè×ÿæÔÂÿWPHÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ@@@ÿqqqÿ¢¢¢ÿÐÐÐÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùæÔÿ︂ÿüóéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúêÛÿï·ÿÔÎÈÿ222ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ›››ÿüüü|þþþ{ýýýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÑ­ÿóˤÿüöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõÓ²ÿñÅ—ÿüôëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÙ¼ÿð¿ŽÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÊÿð¼‰ÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿèèèÿYYYÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;;;ÿjjjÿšššÿÍÍÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÝÂÿﻇÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿøâÍÿ泂ÿ[[[ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ˜˜˜þþþþÿÿÿÿQýýýˆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóͧÿóΨÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΪÿòÉžÿüõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôÓ±ÿñÄ—ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÙ¼ÿñÂ’ÿþùöÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþÿÿþÿÿÿåååÿ[[[ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ777ÿaaaÿ“““ÿÊÊÊÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿõÒ¯ÿñÁ“ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿö׺ÿƒjRÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿšššÿÿÿÿÿþþþÿ÷÷÷$ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÊ¢ÿôЬÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóË¢ÿôͧÿý÷ñÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿó̦ÿòÊ¢ÿýøôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЭÿòÈÿþû÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿåååÿaaaÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ333ÿYYYÿŒŒŒÿÆÆÆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿþÿÿÿÿÿÿÿÿÿýúöÿòÈÿóË£ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿý÷òÿ°“xÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŸŸŸÿÿÿÿÿÿÿÿÿþþþíßßßÿÿÿ‘ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóÈŸÿõÒ°ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿòÇœÿôÑ®ÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿòÆœÿôЬÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿòÇÿôÏ©ÿþüúÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçççÿhhhÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ,&!ÿMD;ÿthÿ¾®žÿùèÖÿúìßÿûñæÿüóêÿýöîÿýùõÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿñÀÿöÙ»ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÛÔÍÿA4(ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¦¦¦ÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÇÿÿÿ–ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿòÆœÿõÔ³ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýüÿñÄ—ÿõÔ´ÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÁ’ÿöÖ¶ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð¿ÿö×·ÿþüûÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿéééÿuuuÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ'ÿD6'ÿv\Cÿ´Œeÿî¹…ÿﻇÿð¼Šÿñ¿ŽÿñÁ“ÿòÅ™ÿòÈžÿóË¥ÿôЭÿôÒ°ÿîµ}ÿôΩÿúéØÿúëÛÿûïâÿüôêÿýøóÿþýûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿúúúÿnieÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ±±±ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýý—ÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿòÅ™ÿõÖ·ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþûøÿñ“ÿõ×¹ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿð½ŒÿöÚ¾ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿï¹…ÿ÷ÞÃÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿîîîÿ‚‚‚ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿ$!ÿ@;5ÿti_ÿ¹¥’ÿó×¹ÿõÕ´ÿõÑ­ÿôͨÿóÊ¢ÿòÈÿðÁ‘ÿí®rÿﻈÿñ¿Žÿð½Šÿﻈÿﺆÿﺅÿﻇÿð»‰ÿð¾ŒÿñÁ’ÿòÆšÿóË£ÿôÏ«ÿõÓ²ÿö×¹ÿ÷ÛÁÿøàÊÿùæÓÿúëÝÿûîãÿûòçÿüõíÿýúõÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¾¾¾ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüübÿÿÿééé ýýý¥ÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿñÄ—ÿöÙ¼ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿðÀÿöÛÀÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýüùÿﺆÿöÝÄÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïµ~ÿùäÏÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòòòÿ’ŽŠÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿ::9ÿqonÿ»¸µÿùôïÿý÷ñÿüõîÿøÞÅÿî¶~ÿúëÛÿüðåÿúìßÿúêÚÿùçÕÿùäÐÿøáËÿ÷ÞÆÿ÷ÛÀÿö×¹ÿõÓ±ÿôϪÿóË£ÿòÇœÿñÄ–ÿðÀÿð½‹ÿﺆÿ︃ÿï·ÿî·€ÿî·ÿÿð»ˆÿð½ŒÿðÁ‘ÿñÄ—ÿòÈŸÿóΪÿ½¤‹ÿ,'"ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ,,,ÿÍÍÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿÿÿÿ1ÿÿÿÿÿÿ¬ÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿñ•ÿöÛÁÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿð¾ÿ÷ßÇÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøòÿ︃ÿøãÍÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþû÷ÿî´|ÿúêÙÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõéÞÿšuPÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿ444ÿlllÿ¹¸¸ÿôÙ¾ÿﻈÿþýúÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþýÿþýüÿþýûÿþüúÿþûøÿþúöÿýùôÿýøòÿý÷ñÿüöïÿüôìÿüòèÿûðåÿûîáÿûìÝÿúéØÿùåÑÿøàÉÿöÛÁÿõ×¹ÿõÔ³ÿôЬÿóÌ¥ÿÛµÿTE5ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿA@@ÿÛÛÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïïïÿÿÿÿÿÿ¯ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûòçÿñ”ÿ÷ßÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûðäÿð½ŠÿøãÎÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüòèÿï·ÿùèÖÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿîµ}ÿûîáÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúëÜÿë±yÿµ­¥ÿ###ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ,%ÿaN;ÿ···ÿûûûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿþþþÿþþýÿþýüÿþüúÿþûùÿþûøÿþú÷ÿüøôÿ„‚€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿcccÿæææÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæþþþðððÿÿÿ¯þþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûïâÿñ“ÿøâËÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÞÿð½ŠÿùçÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìÞÿ︂ÿûíàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúìÝÿï·ÿüòèÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùâÌÿî·€ÿüõíÿËËËÿ???ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ%&&ÿcccÿµµµÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ²²²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ~dLÿâ¸ÿòÉ ÿóͨÿôÒ°ÿöغÿ÷߯ÿøåÏÿùçÖÿûëÝÿúïä¸ÌÌÌÿÿÿÿÿÿ²ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûìÞÿñ“ÿùäÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúéØÿð½‹ÿúëÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÓÿï¹…ÿüòçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøãÎÿﻈÿýõîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÙ¼ÿ(ÿýøõÿþþþÿÞÞÞÿ```ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ___ÿ²²²ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÔÔÔÿ==<ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¥’€ÿìίÿôЭÿóË¥ÿòÆœÿñ”ÿð¾Œÿð»…ÿï·€ÿïµ|ÿî³zÿïµ}€ªªUÿÿÿÿÿÿ¹ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùè×ÿñÁ“ÿùåÓÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÑÿñ¾ÿûíßÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷àÈÿ*ÿüóëÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÜÀÿñÀÿýøóÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôЬÿñ”ÿþüúÿÿþþÿÿÿÿÿïïïÿƒƒƒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿ\\\ÿ®®®ÿýýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿïïïÿnnnÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"""ÿÉÈÈÿúùøÿþýûÿþüûÿþüúÿþüúÿþûùÿþúöÿþøôÿý÷ñÿýõíÿüòèÿ÷éÛHþþþ)ýýýÁÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùäÐÿñÁ“ÿúè×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿ÷àÉÿðÀÿûîâÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÚ¿ÿð¿ÿüôìÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÔµÿòÆšÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÇÿóË¢ÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿüüüÿ¨¨¨ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿXXXÿ¬¬¬ÿùùùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿŸŸŸÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿRRRÿãããÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿþþþÿýýýþþþþÿõõõÿÿÿ3ýýýÈþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøàÉÿñÁ“ÿúëÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿ÷ÛÀÿñÔÿûðæÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿõÕ´ÿñĘÿüöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿó̧ÿò̤ÿþú÷ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿðÀÿõÓ±ÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÍÍÍÿ===ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿTTTÿªªªÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÇÇÇÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿˆˆˆÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿ;þþþÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÝÃÿñ•ÿûíàÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÖ·ÿòÆšÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΩÿóÊ¡ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÅšÿôÒ°ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿﻇÿöÚ¾ÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿíííÿlllÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿPPPÿ¨¨¨ÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿáááÿNNNÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ···ÿüüüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÖççç ÿÿÿ=ýýýÐÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿöÚ¾ÿòÄ—ÿûïãÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿõÒ°ÿóÉŸÿüôìÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòÉŸÿóϪÿýùôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð¿ŽÿöÚ¼ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýû÷ÿî·€ÿøâÌÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ   ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿMMMÿ¨¨¨ÿåååÿˆˆˆÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿMF@ÿàààÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿ¡ÿÿÿûûûFýýý×þþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿöغÿòÅšÿüñçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôΩÿó̤ÿýöðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÖÿõÕµÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ﹄ÿøàÉÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüôìÿîµ}ÿúêÚÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ×××ÿGGGÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿˆiLÿôæÚÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüüüh¿¿¿ûûûPþþþàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿöÕµÿòÈžÿüóëÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóË£ÿôΪÿýøòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿð¿ÿöØ»ÿþûùÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿî¶ÿúæÔÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúíßÿïµ|ÿüñæÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ„„„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;;;ÿİœÿð½Šÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþþÿúúú6ÿÿÿ\ÿÿÿêþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôѯÿóÊ¢ÿüöïÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿòÈžÿõѯÿýùõÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿjÿöÝÂÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿîµ|ÿúëÜÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùåÑÿï·ÿý÷ñÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿËËËÿ>>>ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€€€ÿôñîÿõÖ·ÿñ”ÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿüüü\ÿÿÿÚýýýìýýýìþþþïÿÿÿñýýýòýýýôþþþöýýýúÿÿÿýþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿóͧþóͧÿýøóÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüúÿòÅ™ÿõÕµÿþú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøóÿð»‡ÿøàÉÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿî¶~ÿûïäÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿ÷ÝÃÿﺆÿþûøÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ„„„ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿAAAÿÄÅÅÿÿÿÿÿýøóÿó̦ÿóÌ¥ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñðððÿÿÿ ÷÷÷!úúú3ÿÿÿGüüüZüüühÿÿÿmüüüyýýýŒÿÿÿ¢ýýý¸ÿÿÿËÿÿÿ×ÿÿÿÙÿÿÿÜþþþàÿÿÿäÿÿÿçþþþéÿÿÿêÿÿÿìýýýðÿÿÿóþþþöÿÿÿøÿÿÿùýýýûÿÿÿýþþþÿÿÿÿÿþþþÿóË£ÿôÏ«ÿýú÷ÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýùôÿñ”ÿöÙ¼ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóêÿﺅÿùåÒÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùæÕÿ︃ÿüòéÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿõÔ´ÿðÀÿþüùÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÕÕÕÿLLLÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ###ÿ‹‹‹ÿúúúÿÿÿÿÿÿÿÿÿüôìÿñÔÿö×¹ÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýýý¾þþþÿÿÿôôôÿÿÿ,úúú=ûûûJÿÿÿNÿÿÿYÿÿÿlþþþ~ÿÿÿýýý™ÿÿÿžýýý§ÿÿÿ´ýýýÂÿÿÿÎÿýüÕñÈž×ôÑ®ÚýûùÞþþþâýýýçýýýêÿÿÿëþþþîÿÿÿóýýýøýýýýþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýþÿÿÿÿüöîÿðÁÿ÷ÝÂÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûíßÿðº…ÿúêÛÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ÷߯ÿð½ŠÿýõîÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿóË¥ÿòÇœÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¡¡¡ÿ000ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ[[[ÿÖÖÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîáÿ(ÿùãÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿˆÿÿÿÿÿÿÿÿÿå²f óÝÇøøø)ÿÿÿ<ÿÿÿNÿÿÿYÿÿÿ`ÿÿÿnýýý‚ýýý—ÿÿÿ«ýýý»ÿÿÿÃþþþÅþþþÊÿÿÿÐýýýÖýýýÛÿÿÿÝýýýßÿÿÿãÿÿÿèþþþíÿÿÿñÿÿÿóÿÿÿõýýýøþþþüÿÿÿÿþþþÿþþþÿÿÿÿÿüòéÿñ¿ÿøàÉÿÿþþÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿùçÕÿﻈÿûïãÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿõÖ¶ÿñ”ÿý÷òÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿñÄ–ÿôÏ«ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóóóÿuuuÿ%%%ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ@@@ÿ°°°ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿùæÔÿðº…ÿûðäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿTÿÿÿªªªòòò÷÷÷$ÿÿÿ0úúú8ÿÿÿ=ûûûLüüü\ÿÿÿmüüüzÿÿÿ€ýýýˆÿÿÿ”þþþ£ÿÿÿ²ÿÿÿ¾ÿÿÿÃÿÿÿÆùïäËフÒ÷âÍÙþþþßþþþâýýýäýýýéýýýðýýý÷ýýýüÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿýýýþÿÿÿÿÿÿÿÿÿÿÿÿøáËÿð½ŒÿûñçÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿóͨÿòÇÿýùôÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿð½‹ÿöÙºÿþýüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÓÓÓÿ]]]ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ555ÿŽŽŽÿøøøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþüûÿ÷ÞÅÿð¼‰ÿþúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ.ÿÿÿïßÏð´"õçÙ6ûÿÿFÿÿÿPÿÿÿVüüüeþþþwÿÿÿŠýýýšÿÿÿ¦ÿÿÿ©ÿÿÿ®þþþ¶ýýý¿ÿÿÿÈÿÿÿÌÿÿÿÎÿÿÿÒÿÿÿØþþþßýýýåþþþéÿÿÿëýýýïýýýõýýýüþþþÿÿÿÿÿÿÿÿÿþþþÿÿþþÿÿÿÿÿöÛÁÿðÁ‘ÿüóéÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿòÇÿóΧÿýúöÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýøôÿ︂ÿøàÉÿþýýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¹¹¹ÿQQQÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ111ÿxxxÿäääÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþûøÿõÖµÿñ•ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ¿¿¿ïïïÿÿÿ÷÷÷"ÿÿÿ'ùùù/ÿÿÿ>ûûûNüüü\üüüdÿÿÿiüüüsÿÿÿ‚ÿÿÿ’ÿÿÿ¢ýýý«ýýý¯ÿÿÿµÿÿÿ½ÿÿÿÆõÕ¶ÏñÖÖûóëÙÿÿÿÝÿÿÿäýýýìÿÿÿôÿÿÿúÿÿÿýÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿýýýþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÁ“ÿôÓ²ÿþûøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüóëÿî¶~ÿùæÔÿþþýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ«««ÿMMMÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ000ÿpppÿÕÕÕÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýøôÿóË¢ÿôͦÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýýý×òòòþþþÿÿÿ ôʦ1òÆ?ûóìEÿÿÿMþþþ[üüüjüüüyÿÿÿ…ÿÿÿ‹ÿÿÿÿÿÿ˜ýýý£ýýý­þþþ¶ÿÿÿ¹ýýý¼ÿÿÿÄÿÿÿÌÿÿÿÕÿÿÿÛÿÿÿÞþþþâÿÿÿêÿÿÿóÿÿÿýÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿþÿÿÿjÿöÙ½ÿþüúÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿûîâÿî¶}ÿúìÝÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýÿ¥¥¥ÿQQQÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ333ÿqqqÿÍÍÍÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõíÿñÀÿöÙ¼ÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿýýý¦ìììâââ ÿÿÿñññÿÿÿÿÿÿ$ÿÿÿ3ÿÿÿ@ÿÿÿKûûûPüüüWÿÿÿdüüüsýýýƒýýý‘ÿÿÿ˜ÿÿÿœÿÿÿ¥ÿÿÿ°ÿÿÿ»ÿÿÿÄýüùÊÌ÷ÞÇÓýüúÜÿÿÿæþþþîÿÿÿóýýýöÿÿÿùÿÿÿþþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿþþþÿÿÿÿþÿÿÿÿùçÕÿï·€ÿüñæÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿúúúÿ¢ŽzÿVE5ÿ!!!ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;;;ÿyyyÿÌÌÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûîâÿ﹄ÿùæÒÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿvßßßÿÿÿöööÿÿÿ+úõð3ì´}7÷ãÏ@ûûûMÿÿÿZüüüeüüümþþþpüüüxÿÿÿ„ýýýÿÿÿšÿÿÿŸÿÿÿ¢ÿÿÿ«ÿÿÿµþþþ¿ýýýÉýýýÏýýýÓÿÿÿÜÿÿÿçÿÿÿôÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿ÷ÝÄÿð»ˆÿüõîÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿôͧÿñʦÿ²²±ÿjjjÿ...ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿHHHÿˆˆˆÿÔÔÔÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿúæÔÿ﹂ÿüòèÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿûûûLÿÿÿÿÿÿïïïõõõþþþ)úúú4ÿÿÿ<ûûû@ÿÿÿJÿÿÿXüüügÿÿÿuüüüýýý„ÿÿÿŠÿÿÿ•ýýý¡ýýý¬ÿÿÿ´ÿÿÿ¸ÿÿÿ½ôÔµÇð¿ÒüöóÝÿÿÿäÿÿÿçÿÿÿìÿÿÿôýýýýÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿþþþÿÿÿÿÿñ“ÿöÙ¼ÿþþþÿÿÿÿÿÅÅÅÿÿBBBÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"""ÿ\\\ÿÿáááÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷ÞÅÿ)ÿþüûÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿùùù,ìììôôô÷÷÷ ÿÿÿ#þþþ)ðÍ¥3îÁ”>ûøôIÿÿÿPûÿÿSüüüZÿÿÿdþþþpüüü{ÿÿÿƒÿÿÿ…ÿÿÿŽÿÿÿšýýý¨ÿÿÿµýýýÀÿÿÿÆÿÿÿÌÿÿÿÙýýýæÿÿÿôþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿï·ÿùäÑÿþþþÿþþþÿÿÿÿÿÿÿÿÿÙÙÙÿšššþ___ÿ ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ;;;ÿ{{{ÿ¶¶¶ÿòòòÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿþûùÿôÔ³ÿñÖÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿæþþþééé ÿÿÿ÷÷÷$ÿÿÿ-ùùù2ÿÿÿ7ÿÿÿBûûûNÿÿÿYüüücÿÿÿhüüülüüüvÿÿÿƒÿÿÿÿÿÿ˜ýýýþþþ£ÿÿÿ­ÿÿÿºýýýÇì°uÐúìàÔýýýÚþþþåÿÿÿòþþþÿÿÿÿÿÿÿÿÿíííÿºººÿ„„„ÿFFFÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"""ÿcccÿÿÑÑÑÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿýùõÿòÈÿôΨÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ½ÿÿÿÿÿÿÿÿÿ ÿÿÿñññÿÿÿÿÿÿÿÿÿ(ÿùù1ì¨m8úòé;úúú?ÿÿÿHûûûSÿÿÿ\üüüeüüühþþþqþþþ~ÿÿÿÅÅÅ®•••È```Ý***ðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿTTTÿÿÀÀÀÿîîîÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüõîÿð½Œÿ÷Û¿ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ”ìììÿÿÿééé ÿÿÿÿÿÿ ÂÂÂ.gggOBBBs%%%£Öÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿNA4ÿŽŽŽÿ¼¼½ÿâââÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿûïâÿÿúé×ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿüüülÚÚÚ +Kºöÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ"""ÿ```ÿ˜—–ÿ¸•qÿÙ¾¥ÿýýýÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþýÿúæÔÿî¸ÿüõíÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿûûûGÿÿÿ ":bšÓÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ ÿEEEÿ~~~ÿ²²²ÿÐÐÐÿèèèÿýûùÿï·€ÿùãÏÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþýûÿ÷ÝÃÿð¼‰ÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿòùùù+';gÐýÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿDDDÿyyyÿ­­­ÿÏÏÏÿßßßÿóóóÿÿÿÿÿÿÿÿÿþþþÿýøôÿí°tÿüïäÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿþüùÿôÑ®ÿñÄ—ÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿËööö!0Q‚®Úÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿó Я777Žgggj^³³³bÝÝÝkÿÿÿxýýýŒÿÿÿœýýý¢ýýý­ÿÿÿ½ýýýÐúîãáí±xîýùõôÿÿÿ÷þþþüþþþÿÿÿÿÿþþþÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþÿÿÿÿÿÿþû÷ÿñŘÿôϬÿÿÿÿÿÿþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿýýýªÿÿÿ *Dl’µÖùÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿêȧ‚[4$ÌÌÌÿÿÿ ÿÿÿÿÿÿÿÿÿóóóÿÿÿööö÷éÛ$ë°u'ÿøø(ÿÿÿ.ÿÿÿ:ÿÿÿFÿÿÿQÿÿÿXÿÿÿ^ÿÿÿhÿÿÿyÿÿÿŒýýýžÿÿÿ¨ÿÿÿ®ÿÿÿ¼ÿÿÿÐÿÿÿæýýýûÿÿÿÿþþþÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿýöïÿð»‡ÿ÷ÞÄÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿ‹þþþ *C`y¥ºËÛêöÿÿÿÿÿÿÿÿÿÿÿüñãÓıœ†oS7# ÿÿÿÿÿÿÿÿÿÿÿÿ ÿÿÿ ðððÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ#ÿÿÿ&øøø(ÿÿÿ5ÿÿÿHüüü^þþþqÿÿÿ€ýýý†ÿÿÿŽÿÿÿ ÿÿÿ²ÿÿÿÃýýýÐúîâÖî¶~ÝùëÛéÿÿÿ÷ÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþþþÿÿÿÿÿþþþÿÿÿÿÿþþþeÿÿÿ  #&%" ÿÿÿßßßååå ççç ÿÿÿ ÿÿÿÿÿÿÿÿÿóóóóèÝë°÷ïà!ÿÿÿ(ÿÿÿ/ÿÿÿ2ÿÿÿ7ÿÿÿEÿÿÿXÿÿÿnÿÿÿƒÿÿÿ“ÿÿÿšÿÿÿ¨ÿÿÿ½ýýýÓþþþéýýýüþþþÿÿÿÿA¿¿¿ÿÿÿÿÿÿ ÿÿÿ ÿÿÿ ëëë ÿÿÿÿÿÿòòòóóóÿÿÿÌÌÌÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿçÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿà?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿà?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿø?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀ?ÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀ?ÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿü?ÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿà?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿà?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿà?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿà?ÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿ?ÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿà?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿð?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿà?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿøÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿàÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿüÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿü€ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÀÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿðÿÿÿÿÿÿ?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ€?ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿipe-7.2.13/src/ipe/appui_win.cpp0000644000175000017500000014367113561570220016313 0ustar otfriedotfried// -------------------------------------------------------------------- // AppUi for Win32 // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "appui_win.h" #include "ipecanvas_win.h" #include "controls_win.h" #include "ipeui_wstring.h" #include "ipelua.h" #include #include #include #include #define IDI_MYICON 1 #define ID_STATUS_TIMER 1 #define IDC_STATUSBAR 7000 #define IDC_BOOKMARK 7100 #define IDC_NOTES 7200 #define IDC_LAYERS 7300 #define IDBASE 8000 #define TEXT_STYLE_BASE 8300 #define ID_SELECTOR_BASE 8500 #define ID_ABSOLUTE_BASE 8600 #define ID_PATHVIEW 8700 #define ID_MOVETOLAYER_BASE 8800 #define ID_SELECTINLAYER_BASE 9000 #define ID_GRIDSIZE_BASE 9100 #define ID_ANGLESIZE_BASE 9500 using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- const int TBICONSIZE = 24; static HINSTANCE win_hInstance = nullptr; static int win_nCmdShow = 0; const wchar_t AppUi::className[] = L"ipeWindowClass"; // -------------------------------------------------------------------- static HBITMAP loadIcon(String action, int w, int h, int r0, int g0, int b0) { String dir = ipeIconDirectory(); String base = dir + action; String fname; int ww = w < 0 ? -w : w; if (ww >= 64 && Platform::fileExists(base + "_32x32@2x.png")) fname = base + "_32x32@2x.png"; else if (ww >= 48 && Platform::fileExists(base + "@2x.png")) fname = base + "@2x.png"; else if (ww >= 32 && Platform::fileExists(base + "_32x32.png")) fname = base + "_32x32.png"; else fname = base + ".png"; // ipeDebug("loadIcon %s at %d x %d from %s", action.z(), w, h, fname.z()); if (!Platform::fileExists(fname)) return nullptr; Gdiplus::Bitmap *bitmap = Gdiplus::Bitmap::FromFile(WString(fname).data(), FALSE); if (bitmap->GetLastStatus() != Gdiplus::Ok) { delete bitmap; return nullptr; } int wd = bitmap->GetWidth(); int ht = bitmap->GetHeight(); Gdiplus::BitmapData* bitmapData = new Gdiplus::BitmapData; Gdiplus::Rect rect(0, 0, wd, ht); bitmap->LockBits(&rect, Gdiplus::ImageLockModeRead, PixelFormat32bppPARGB, bitmapData); if (w < 0) w = wd; if (h < 0) h = ht; BITMAPINFO bmi; ZeroMemory(&bmi, sizeof(bmi)); bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); bmi.bmiHeader.biWidth = w; bmi.bmiHeader.biHeight = h; bmi.bmiHeader.biPlanes = 1; bmi.bmiHeader.biBitCount = (r0 >= 0) ? 24 : 32; bmi.bmiHeader.biCompression = BI_RGB; void *pbits = nullptr; HBITMAP bm = CreateDIBSection(nullptr, &bmi, DIB_RGB_COLORS, &pbits, nullptr, 0); unsigned char *p = (unsigned char *) bitmapData->Scan0; unsigned char *q = (unsigned char *) pbits; int stride = bitmapData->Stride; if (r0 < 0) { // make it transparent for (unsigned char *r = q; r < q + 4 * w * h;) *r++ = 0x00; int x0 = wd < w ? (w - wd)/2 : 0; int y0 = ht < h ? (h - ht)/2 : 0; int xs = wd > w ? w : wd; int ys = ht > h ? h : ht; for (int y = 0; y < ys; ++y) { unsigned char *src = p + (ht - 1 - y) * stride; unsigned char *dst = q + (y0 + y) * (4 * w) + 4 * x0; int n = 4 * xs; while (n--) *dst++ = *src++; } } else { // mix with color r0, g0, b0 // assumes w = wd, h = ht int dstride = (3 * w + 3) & (~3); for (int x = 0; x < w; ++x) { for (int y = 0; y < h; ++y) { unsigned char *src = p + (h - 1 - y) * stride + 4 * x; unsigned char *dst = q + y * dstride + 3 * x; int b1 = *src++; int g1 = *src++; int r1 = *src++; int trans = *src++; *dst++ = b1 + int((0xff - trans) * b0 / 0xff); *dst++ = g1 + int((0xff - trans) * g0 / 0xff); *dst++ = r1 + int((0xff - trans) * r0 / 0xff); } } } bitmap->UnlockBits(bitmapData); delete bitmapData; delete bitmap; return bm; } static int loadIcon(String action, HIMAGELIST il, int scale) { int size = scale * TBICONSIZE / 100; HBITMAP bm = loadIcon(action, size, size, -1, -1, -1); if (bm == nullptr) return -1; int r = ImageList_Add(il, bm, nullptr); DeleteObject(bm); return r; } static HBITMAP loadButtonIcon(String action, int scale) { int size = scale * 24 / 100; DWORD rgb = GetSysColor(COLOR_BTNFACE); int r0 = GetRValue(rgb); int g0 = GetGValue(rgb); int b0 = GetBValue(rgb); return loadIcon(action, -size, -1, r0, g0, b0); } static HBITMAP colorIcon(Color color, int scale) { int r = int(color.iRed.internal() * 255 / 1000); int g = int(color.iGreen.internal() * 255 / 1000); int b = int(color.iBlue.internal() * 255 / 1000); COLORREF rgb = RGB(r, g, b); int cx = scale * 22 / 100; int cy = scale * 22 / 100; HDC hdc = GetDC(nullptr); HDC memDC = CreateCompatibleDC(hdc); HBITMAP bm = CreateCompatibleBitmap(hdc, cx, cy); SelectObject(memDC, bm); for (int y = 0; y < cy; ++y) { for (int x = 0; x < cx; ++x) { SetPixel(memDC, x, y, rgb); } } DeleteDC(memDC); ReleaseDC(nullptr, hdc); return bm; } // -------------------------------------------------------------------- void AppUi::addRootMenu(int id, const char *name) { hRootMenu[id] = CreatePopupMenu(); WString wname(name); AppendMenuW(hMenuBar, MF_STRING | MF_POPUP, (UINT_PTR) hRootMenu[id], wname.data()); } void AppUi::createAction(String name, String tooltip, bool canWhileDrawing) { SAction s; s.name = String(name); s.icon = loadIcon(name, hIcons, iToolbarScale); s.tooltip = tooltip; s.alwaysOn = canWhileDrawing; iActions.push_back(s); } void AppUi::addItem(HMENU menu, const char *title, const char *name) { if (title == nullptr) { AppendMenu(menu, MF_SEPARATOR, 0, nullptr); } else { bool canUseWhileDrawing = false; if (name[0] == '@') { canUseWhileDrawing = true; name = name + 1; } if (name[0] == '*') name += 1; // in Win32 all menu items are checkable anyway // check for shortcut lua_getglobal(L, "shortcuts"); lua_getfield(L, -1, name); String sc; if (lua_isstring(L, -1)) sc = lua_tolstring(L, -1, nullptr); lua_pop(L, 2); // shortcuts, shortcuts[name] String tooltip = title; if (!sc.empty()) tooltip = tooltip + " [" + sc + "]"; createAction(name, tooltip, canUseWhileDrawing); if (sc.empty()) { AppendMenuW(menu, MF_STRING, iActions.size() - 1 + IDBASE, WString(title).data()); } else { String t = title; t += "\t"; t += sc; AppendMenu(menu, MF_STRING, iActions.size() - 1 + IDBASE, WString(t).data()); } } } void AppUi::addItem(int id, const char *title, const char *name) { addItem(hRootMenu[id], title, name); } static HMENU submenu = nullptr; void AppUi::startSubMenu(int id, const char *name, int tag) { submenu = CreatePopupMenu(); AppendMenuW(hRootMenu[id], MF_STRING | MF_POPUP, (UINT_PTR) submenu, WString(name).data()); } void AppUi::addSubItem(const char *title, const char *name) { addItem(submenu, title, name); } MENUHANDLE AppUi::endSubMenu() { return submenu; } HWND AppUi::createToolBar(HINSTANCE hInst) { HWND tb = CreateWindowExW(0, TOOLBARCLASSNAMEW, nullptr, WS_CHILD | WS_VISIBLE | TBSTYLE_TOOLTIPS | CCS_NOPARENTALIGN | CCS_NORESIZE, 0, 0, 0, 0, hwnd, nullptr, hInst, nullptr); // needed to set version of control library to be used SendMessage(tb, TB_BUTTONSTRUCTSIZE, (WPARAM) sizeof(TBBUTTON), 0); SendMessage(tb, TB_SETIMAGELIST, 0, (LPARAM) hIcons); SendMessage(tb, TB_SETMAXTEXTROWS, 0, (LPARAM) 0); return tb; } void AppUi::addTButton(HWND tb, const char *name, int flags) { TBBUTTON tbb; ZeroMemory(&tbb, sizeof(tbb)); if (name == nullptr) { tbb.iBitmap = 1; tbb.fsStyle = BTNS_SEP | flags; SendMessageW(tb, TB_ADDBUTTONS, 1, (LPARAM) &tbb); } else { int i = findAction(name); tbb.iBitmap = iconId(name); tbb.fsState = TBSTATE_ENABLED; tbb.fsStyle = TBSTYLE_BUTTON | flags; tbb.idCommand = i + IDBASE; WString tt(iActions[i].tooltip); tbb.iString = INT_PTR(tt.data()); SendMessageW(tb, TB_ADDBUTTONS, 1, (LPARAM) &tbb); } } void AppUi::setTooltip(HWND h, String tip, bool isComboBoxEx) { if (isComboBoxEx) h = (HWND) SendMessage(h, CBEM_GETCOMBOCONTROL, 0, 0); TOOLINFO toolInfo = { 0 }; toolInfo.cbSize = sizeof(toolInfo); toolInfo.hwnd = hwnd; toolInfo.uFlags = TTF_IDISHWND | TTF_SUBCLASS; toolInfo.uId = (UINT_PTR) h; WString wtip(tip); toolInfo.lpszText = wtip.data(); SendMessage(hTip, TTM_ADDTOOL, 0, (LPARAM) &toolInfo); } HWND AppUi::createButton(HINSTANCE hInst, int id, int flags) { return CreateWindowExW(0, L"button", nullptr, WS_CHILD | WS_VISIBLE | flags, 0, 0, 0, 0, hwnd, (HMENU) (INT_PTR) id, hInst, nullptr); } void AppUi::toggleFullscreen() { if (!iFullScreen) { HMONITOR hmon = MonitorFromWindow(hwnd, MONITOR_DEFAULTTONEAREST); MONITORINFO mi = { sizeof(mi) }; if (!GetMonitorInfo(hmon, &mi)) return; iWasMaximized = IsZoomed(hwnd); if (iWasMaximized) SendMessage(hwnd, WM_SYSCOMMAND, SC_RESTORE, 0); GetWindowRect(hwnd, &iWindowRect); iWindowStyle = GetWindowLong(hwnd, GWL_STYLE); iWindowExStyle = GetWindowLong(hwnd, GWL_EXSTYLE); SetWindowLong(hwnd, GWL_STYLE, iWindowStyle & ~(WS_CAPTION | WS_THICKFRAME)); SetWindowLong(hwnd, GWL_EXSTYLE, iWindowExStyle & ~(WS_EX_DLGMODALFRAME | WS_EX_WINDOWEDGE | WS_EX_CLIENTEDGE | WS_EX_STATICEDGE)); SetWindowPos(hwnd, HWND_TOP, mi.rcMonitor.left, mi.rcMonitor.top, mi.rcMonitor.right - mi.rcMonitor.left, mi.rcMonitor.bottom - mi.rcMonitor.top, SWP_SHOWWINDOW); iFullScreen = true; } else { SetWindowLong(hwnd, GWL_STYLE, iWindowStyle); SetWindowLong(hwnd, GWL_EXSTYLE, iWindowExStyle); SetWindowPos(hwnd, nullptr, iWindowRect.left, iWindowRect.top, iWindowRect.right - iWindowRect.left, iWindowRect.bottom - iWindowRect.top, SWP_NOZORDER | SWP_NOACTIVATE | SWP_FRAMECHANGED); if (iWasMaximized) SendMessage(hwnd, WM_SYSCOMMAND, SC_MAXIMIZE, 0); iFullScreen = false; } } // -------------------------------------------------------------------- AppUi::AppUi(lua_State *L0, int model) : AppUiBase(L0, model) { // windows procedure may receive WM_SIZE message before canvas is created iCanvas = nullptr; HWND hwnd = CreateWindowExW(WS_EX_CLIENTEDGE, className, L"Ipe", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, nullptr, nullptr, win_hInstance, this); if (hwnd == nullptr) { MessageBoxW(nullptr, L"AppUi window creation failed!", L"Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } assert(GetWindowLongPtr(hwnd, GWLP_USERDATA)); iFullScreen = false; } static void insert_tb(HWND hRebar, REBARBANDINFO &rbBand, HWND tb, int size) { rbBand.hwndChild = tb; rbBand.cxMinChild = size; rbBand.cx = size; SendMessage(hRebar, RB_INSERTBAND, (WPARAM)-1, (LPARAM) &rbBand); } // called during Window creation void AppUi::initUi() { // update scale if dpi information is available int dpi = Canvas::getDpiForWindow(hwnd); if (iUiScale == 100) iUiScale = dpi; if (iToolbarScale == 100) iToolbarScale = dpi; int tbsize = iToolbarScale * TBICONSIZE / 100; hIcons = ImageList_Create(tbsize, tbsize, ILC_COLOR32, 20, 4); hColorIcons = ImageList_Create(uiscale(22), uiscale(22), ILC_COLOR32, 20, 4); HINSTANCE hInst = (HINSTANCE) GetWindowLongPtr(hwnd, GWLP_HINSTANCE); hMenuBar = CreateMenu(); buildMenus(); SetMenu(hwnd, hMenuBar); hStatusBar = CreateWindowExW(0, STATUSCLASSNAMEW, nullptr, WS_CHILD | WS_VISIBLE | SBARS_SIZEGRIP, 0, 0, 0, 0, hwnd, (HMENU) IDC_STATUSBAR, hInst, nullptr); hTip = CreateWindowEx(0, TOOLTIPS_CLASS, nullptr, WS_POPUP | TTS_NOPREFIX | TTS_ALWAYSTIP, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, hwnd, nullptr, hInst, nullptr); SetWindowPos(hTip, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE); // ------------------------------------------------------------ hSnapTools = createToolBar(hInst); addTButton(hSnapTools, "snapvtx", BTNS_CHECK); addTButton(hSnapTools, "snapctl", BTNS_CHECK); addTButton(hSnapTools, "snapbd", BTNS_CHECK); addTButton(hSnapTools, "snapint", BTNS_CHECK); addTButton(hSnapTools, "snapgrid", BTNS_CHECK); addTButton(hSnapTools, "snapangle", BTNS_CHECK); addTButton(hSnapTools, "snapauto", BTNS_CHECK); #define SNAP_BUTTONS 7 hEditTools = createToolBar(hInst); int EDIT_BUTTONS = 0; if (iLeftDockFloats) { createAction("dock_visible", "Show properties and layers", true); addTButton(hEditTools, "dock_visible", BTNS_CHECK); EDIT_BUTTONS += 1; } if (!isMiniEdit) { addTButton(hEditTools, "copy"); addTButton(hEditTools, "cut"); addTButton(hEditTools, "paste"); addTButton(hEditTools, "delete"); EDIT_BUTTONS += 4; } addTButton(hEditTools, "undo"); addTButton(hEditTools, "redo"); EDIT_BUTTONS += 2; if (!isMiniEdit) { addTButton(hEditTools, "zoom_in"); addTButton(hEditTools, "zoom_out"); addTButton(hEditTools, "fit_objects"); addTButton(hEditTools, "fit_page"); addTButton(hEditTools, "fit_width"); addTButton(hEditTools, "keyboard"); EDIT_BUTTONS += 6; } createAction("shift_key", "Press the Shift key", true); addTButton(hEditTools, "shift_key", BTNS_CHECK); addTButton(hEditTools, "grid_visible", BTNS_CHECK); createAction("stop", "Abort object being drawn [Esc]", true); addTButton(hEditTools, "stop"); EDIT_BUTTONS += 3; hObjectTools = createToolBar(hInst); addTButton(hObjectTools, "mode_select", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_translate", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_rotate", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_stretch", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_shear", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_graph", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_pan", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_shredder", BTNS_CHECKGROUP); addTButton(hObjectTools, nullptr, BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_label", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_math", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_paragraph", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_marks", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_rectangles1", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_rectangles2", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_rectangles3", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_parallelogram", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_lines", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_polygons", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_splines", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_splinegons", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_arc1", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_arc2", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_arc3", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_circle1", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_circle2", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_circle3", BTNS_CHECKGROUP); addTButton(hObjectTools, "mode_ink", BTNS_CHECKGROUP); #define MODE_BUTTONS 24 // size is used for dropdown list! Don't set to zero. for (int i = EUiGridSize; i <= EUiAngleSize; ++i) hSelector[i] = CreateWindowExW(0, WC_COMBOBOXEXW, nullptr, WS_CHILD | WS_VISIBLE | CBS_DROPDOWNLIST, 0, 0, uiscale(100), uiscale(300), hwnd, (HMENU) (INT_PTR) (ID_SELECTOR_BASE + i), hInst, nullptr); hRebar = CreateWindowEx(WS_EX_TOOLWINDOW, REBARCLASSNAME, nullptr, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | RBS_VARHEIGHT | RBS_AUTOSIZE | CCS_NODIVIDER | RBS_BANDBORDERS, 0, 0, 0, 0, hwnd, nullptr, hInst, nullptr); // Initialize band info for all bands REBARBANDINFO rbBand = { sizeof(REBARBANDINFO) }; rbBand.fMask = RBBIM_STYLE // fStyle is valid. | RBBIM_CHILD // hwndChild is valid. | RBBIM_CHILDSIZE // child size members are valid. | RBBIM_SIZE; // cx is valid. // Get the height of the toolbars. DWORD dwBtnSize = (DWORD) SendMessage(hEditTools, TB_GETBUTTONSIZE, 0, 0); rbBand.fStyle = RBBS_CHILDEDGE | RBBS_GRIPPERALWAYS | RBBS_HIDETITLE; rbBand.cyMinChild = HIWORD(dwBtnSize) + 4; rbBand.cyChild = HIWORD(dwBtnSize) + 4; int bw = LOWORD(dwBtnSize); lua_getglobal(L, "prefs"); lua_getfield(L, -1, "toolbar_order"); if (lua_istable(L, -1)) { int n = lua_rawlen(L, -1); for (int i = 1; i <= n; ++i) { lua_rawgeti(L, -1, i); if (lua_isstring(L, -1)) { String s = lua_tolstring(L, -1, nullptr); if (s == "edit") insert_tb(hRebar, rbBand, hEditTools, EDIT_BUTTONS * bw); else if (s == "grid") insert_tb(hRebar, rbBand, hSelector[EUiGridSize], 160); else if (s == "angle") insert_tb(hRebar, rbBand, hSelector[EUiAngleSize], 100); else if (s == "snap") insert_tb(hRebar, rbBand, hSnapTools, SNAP_BUTTONS * bw); else if (s == "mode") insert_tb(hRebar, rbBand, hObjectTools, MODE_BUTTONS * bw); } lua_pop(L, 1); } } lua_pop(L, 2); // toolbar_order, prefs // ------------------------------------------------------------ hProperties = CreateWindowExW(0, L"button", L"Properties", WS_CHILD | WS_VISIBLE | BS_GROUPBOX, 0, 100, 200, 280, hwnd, nullptr, hInst, nullptr); for (int i = 0; i <= EUiSymbolSize; ++i) { if (i != EUiMarkShape) hButton[i] = createButton(hInst, ID_ABSOLUTE_BASE + i); } // size is used for dropdown list! Don't set to zero. for (int i = 0; i < EUiGridSize; ++i) hSelector[i] = CreateWindowExW(0, WC_COMBOBOXEXW, nullptr, WS_CHILD | WS_VISIBLE | CBS_DROPDOWNLIST, 0, 0, uiscale(100), uiscale(300), hwnd, (HMENU) (INT_PTR) (ID_SELECTOR_BASE + i), hInst, nullptr); SendMessage(hButton[EUiPen], BM_SETIMAGE, IMAGE_BITMAP, (LPARAM) loadButtonIcon("pen", iUiScale)); SendMessage(hButton[EUiTextSize], BM_SETIMAGE, IMAGE_BITMAP, (LPARAM) loadButtonIcon("mode_label", iUiScale)); SendMessage(hButton[EUiSymbolSize], BM_SETIMAGE, IMAGE_BITMAP, (LPARAM) loadButtonIcon("mode_marks", iUiScale)); SendMessage(hButton[EUiStroke], BM_SETIMAGE, IMAGE_BITMAP, (LPARAM) colorIcon(Color(1000, 0, 0), iUiScale)); SendMessage(hButton[EUiFill], BM_SETIMAGE, IMAGE_BITMAP, (LPARAM) colorIcon(Color(1000, 1000, 0), iUiScale)); hButton[EUiMarkShape] = CreateWindowExW(0, L"static", nullptr, WS_CHILD | WS_VISIBLE | SS_BITMAP | SS_CENTERIMAGE, 0, 0, 0, 0, hwnd, nullptr, hInst, nullptr); SendMessage(hButton[EUiMarkShape], STM_SETIMAGE, IMAGE_BITMAP, (LPARAM) loadButtonIcon("mode_marks", iUiScale)); iPathView = new PathView(hwnd, ID_PATHVIEW); hViewNumber = createButton(hInst, ID_ABSOLUTE_BASE + EUiView, BS_TEXT|BS_PUSHBUTTON); hPageNumber = createButton(hInst, ID_ABSOLUTE_BASE + EUiPage, BS_TEXT|BS_PUSHBUTTON); hViewMarked = createButton(hInst, ID_ABSOLUTE_BASE + EUiViewMarked, BS_AUTOCHECKBOX); hPageMarked = createButton(hInst, ID_ABSOLUTE_BASE + EUiPageMarked, BS_AUTOCHECKBOX); hLayerGroup = CreateWindowExW(0, L"button", L"Layers", WS_CHILD | WS_VISIBLE | BS_GROUPBOX, 0, 0, 0, 0, hwnd, nullptr, hInst, nullptr); hLayers = CreateWindowExW(0, WC_LISTVIEWW, nullptr, WS_CHILD | WS_VISIBLE | LVS_LIST | LVS_SINGLESEL, 0, 0, 0, 0, hwnd, (HMENU) IDC_LAYERS, hInst, nullptr); (void) ListView_SetExtendedListViewStyle(hLayers, LVS_EX_CHECKBOXES); hNotesGroup = CreateWindowExW(0, L"button", L"Notes", WS_CHILD | WS_VISIBLE | BS_GROUPBOX, 0, 0, 0, 0, hwnd, nullptr, hInst, nullptr); hNotes = CreateWindowExW(0, L"edit", nullptr, WS_CHILD | WS_VISIBLE | WS_BORDER | WS_VSCROLL | ES_READONLY | ES_LEFT | ES_MULTILINE | ES_AUTOVSCROLL, 0, 0, 0, 0, hwnd, (HMENU) IDC_NOTES, hInst, nullptr); hBookmarksGroup = CreateWindowExW(0, L"button", L"Bookmarks", WS_CHILD | WS_VISIBLE | BS_GROUPBOX, 0, 0, 0, 0, hwnd, nullptr, hInst, nullptr); hBookmarks = CreateWindowExW(0, L"listbox", nullptr, WS_CHILD | WS_VISIBLE | WS_VSCROLL | WS_BORDER | LBS_HASSTRINGS | LBS_NOTIFY | LBS_NOSEL, 0, 0, 0, 0, hwnd, (HMENU) IDC_BOOKMARK, hInst, nullptr); Canvas *canvas = new Canvas(hwnd); hwndCanvas = canvas->windowId(); iCanvas = canvas; iCanvas->setObserver(this); // Tooltips setTooltip(hButton[EUiStroke], "Absolute stroke color"); setTooltip(hButton[EUiFill], "Absolute fill color"); setTooltip(hButton[EUiPen], "Absolute pen width"); setTooltip(hButton[EUiTextSize], "Absolute text size"); setTooltip(hButton[EUiSymbolSize], "Absolute symbol size"); setTooltip(hSelector[EUiStroke], "Symbolic stroke color", true); setTooltip(hSelector[EUiFill], "Symbolic fill color", true); setTooltip(hSelector[EUiPen], "Symbolic pen width", true); setTooltip(hSelector[EUiTextSize], "Symbolic text size", true); setTooltip(hSelector[EUiMarkShape], "Mark shape", true); setTooltip(hSelector[EUiSymbolSize], "Symbolic symbol size", true); setTooltip(hSelector[EUiGridSize], "Grid size", true); setTooltip(hSelector[EUiAngleSize], "Angle for angular snap", true); setTooltip(hViewNumber, "Current view number"); setTooltip(hPageNumber, "Current page number"); setTooltip(hNotes, "Notes for this page"); setTooltip(hBookmarks, "Bookmarks of this document"); setTooltip(hLayers, "Layers of this page"); setCheckMark("coordinates|", "points"); setCheckMark("scaling|", "1"); setCheckMark("mode_", "select"); SetFocus(hwndCanvas); hFont = CreateFontW(uiscale(18), 0, 0, 0, FW_DONTCARE, FALSE, FALSE, FALSE, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, L"MS Shell Dlg"); if (hFont != nullptr) { SendMessage(hNotes, WM_SETFONT, WPARAM (hFont), TRUE); SendMessage(hNotesGroup, WM_SETFONT, WPARAM (hFont), TRUE); SendMessage(hBookmarksGroup, WM_SETFONT, WPARAM (hFont), TRUE); SendMessage(hBookmarks, WM_SETFONT, WPARAM (hFont), TRUE); SendMessage(hProperties, WM_SETFONT, WPARAM (hFont), TRUE); SendMessage(hLayerGroup, WM_SETFONT, WPARAM (hFont), TRUE); SendMessage(hViewNumber, WM_SETFONT, WPARAM (hFont), TRUE); SendMessage(hPageNumber, WM_SETFONT, WPARAM (hFont), TRUE); } // default is on, Lua code will turn off if necessary CheckMenuItem(hMenuBar, actionId("toggle_notes"), MF_CHECKED); CheckMenuItem(hMenuBar, actionId("toggle_bookmarks"), MF_CHECKED); if (iLeftDockFloats) // SendMessage(hEditTools, TB_SETSTATE, actionId("dock_visible"), // (LPARAM) (TBSTATE_ENABLED | TBSTATE_CHECKED)); setLeftDockVisibility(false); } AppUi::~AppUi() { // canvas is deleted by Windows ImageList_Destroy(hIcons); ImageList_Destroy(hColorIcons); KillTimer(hwnd, ID_STATUS_TIMER); DeleteObject(hFont); } void AppUi::layoutChildren(bool resizeRebar) { RECT rc, rc1, rc2; GetClientRect(hwnd, &rc); SendMessage(hStatusBar, WM_SIZE, 0, 0); if (resizeRebar) MoveWindow(hRebar, 0, 0, rc.right - rc.left, 10, FALSE); GetClientRect(hStatusBar, &rc1); GetClientRect(hRebar, &rc2); int sbh = rc1.bottom - rc1.top; int tbh = rc2.bottom - rc2.top; int cvh = rc.bottom - sbh - tbh; RECT rect; bool visLeftDock = IsWindowVisible(hProperties); if (visLeftDock) { rect.left = 0; rect.top = tbh; rect.right = uiscale(200); rect.bottom = rc.bottom - sbh; InvalidateRect(hwnd, &rect, TRUE); int dy = 28 + iUiGap; int pbh = uiscale(dy * 6 + 28 + 70); MoveWindow(hProperties, uiscale(8), tbh + uiscale(2), uiscale(180), pbh, TRUE); for (int i = 0; i <= EUiSymbolSize; ++i) { int y = uiscale(24 + dy * i + (i > 2 ? 42 : 0)); MoveWindow(hButton[i], uiscale(16), tbh + y, uiscale(26), uiscale(26), TRUE); MoveWindow(hSelector[i], uiscale(50), tbh + y, uiscale(132), uiscale(26), TRUE); } int y = tbh + uiscale(24 + dy * 6 + 42); MoveWindow(hViewNumber, uiscale(16), y, uiscale(68), uiscale(26), TRUE); MoveWindow(hPageNumber, uiscale(116), y, uiscale(68), uiscale(26), TRUE); MoveWindow(hViewMarked, uiscale(85), y + uiscale(6), uiscale(13), uiscale(13), TRUE); MoveWindow(hPageMarked, uiscale(100), y + uiscale(6), uiscale(13), uiscale(13), TRUE); MoveWindow(iPathView->windowId(), uiscale(16), tbh + uiscale(24 + dy * 2 + 28 + iUiGap / 2), uiscale(168), uiscale(40), TRUE); MoveWindow(hLayerGroup, uiscale(8), tbh + uiscale(6) + pbh, uiscale(180), cvh - pbh - uiscale(8), TRUE); MoveWindow(hLayers, uiscale(16), tbh + uiscale(24) + pbh, uiscale(164), cvh - pbh - uiscale(32), TRUE); } bool visNotes = IsWindowVisible(hNotes); bool visBookmarks = IsWindowVisible(hBookmarks); int cvl = visLeftDock ? uiscale(200) : 0; int cvw = rc.right - cvl - ((visNotes || visBookmarks) ? uiscale(iWidthNotesBookmarks) : 0); MoveWindow(hwndCanvas, cvl, tbh, cvw, cvh, TRUE); if (visNotes || visBookmarks) { rect.left = rc.right - uiscale(iWidthNotesBookmarks); rect.top = tbh; rect.right = rc.right; rect.bottom = rc.bottom - sbh; InvalidateRect(hwnd, &rect, TRUE); } int nth = (visNotes && visBookmarks) ? cvh / 2 - uiscale(4): cvh; int nty = tbh; if (visNotes) { MoveWindow(hNotesGroup, rc.right - uiscale(iWidthNotesBookmarks), nty, uiscale(iWidthNotesBookmarks), nth, TRUE); MoveWindow(hNotes, rc.right - uiscale(iWidthNotesBookmarks - 6), nty + uiscale(18), uiscale(iWidthNotesBookmarks - 14), nth - uiscale(24), TRUE); nty += nth + uiscale(2); } if (visBookmarks) { MoveWindow(hBookmarksGroup, rc.right - uiscale(iWidthNotesBookmarks), nty, uiscale(iWidthNotesBookmarks), nth, TRUE); MoveWindow(hBookmarks, rc.right - uiscale(iWidthNotesBookmarks - 6), nty + uiscale(18), uiscale(iWidthNotesBookmarks - 14), nth - uiscale(24), TRUE); } int statwidths[] = {rc.right - uiscale(320), rc.right - uiscale(220), rc.right - uiscale(80), rc.right }; SendMessage(hStatusBar, SB_SETPARTS, 4, (LPARAM) statwidths); iCanvas->update(); BringWindowToTop(hProperties); } // -------------------------------------------------------------------- // add item to ComboBoxEx static void addComboEx(HWND h, String s) { WString ws(s); COMBOBOXEXITEM item; item.mask = CBEIF_TEXT; item.iItem = (INT_PTR) -1; item.pszText = ws.data(); SendMessage(h, CBEM_INSERTITEM, 0, (LPARAM) &item); } void AppUi::resetCombos() { for (int i = 0; i < EUiView; ++i) SendMessage(hSelector[i], CB_RESETCONTENT, 0, 0); } void AppUi::addComboColors(AttributeSeq &sym, AttributeSeq &abs) { // clear all icons ImageList_Remove(hColorIcons, -1); COMBOBOXEXITEM item; item.mask = CBEIF_TEXT | CBEIF_IMAGE; item.iItem = (INT_PTR) -1; for (int i = 0; i < size(sym); ++i) { Color color = abs[i].color(); HBITMAP bm = colorIcon(color, iUiScale); ImageList_Add(hColorIcons, bm, nullptr); DeleteObject(bm); String s = sym[i].string(); WString ws(s); item.iImage = i; item.iSelectedImage = i; item.pszText = ws.data(); SendMessage(hSelector[EUiStroke], CBEM_INSERTITEM, 0, (LPARAM) &item); SendMessage(hSelector[EUiFill], CBEM_INSERTITEM, 0, (LPARAM) &item); iComboContents[EUiStroke].push_back(s); iComboContents[EUiFill].push_back(s); } SendMessage(hSelector[EUiStroke], CBEM_SETIMAGELIST, 0, (LPARAM) hColorIcons); SendMessage(hSelector[EUiFill], CBEM_SETIMAGELIST, 0, (LPARAM) hColorIcons); } void AppUi::addCombo(int sel, String s) { addComboEx(hSelector[sel], s); } void AppUi::setComboCurrent(int sel, int idx) { SendMessage(hSelector[sel], CB_SETCURSEL, idx, 0); } void AppUi::setButtonColor(int sel, Color color) { // ipeDebug("Changing color for %d"); SendMessage(hButton[sel], BM_SETIMAGE, IMAGE_BITMAP, (LPARAM) colorIcon(color, iUiScale)); } void AppUi::setPathView(const AllAttributes &all, Cascade *sheet) { iPathView->set(all, sheet); } void AppUi::setCheckMark(String name, Attribute a) { setCheckMark(name + "|", a.string()); } void AppUi::setCheckMark(String name, String value) { String sa = name; int na = sa.size(); String sb = sa + value; int first = -1; int last = -1; int check = -1; for (int i = 0; i < int(iActions.size()); ++i) { if (iActions[i].name.left(na) == sa) { if (first < 0) first = IDBASE + i; last = IDBASE + i; if (iActions[i].name == sb) check = IDBASE + i; } } // ipeDebug("CheckMenuRadioItem %s %d %d %d", name.z(), first, last, check); if (check > 0) CheckMenuRadioItem(hMenuBar, first, last, check, MF_BYCOMMAND); if (name == "mode_") { for (int i = 0; i < int(iActions.size()); ++i) { if (iActions[i].name.left(na) == sa) { int id = IDBASE + i; int state = TBSTATE_ENABLED; if (id == check) state |= TBSTATE_CHECKED; SendMessage(hEditTools, TB_SETSTATE, id, (LPARAM) state); SendMessage(hSnapTools, TB_SETSTATE, id, (LPARAM) state); SendMessage(hObjectTools, TB_SETSTATE, id, (LPARAM) state); } } } } void AppUi::setLayers(const Page *page, int view) { iLayerNames.clear(); for (int i = 0; i < page->countLayers(); ++i) iLayerNames.push_back(page->layer(i)); std::vector objCounts; page->objectsPerLayer(objCounts); iSettingLayers = true; // TODO send WM_SETREDRAW (void) ListView_DeleteAllItems(hLayers); LVITEM lvI; lvI.mask = LVIF_TEXT | LVIF_PARAM; lvI.iSubItem = 0; for (int i = 0; i < page->countLayers(); ++i) { lvI.iItem = i; lvI.lParam = 0; if (page->layer(i) == page->active(view)) lvI.lParam |= 1; if (page->isLocked(i)) lvI.lParam |= 2; if (!page->hasSnapping(i)) lvI.lParam |= 4; WString text(page->layer(i)); char buf[16]; sprintf(buf, " (%d)", objCounts[i]); text += WString(buf); lvI.pszText = text.data(); (void) ListView_InsertItem(hLayers, &lvI); ListView_SetCheckState(hLayers, i, page->visible(view, i)); } iSettingLayers = false; } static void enableAction(HWND h, int id, int tstate) { int ostate = SendMessage(h, TB_GETSTATE, id, 0); if (ostate != -1) SendMessage(h, TB_SETSTATE, id, (LPARAM) ((ostate & BST_CHECKED)|tstate)); } void AppUi::setActionsEnabled(bool mode) { int mstate = mode ? MF_ENABLED : MF_GRAYED; int tstate = mode ? TBSTATE_ENABLED : 0; for (int i = 0; i < int(iActions.size()); ++i) { int id = i + IDBASE; if (!iActions[i].alwaysOn) { EnableMenuItem(hMenuBar, id, mstate); enableAction(hEditTools, id, tstate); enableAction(hSnapTools, id, tstate); enableAction(hObjectTools, id, tstate); } } EnableWindow(hBookmarks, mode); } void AppUi::setNumbers(String vno, bool vm, String pno, bool pm) { setWindowText(hViewNumber, vno.z()); setWindowText(hPageNumber, pno.z()); Button_SetCheck(hViewMarked, vm ? BST_CHECKED : BST_UNCHECKED); Button_SetCheck(hPageMarked, pm ? BST_CHECKED : BST_UNCHECKED); EnableWindow(hViewNumber, !vno.empty()); EnableWindow(hViewMarked, !vno.empty()); EnableWindow(hPageNumber, !pno.empty()); EnableWindow(hPageMarked, !pno.empty()); } void AppUi::setNotes(String notes) { setWindowText(hNotes, notes.z()); } void AppUi::closeRequested() { // calls model lua_rawgeti(L, LUA_REGISTRYINDEX, iModel); lua_getfield(L, -1, "closeEvent"); lua_pushvalue(L, -2); // model lua_remove(L, -3); luacall(L, 1, 1); bool result = lua_toboolean(L, -1); if (result) DestroyWindow(hwnd); } void AppUi::closeWindow() { SendMessage(hwnd, WM_CLOSE, 0, 0); } // Determine if an action is checked. // Used for viewmarked, pagemarked, snapXXX, grid_visible, show_axes, // pretty_display, toggle_notes, toggle_bookmarks, auto_latex. bool AppUi::actionState(const char *name) { if (!strcmp(name, "viewmarked")) return (Button_GetCheck(hViewMarked) == BST_CHECKED); if (!strcmp(name, "pagemarked")) return (Button_GetCheck(hPageMarked) == BST_CHECKED); int idx = actionId(name); // ipeDebug("actionState %s (%d)", name, idx); return GetMenuState(hMenuBar, idx, MF_CHECKED); } // Check/uncheck an action. // Used by Lua for snapangle and grid_visible // Also to initialize mode_select // Used from AppUi::action to toggle checkable actions. void AppUi::setActionState(const char *name, bool value) { // ipeDebug("setActionState %s %d", name, value); int idx = actionId(name); CheckMenuItem(hMenuBar, idx, value ? MF_CHECKED : MF_UNCHECKED); int state = TBSTATE_ENABLED; if (value) state |= TBSTATE_CHECKED; SendMessage(hEditTools, TB_SETSTATE, idx, (LPARAM) state); SendMessage(hSnapTools, TB_SETSTATE, idx, (LPARAM) state); SendMessage(hObjectTools, TB_SETSTATE, idx, (LPARAM) state); } void AppUi::setBookmarks(int no, const String *s) { SendMessage(hBookmarks, LB_RESETCONTENT, 0, 0); for (int i = 0; i < no; ++i) sendMessage(hBookmarks, LB_ADDSTRING, s[i].z()); } void AppUi::setToolVisible(int m, bool vis) { if (m == 1) { ShowWindow(hBookmarksGroup, vis ? SW_SHOW : SW_HIDE); ShowWindow(hBookmarks, vis ? SW_SHOW : SW_HIDE); CheckMenuItem(hMenuBar, actionId("toggle_bookmarks"), vis ? MF_CHECKED : MF_UNCHECKED); } else if (m == 2) { ShowWindow(hNotesGroup, vis ? SW_SHOW : SW_HIDE); ShowWindow(hNotes, vis ? SW_SHOW : SW_HIDE); CheckMenuItem(hMenuBar, actionId("toggle_notes"), vis ? MF_CHECKED : MF_UNCHECKED); } layoutChildren(false); } static void clearMenu(HMENU h) { for (int i = GetMenuItemCount(h) - 1; i >= 0; --i) DeleteMenu(h, i, MF_BYPOSITION); } void AppUi::populateTextStyleMenu() { AttributeSeq seq; iCascade->allNames(ETextStyle, seq); clearMenu(iTextStyleMenu); int check = 0; for (int i = 0; i < size(seq); ++i) { String s = seq[i].string(); AppendMenuW(iTextStyleMenu, MF_STRING, TEXT_STYLE_BASE + i, WString(s).data()); if (s == iAll.iTextStyle.string()) check = i; } CheckMenuRadioItem(iTextStyleMenu, TEXT_STYLE_BASE, TEXT_STYLE_BASE + seq.size() - 1, TEXT_STYLE_BASE + check, MF_BYCOMMAND); } void AppUi::populateSizeMenu(HMENU h, int sel, int base) { clearMenu(h); auto i = 0; for (auto &name : iComboContents[sel]) { AppendMenuW(h, MF_STRING, base + i, WString(name).data()); ++i; } auto cur = SendMessage(hSelector[sel], CB_GETCURSEL, 0, 0); if (cur != CB_ERR) CheckMenuRadioItem(h, base, base + iComboContents[sel].size() - 1, base + cur, MF_BYCOMMAND); } void AppUi::populateSizeMenus() { populateSizeMenu(iGridSizeMenu, EUiGridSize, ID_GRIDSIZE_BASE); populateSizeMenu(iAngleSizeMenu, EUiAngleSize, ID_ANGLESIZE_BASE); } void AppUi::populateLayerMenus() { clearMenu(iSelectLayerMenu); clearMenu(iMoveToLayerMenu); for (int i = 0; i < int(iLayerNames.size()); ++i) { WString ws(iLayerNames[i]); AppendMenuW(iSelectLayerMenu, MF_STRING, ID_SELECTINLAYER_BASE + i, ws.data()); AppendMenuW(iMoveToLayerMenu, MF_STRING, ID_MOVETOLAYER_BASE + i, ws.data()); } } int AppUi::findAction(const char *name) const { for (int i = 0; i < int(iActions.size()); ++i) { if (iActions[i].name == name) return i; } return -1; } int AppUi::actionId(const char *name) const { return findAction(name) + IDBASE; } int AppUi::iconId(const char *name) const { int i = findAction(name); if (i >= 0 && iActions[i].icon >= 0) return iActions[i].icon; else return I_IMAGENONE; } int AppUi::actionInfo(lua_State *L) const { const char *action = luaL_checklstring(L, 2, nullptr); int i = findAction(action); lua_pushinteger(L, (i >= 0) ? i + IDBASE : 0); lua_pushboolean(L, (i >= 0) ? iActions[i].alwaysOn : 0); return 2; } void AppUi::cmd(int id, int notification) { // ipeDebug("WM_COMMAND %d %d", id, notification); if (id == IDC_BOOKMARK && notification == LBN_SELCHANGE) luaBookmarkSelected(ListBox_GetCurSel(hBookmarks)); else if (ID_ABSOLUTE_BASE <= id && id <= ID_ABSOLUTE_BASE + EUiPageMarked) luaAbsoluteButton(selectorNames[id - ID_ABSOLUTE_BASE]); else if (ID_SELECTOR_BASE <= id && id <= ID_SELECTOR_BASE + EUiAngleSize) { int sel = id - ID_SELECTOR_BASE; int idx = SendMessage(hSelector[sel], CB_GETCURSEL, 0, 0); luaSelector(String(selectorNames[sel]), iComboContents[sel][idx]); } else if (ID_SELECTINLAYER_BASE <= id && id < ID_SELECTINLAYER_BASE + int(iLayerNames.size())) { action(String("selectinlayer-") + iLayerNames[id - ID_SELECTINLAYER_BASE]); } else if (ID_MOVETOLAYER_BASE <= id && id < ID_MOVETOLAYER_BASE + int(iLayerNames.size())) { action(String("movetolayer-") + iLayerNames[id - ID_MOVETOLAYER_BASE]); } else if (ID_GRIDSIZE_BASE <= id && id < ID_GRIDSIZE_BASE + int(iComboContents[EUiGridSize].size())) { luaSelector("gridsize", iComboContents[EUiGridSize][id - ID_GRIDSIZE_BASE]); } else if (ID_ANGLESIZE_BASE <= id && id < ID_ANGLESIZE_BASE + int(iComboContents[EUiAngleSize].size())) { luaSelector("anglesize", iComboContents[EUiAngleSize][id - ID_ANGLESIZE_BASE]); } else if (id == ID_PATHVIEW) { luaShowPathStylePopup(Vector(iPathView->popupPos().x, iPathView->popupPos().y)); } else if (id == ID_PATHVIEW+1) { action(iPathView->action()); } else if (IDBASE <= id && id < IDBASE + int(iActions.size())) action(iActions[id - IDBASE].name); else ipeDebug("Unknown cmd %d", id); } static const char * const aboutText = "Ipe %d.%d.%d\n\n" "Copyright (c) 1993-%d Otfried Cheong\n\n" "The extensible drawing editor Ipe creates figures " "in Postscript and PDF format, " "using LaTeX to format the text in the figures.\n" "Ipe is released under the GNU Public License.\n" "See http://ipe.otfried.org for details.\n\n" "You can \"like\" Ipe and follow Ipe announcements on Facebook " "(http://www.facebook.com/drawing.editor.Ipe7).\n\n" "If you are an Ipe fan and want to show others, have a look at the " "Ipe T-shirts (www.shirtee.com/en/store/ipe).\n\n" "Platinum sponsors\n\n" " * Hee-Kap Ahn\n" " * Martin Ziegler\n\n" "If you enjoy Ipe, you can become a member of the exclusive community of " "Ipe patrons (http://patreon.com/otfried). " "For the price of a cup of coffee per month you can make a meaningful contribution " "to the continuing development of Ipe."; void AppUi::aboutIpe() { std::vector buf(strlen(aboutText) + 100); sprintf(&buf[0], aboutText, IPELIB_VERSION / 10000, (IPELIB_VERSION / 100) % 100, IPELIB_VERSION % 100, COPYRIGHT_YEAR); MessageBoxA(hwnd, &buf[0], "About Ipe", MB_OK | MB_ICONINFORMATION | MB_APPLMODAL); } void AppUi::setLeftDockVisibility(bool vis) { int cmd = vis ?SW_SHOW : SW_HIDE; ShowWindow(hProperties, cmd); ShowWindow(hLayerGroup, cmd); ShowWindow(hLayers, cmd); for (int i = 0; i < EUiGridSize; ++i) ShowWindow(hButton[i], cmd); for (int i = 0; i < EUiView; ++i) if (i != EUiGridSize && i != EUiAngleSize) ShowWindow(hSelector[i], cmd); ShowWindow(hViewNumber, cmd); ShowWindow(hPageNumber, cmd); ShowWindow(hViewMarked, cmd); ShowWindow(hPageMarked, cmd); ShowWindow(iPathView->windowId(), cmd); layoutChildren(false); auto pan = iCanvas->pan(); double delta = (vis ? +1 : -1) * uiscale(100) / iCanvas->zoom(); iCanvas->setPan(pan + Vector(delta, 0.0)); } void AppUi::action(String name) { ipeDebug("action %s", name.z()); int id = actionId(name.z()); if (name == "fullscreen") { toggleFullscreen(); } else if (name == "about") aboutIpe(); else if (name == "shift_key") { if (iCanvas) { int mod = 0; if (SendMessage(hEditTools, TB_GETSTATE, (WPARAM) id, 0) & TBSTATE_CHECKED) mod |= CanvasBase::EShift; iCanvas->setAdditionalModifiers(mod); } } else if (name == "dock_visible") { bool vis = (SendMessage(hEditTools, TB_GETSTATE, (WPARAM) id, 0) & TBSTATE_CHECKED); setLeftDockVisibility(vis); } else { // Implement radio buttons int i = name.find("|"); if (i >= 0) setCheckMark(name.left(i+1), name.substr(i+1)); if (name.hasPrefix("mode_")) setCheckMark("mode_", name.substr(5)); if (name.hasPrefix("snap") || name == "grid_visible" || name == "auto_latex" || name == "pretty_display" || name == "show_axes" || name.hasPrefix("toggle_")) setActionState(name.z(), !GetMenuState(hMenuBar, id, MF_CHECKED)); luaAction(name); } } WINID AppUi::windowId() { return hwnd; } void AppUi::setWindowCaption(bool mod, const char *s) { setWindowText(hwnd, s); } void AppUi::showWindow(int width, int height) { SetWindowPos(hwnd, nullptr, 0, 0, width, height, SWP_NOMOVE); ShowWindow(hwnd, win_nCmdShow); UpdateWindow(hwnd); } // show for t milliseconds, or permanently if t == 0 void AppUi::explain(const char *s, int t) { if (t) SetTimer(hwnd, ID_STATUS_TIMER, t, nullptr); else KillTimer(hwnd, ID_STATUS_TIMER); sendMessage(hStatusBar, SB_SETTEXT, s); } void AppUi::setSnapIndicator(const char *s) { sendMessage(hStatusBar, SB_SETTEXT, s, 1); } void AppUi::setMouseIndicator(const char *s) { sendMessage(hStatusBar, SB_SETTEXT, s, 2); } void AppUi::setZoom(double zoom) { char s[32]; sprintf(s, "%dppi", int(72.0 * zoom)); iCanvas->setZoom(zoom); sendMessage(hStatusBar, SB_SETTEXT, s, 3); } // -------------------------------------------------------------------- static void listFormats() { UINT format = 0; char name[256]; while ((format = EnumClipboardFormats(format)) != 0) { GetClipboardFormatNameA(format, name, 256); ipeDebug("Clipboard format %d %s", format, name); } } static int clipboardBitmap(lua_State *L) { HBITMAP bm = (HBITMAP) GetClipboardData(CF_BITMAP); BITMAPINFO bmi; BITMAPINFOHEADER *s = (BITMAPINFOHEADER *) &bmi; s->biSize = sizeof(BITMAPINFOHEADER); s->biBitCount = 0; s->biClrUsed = 0; HDC hdc = GetDC(nullptr); // CreateCompatibleDC(nullptr); if (GetDIBits(hdc, bm, 0, 0, nullptr, &bmi, DIB_RGB_COLORS) == 0) { ipeDebug("AppUi::clipboard() GetDIBits failed"); ReleaseDC(nullptr, hdc); CloseClipboard(); return 0; } int w = s->biWidth; int h = s->biHeight; Vector res(s->biXPelsPerMeter, s->biYPelsPerMeter); ipeDebug("AppUi::clipboard() bitmap: %d x %d resolution %g x %g %d %d", w, h, res.x, res.y, s->biCompression, s->biBitCount); s->biPlanes = 1; s->biCompression = BI_RGB; s->biSizeImage = 0; DWORD *bits = (DWORD *) VirtualAlloc(nullptr, 4 * w, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); Buffer pixels(w * h * 4); uint32_t *p = (uint32_t *) pixels.data(); for (int y = h-1; y >= 0; --y) { if (GetDIBits(hdc, bm, y, 1, bits, &bmi, DIB_RGB_COLORS) == 0) { ipeDebug("AppUi::clipboard() GetDIBits failed to retrieve bits"); VirtualFree(bits, 0, MEM_RELEASE); ReleaseDC(nullptr, hdc); CloseClipboard(); return 0; } DWORD *r = bits; for (int x = 0; x < w; ++x) *p++ = *r++; } Bitmap ibm(w, h, Bitmap::ENative, pixels); Rect r(Vector::ZERO, Vector(w, h)); Image *img = new Image(r, ibm); push_object(L, img); VirtualFree(bits, 0, MEM_RELEASE); ReleaseDC(nullptr, hdc); CloseClipboard(); return 1; } int AppUi::clipboard(lua_State *L) { bool allow_bitmap = lua_toboolean(L, 2); OpenClipboard(hwnd); listFormats(); UINT format = 0; while ((format = EnumClipboardFormats(format)) != 0) { if (format == CF_BITMAP || format == CF_UNICODETEXT) break; } if (allow_bitmap && format == CF_BITMAP) return clipboardBitmap(L); if (format == CF_UNICODETEXT){ HGLOBAL hGlobal = GetClipboardData(CF_UNICODETEXT); if (hGlobal == nullptr) { CloseClipboard(); return 0; } String s((wchar_t *) GlobalLock(hGlobal)); GlobalUnlock(hGlobal); CloseClipboard(); lua_pushstring(L, s.z()); return 1; } CloseClipboard(); return 0; } int AppUi::setClipboard(lua_State *L) { const char *s = luaL_checklstring(L, 2, nullptr); WString ws(s); size_t size = (ws.size() + 1) * sizeof(wchar_t); HGLOBAL hGlobal = GlobalAlloc(GMEM_MOVEABLE, size); wchar_t *p = (wchar_t *) GlobalLock(hGlobal); memcpy(p, ws.data(), size); GlobalUnlock(hGlobal); OpenClipboard(hwnd); EmptyClipboard(); if (SetClipboardData(CF_UNICODETEXT, hGlobal) == nullptr) GlobalFree(hGlobal); // clipboard didn't take the data CloseClipboard(); return 0; } // -------------------------------------------------------------------- struct WindowCounter { int count; HWND hwnd; }; BOOL CALLBACK AppUi::enumThreadWndProc(HWND hwnd, LPARAM lParam) { WindowCounter *wc = (WindowCounter *) lParam; // ipeDebug("Enumerating Window %d", int(hwnd)); wchar_t cname[100]; if (GetClassNameW(hwnd, cname, 100) && !wcscmp(cname, className) && wc->hwnd != hwnd) wc->count += 1; return TRUE; } LRESULT CALLBACK AppUi::wndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { AppUi *ui = (AppUi*) GetWindowLongPtr(hwnd, GWLP_USERDATA); switch (message) { case WM_CREATE: { LPCREATESTRUCT p = (LPCREATESTRUCT) lParam; ui = (AppUi *) p->lpCreateParams; ui->hwnd = hwnd; SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR) ui); ui->initUi(); } break; case WM_INITMENUPOPUP: if (ui) { if (lParam == 2) ui->populateTextStyleMenu(); else if (lParam == 3) ui->populateSizeMenus(); else if (lParam == 6) ui->populateLayerMenus(); } break; case WM_ACTIVATE: if (ui && ui->iCanvas && LOWORD(wParam)) SetFocus(ui->hwndCanvas); return 0; case WM_COMMAND: if (ui) ui->cmd(LOWORD(wParam), HIWORD(wParam)); break; case WM_CTLCOLORSTATIC: if (ui && ui->iCanvas && HWND(lParam) == ui->hNotes) return (INT_PTR) (HBRUSH) GetStockObject(WHITE_BRUSH); break; case WM_TIMER: if (ui && ui->iCanvas) SendMessageW(ui->hStatusBar, SB_SETTEXT, 0, (LPARAM) 0); return 0; case WM_SIZE: if (ui && ui->iCanvas) ui->layoutChildren(true); break; case WM_NOTIFY: switch (((LPNMHDR)lParam)->code) { case RBN_CHILDSIZE: if (ui && ui->iCanvas) ui->layoutChildren(false); break; case NM_CUSTOMDRAW: { switch (((LPNMCUSTOMDRAW) lParam)->dwDrawStage) { case CDDS_PREPAINT: return CDRF_NOTIFYITEMDRAW; case CDDS_ITEMPREPAINT: { LPNMLVCUSTOMDRAW q = (LPNMLVCUSTOMDRAW) lParam; UINT flags = q->nmcd.lItemlParam; if (flags & 0x01) // active q->clrTextBk = 0x0000ffff; if (flags & 0x02) // locked q->clrTextBk = RGB(255, 220, 220); if (flags & 0x04) // no snapping q->clrText = RGB(0, 0, 160); return CDRF_NEWFONT; } default: break; } break; } case NM_RCLICK: if (ui) { LPNMITEMACTIVATE nm = (LPNMITEMACTIVATE) lParam; HWND from = nm->hdr.hwndFrom; int l = nm->iItem; if (from == ui->hLayers && l >= 0) { POINT pos = ((LPNMITEMACTIVATE) lParam)->ptAction; ClientToScreen(ui->hLayers, &pos); Vector v(pos.x, pos.y); ui->luaShowLayerBoxPopup(v, ui->iLayerNames[l]); return 1; // no default processing } } break; case LVN_ITEMACTIVATE: if (ui) { int l = ((LPNMITEMACTIVATE) lParam)->iItem; if (l >= 0) { ui->luaLayerAction("active", ui->iLayerNames[l]); } } break; case LVN_ITEMCHANGED: if (ui && !ui->iSettingLayers) { int i = ((LPNMLISTVIEW) lParam)->iItem; if (i >= 0) { bool checked = (ListView_GetCheckState(ui->hLayers, i) != 0); ui->luaLayerAction(checked ? "selecton" : "selectoff", ui->iLayerNames[i]); } } break; } break; case WM_CLOSE: if (ui) { ui->closeRequested(); return 0; // do NOT allow default procedure to close } break; case WM_DESTROY: { delete ui; // only post quit message when this was the last window WindowCounter wc; wc.count = 0; wc.hwnd = hwnd; EnumThreadWindows(GetCurrentThreadId(), enumThreadWndProc, (LPARAM) &wc); if (wc.count == 0) PostQuitMessage(0); } break; default: break; } return DefWindowProc(hwnd, message, wParam, lParam); } // -------------------------------------------------------------------- bool AppUi::isDrawing(HWND target) { // check that it really is an AppUi window WNDPROC w = (WNDPROC) GetWindowLongPtr(target, GWLP_WNDPROC); if (w != AppUi::wndProc) return false; AppUi *ui = (AppUi*) GetWindowLongPtr(target, GWLP_USERDATA); return ui && ui->iCanvas && ui->iCanvas->tool(); } void AppUi::init(HINSTANCE hInstance, int nCmdShow) { WNDCLASSEX wc; wc.cbSize = sizeof(WNDCLASSEX); wc.style = 0; wc.lpfnWndProc = wndProc; wc.cbClsExtra = 0; wc.cbWndExtra = 0; wc.hInstance = hInstance; wc.hCursor = LoadCursor(nullptr, IDC_ARROW); wc.hbrBackground = (HBRUSH)(COLOR_BTNFACE+1); wc.lpszMenuName = nullptr; wc.lpszClassName = className; wc.hIcon = LoadIcon(GetModuleHandle(nullptr), MAKEINTRESOURCE(IDI_MYICON)); wc.hIconSm = HICON(LoadImage(GetModuleHandle(nullptr), MAKEINTRESOURCE(IDI_MYICON), IMAGE_ICON, 16, 16, 0)); if (!RegisterClassEx(&wc)) { MessageBoxA(nullptr, "AppUi registration failed!", "Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } Canvas::init(hInstance); PathView::init(hInstance); // save for later use win_hInstance = hInstance; win_nCmdShow = nCmdShow; } AppUiBase *createAppUi(lua_State *L0, int model) { return new AppUi(L0, model); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/main_win.cpp0000644000175000017500000001226413561570220016112 0ustar otfriedotfried// -------------------------------------------------------------------- // Main function for Win32 // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebase.h" #include "ipelua.h" #include #include #include "appui_win.h" #include using namespace ipe; using namespace ipelua; #include "main_common.i" // -------------------------------------------------------------------- static void setup_win_config(lua_State *L, const char *var, int folderId) { String s; wchar_t szPath[MAX_PATH]; if (SUCCEEDED(SHGetFolderPathW(nullptr, folderId, nullptr, 0, szPath))) s = String(szPath); else s = "C:"; push_string(L, s); lua_setfield(L, -2, var); } static void setup_globals(lua_State *L) { lua_getglobal(L, "package"); const char *luapath = getenv("IPELUAPATH"); if (luapath) lua_pushstring(L, luapath); else push_string(L, Platform::ipeDir("lua", "?.lua")); lua_setfield(L, -2, "path"); lua_newtable(L); // config table lua_pushliteral(L, "win"); lua_setfield(L, -2, "platform"); lua_pushliteral(L, "win"); lua_setfield(L, -2, "toolkit"); setup_config(L, "system_styles", nullptr, "styles"); setup_config(L, "system_ipelets", nullptr, "ipelets"); setup_config(L, "docdir", "IPEDOCDIR", "doc"); setup_win_config(L, "desktop", CSIDL_DESKTOP); setup_win_config(L, "documents", CSIDL_PERSONAL); setup_common_config(L); int cx = GetSystemMetrics(SM_CXSCREEN); int cy = GetSystemMetrics(SM_CYSCREEN); lua_createtable(L, 0, 2); lua_pushinteger(L, cx); lua_rawseti(L, -2, 1); lua_pushinteger(L, cy); lua_rawseti(L, -2, 2); lua_setfield(L, -2, "screen_geometry"); lua_setglobal(L, "config"); lua_pushcfunction(L, ipe_tonumber); lua_setglobal(L, "tonumber"); } // -------------------------------------------------------------------- static HACCEL makeAccel(lua_State *L, int arg) { luaL_argcheck(L, lua_istable(L, arg), arg, "Argument is not a table"); int no = lua_rawlen(L, arg); luaL_argcheck(L, no > 0, arg, "Table must have at least one shortcut"); std::vector accel; for (int i = 1; i <= no; i += 2) { lua_rawgeti(L, arg, i); lua_rawgeti(L, arg, i+1); ACCEL a; int key = luaL_checkinteger(L, -2); a.key = key & 0xffff; a.cmd = luaL_checkinteger(L, -1); a.fVirt = (((key & 0x10000) ? FALT : 0) | ((key & 0x20000) ? FCONTROL : 0) | ((key & 0x40000) ? FSHIFT : 0) | ((key & 0x80000) ? 0 : FVIRTKEY)); accel.push_back(a); if (0x30 <= a.key && a.key <= 0x39 && (a.fVirt & FVIRTKEY)) { a.key += 0x30; accel.push_back(a); // add numpad version } lua_pop(L, 2); } HACCEL hAccel = CreateAcceleratorTable(&accel[0], accel.size()); return hAccel; } int mainloop(lua_State *L) { HACCEL hAccelAll = makeAccel(L, 1); HACCEL hAccelSub = makeAccel(L, 2); MSG msg; while (GetMessage(&msg, nullptr, 0, 0) > 0) { HWND target = GetAncestor(msg.hwnd, GA_ROOT); HACCEL acc = AppUi::isDrawing(target) ? hAccelSub : hAccelAll; if (!TranslateAccelerator(target, acc, &msg)) { TranslateMessage(&msg); DispatchMessage(&msg); } } return 0; } int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) { Platform::initLib(IPELIB_VERSION); INITCOMMONCONTROLSEX icex; icex.dwSize = sizeof(INITCOMMONCONTROLSEX); icex.dwICC = ICC_COOL_CLASSES | ICC_BAR_CLASSES | ICC_TAB_CLASSES | ICC_LISTVIEW_CLASSES | ICC_USEREX_CLASSES | ICC_STANDARD_CLASSES; InitCommonControlsEx(&icex); AppUi::init(hInstance, nCmdShow); lua_State *L = setup_lua(); // setup command line argument wchar_t *w = GetCommandLineW(); int argc; wchar_t **argv = CommandLineToArgvW(w, &argc); // create table with arguments lua_createtable(L, 0, argc - 1); for (int i = 1; i < argc; ++i) { String p(argv[i]); lua_pushstring(L, p.z()); lua_rawseti(L, -2, i); } lua_setglobal(L, "argv"); setup_globals(L); lua_run_ipe(L, mainloop); lua_close(L); return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/lua/0000755000175000017500000000000013561570220014361 5ustar otfriedotfriedipe-7.2.13/src/ipe/lua/editpath.lua0000644000175000017500000010336713561570220016700 0ustar otfriedotfried---------------------------------------------------------------------- -- editpath.lua ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] EDITTOOL = {} EDITTOOL.__index = EDITTOOL local VERTEX = 1 local SPLINECP = 2 local CENTER = 3 local RADIUS = 4 local MINOR = 5 local CURRENT = 6 local SCISSOR = 7 ---------------------------------------------------------------------- function revertSubpath(t, shape) shape[t.spNum] = t.original end -- clone a subpath -- reuses the same CP (Vector) objects function cloneSubpath(sp) local nsp = {} for n in pairs(sp) do local t = sp[n] if type(t) == "table" then local nt = {} for nn in pairs(t) do nt[nn] = t[nn] end t = nt end nsp[n] = t end return nsp end local function recomputeMatrix(seg, cpno) local alpha, beta = seg.arc:angles() local p = ipe.Direction(alpha) local q = ipe.Direction(beta) local cl if cpno == 1 then cl = ipe.LineThrough(V(0,0), q) p = seg.arc:matrix():inverse() * seg[cpno] else -- cpno == 2 cl = ipe.LineThrough(V(0,0), p) q = seg.arc:matrix():inverse() * seg[cpno] end local center = ipe.Bisector(p, q):intersects(cl) if center and center:sqLen() < 1e10 then local radius = (p - center):len() alpha = (p - center):angle() beta = (q - center):angle() local m = (seg.arc:matrix() * ipe.Matrix(radius, 0, 0, radius, center.x, center.y)) seg.arc = ipe.Arc(m, alpha, beta) end end function moveCP(shape, spno, segno, cpno, v) local sp = shape[spno] if sp.type == "closedspline" then sp[cpno] = v elseif sp.type == "ellipse" then if cpno == 0 then -- center local m = sp[1]:elements() m[5] = v.x m[6] = v.y sp[1] = ipe.Matrix(m) elseif cpno == 1 then -- radius local u = sp[1]:inverse() * v local radius = u:len() local alpha = u:angle() local m = (sp[1] * ipe.Matrix(radius, 0, 0, radius, 0, 0) * ipe.Rotation(alpha)) if not m:isSingular() then sp[1] = m end elseif cpno == 2 then -- minor local u = sp[1]:inverse() * v local m = sp[1] * ipe.Matrix(1, 0, u.x, u.y, 0, 0) if not m:isSingular() then sp[1] = m end end else -- curve local seg = sp[segno] if cpno == 0 then -- center of arc local v1 = seg.arc:matrix():inverse() * v local alpha, beta = seg.arc:angles() local p, q = ipe.Direction(alpha), ipe.Direction(beta) local l = ipe.Bisector(p, q) local center = l:project(v1) local radius = (p - center):len() local m = ipe.Matrix(radius, 0, 0, radius, center.x, center.y) m = seg.arc:matrix() * m seg.arc = ipe.Arc(m, (p - center):angle(), (q - center):angle()) else seg[cpno] = v if cpno == 1 and segno > 1 then local pseg = sp[segno - 1] pseg[#pseg] = v elseif cpno == #seg and segno < #sp then sp[segno + 1][1] = v end if seg.type == "arc" then recomputeMatrix(seg, cpno) end if segno > 1 and cpno == 1 and sp[segno - 1].type == "arc" then recomputeMatrix(sp[segno - 1], 2) end if segno < #sp and cpno == #seg and sp[segno + 1].type == "arc" then recomputeMatrix(sp[segno + 1], 1) end end end end ---------------------------------------------------------------------- function EDITTOOL:new(model, prim, obj) local tool = {} setmetatable(tool, EDITTOOL) tool.model = model tool.undo = {} tool.primary = prim tool.obj = obj tool.shape = obj:shape() transformShape(obj:matrix(), tool.shape) model.ui:shapeTool(tool) tool.setColor(1.0, 0, 0) tool.setSnapping(true, false) tool:resetCP() tool:setShapeMarks() return tool end ---------------------------------------------------------------------- function EDITTOOL:resetCP() self.spNum = 1 self.segNum = 1 self.cpNum = 1 if self.shape[1].type == "ellipse" then self.cpNum = 0 end end function EDITTOOL:type() local cur = self.shape[self.spNum] if cur.type == "closedspline" then return SPLINECP end if self.cpNum == 0 then return CENTER end if cur.type == "ellipse" then if self.cpNum == 1 then return RADIUS else return MINOR end end cur = cur[self.segNum] if self.cpNum == 1 or self.cpNum == #cur then return VERTEX end if cur.type == "spline" or cur.type == "oldspline" then return SPLINECP end -- must be center of arc return CENTER end function EDITTOOL:current() local cur = self.shape[self.spNum] if cur.type == "ellipse" then if self.cpNum == 0 then return cur[1]:translation() elseif self.cpNum == 1 then return cur[1] * V(1,0) elseif self.cpNum == 2 then return cur[1] * V(0,1) end end if cur.type == "curve" then cur = cur[self.segNum] end if self.cpNum == 0 then cur = cur.arc:matrix():translation() else cur = cur[self.cpNum] end return cur end function EDITTOOL:canDelete() local t = self:type() if t == SPLINECP then return true end if t == VERTEX then local sp = self.shape[self.spNum] if sp[self.segNum].type ~= "segment" then return false end if self.cpNum == 1 then return self.segNum == 1 or sp[self.segNum - 1].type == "segment" end if self.cpNum == 2 then return self.segNum == #sp or sp[self.segNum + 1].type == "segment" end end return false end ---------------------------------------------------------------------- function EDITTOOL:setShapeMarks() local m = {} local aux = {} for _, sp in ipairs(self.shape) do if sp.type == "closedspline" then for _,cp in ipairs(sp) do m[#m + 1] = cp m[#m + 1] = SPLINECP end local as = { type="curve", closed=true } for i = 2,#sp do as[#as + 1] = { type="segment", sp[i-1], sp[i] } end aux[#aux + 1] = as elseif sp.type == "curve" then m[#m + 1] = sp[1][1] m[#m + 1] = VERTEX for _,seg in ipairs(sp) do m[#m + 1] = seg[#seg] m[#m + 1] = VERTEX if seg.type=="spline" or seg.type=="oldspline" then for i = 2,#seg-1 do m[#m + 1] = seg[i] m[#m + 1] = SPLINECP end local as = { type="curve", closed=false } for i = 2,#seg do as[#as + 1] = { type="segment", seg[i-1], seg[i] } end aux[#aux + 1] = as elseif seg.type == "arc" then m[#m + 1] = seg.arc:matrix():translation() m[#m + 1] = CENTER end end else -- ellipse m[#m + 1] = sp[1]:translation() m[#m + 1] = CENTER m[#m + 1] = sp[1] * V(1, 0) m[#m + 1] = RADIUS m[#m + 1] = sp[1] * V(0, 1) m[#m + 1] = MINOR end end m[#m + 1] = self:current() m[#m + 1] = CURRENT if self.scissor then m[#m + 1] = self.scissorPos m[#m + 1] = SCISSOR end self.setShape(self.shape) self.setShape(aux, 1) self.setMarks(m) end function EDITTOOL:find(v) local bd = 1000000 -- maybe init with current vertex local spnum, segnum, cpnum for i,sp in ipairs(self.shape) do if sp.type == "closedspline" then for j,cp in ipairs(sp) do if (v-cp):sqLen() < bd then bd = (v-cp):sqLen() spnum = i segnum = 1 cpnum = j end end elseif sp.type == "ellipse" then local cp = sp[1]:translation() if (v-cp):sqLen() < bd then bd = (v-cp):sqLen() spnum = i segnum = 1 cpnum = 0 end cp = sp[1] * V(1,0) if (v-cp):sqLen() < bd then bd = (v-cp):sqLen() spnum = i segnum = 1 cpnum = 1 end cp = sp[1] * V(0,1) if (v-cp):sqLen() < bd then bd = (v-cp):sqLen() spnum = i segnum = 1 cpnum = 2 end else -- curve for j,seg in ipairs(sp) do for k,cp in ipairs(seg) do if (v-cp):sqLen() < bd then bd = (v-cp):sqLen() spnum = i segnum = j cpnum = k end end if seg.type == "arc" then local cp = seg.arc:matrix():translation() if (v-cp):sqLen() < bd then bd = (v-cp):sqLen() spnum = i segnum = j cpnum = 0 end end end end end return spnum, segnum, cpnum end ---------------------------------------------------------------------- function EDITTOOL:action_delete_subpath() local t = { label = "delete subpath", spNum = self.spNum, original = table.remove(self.shape, self.spNum), undo = function (t, shape) table.insert(shape, t.spNum, t.original) end } self.undo[#self.undo + 1] = t self:resetCP() end function EDITTOOL:action_delete() local sp = self.shape[self.spNum] local t = { label = "delete control point", spNum = self.spNum, original = cloneSubpath(sp), undo = revertSubpath } if sp.type == "closedspline" then -- cannot have closed spline with less than 3 cp if #sp < 4 then return end table.remove(sp, self.cpNum) elseif sp.type == "curve" then local seg = sp[self.segNum] if 1 < self.cpNum and self.cpNum < #seg then -- must be SPLINECP table.remove(seg, self.cpNum) if #seg == 2 then seg.type = "segment" end else -- VERTEX assert(seg.type == "segment") -- cannot delete from last segment or from last triangle if #sp == 1 or sp.closed and #sp == 2 then return end if self.cpNum == 1 and self.segNum == 1 then table.remove(sp, 1) elseif self.cpNum == 2 and self.segNum == #sp then table.remove(sp, #sp) else -- not first vertex, not last vertex if self.cpNum == 1 then self.segNum = self.segNum - 1 seg = sp[self.segNum] assert(seg.type == "segment") self.cpNum = 2 end assert(self.cpNum == 2) sp[self.segNum + 1][1] = seg[1] table.remove(sp, self.segNum) end end end self.undo[#self.undo + 1] = t self:resetCP() end function EDITTOOL:action_duplicate() local sp = self.shape[self.spNum] local t = { label = "duplicate control point", spNum = self.spNum, original = cloneSubpath(sp), undo = revertSubpath } if sp.type == "closedspline" then local cp = sp[self.cpNum] table.insert(sp, self.cpNum, cp) local pcp, ncp if self.cpNum > 1 then pcp = sp[self.cpNum - 1] else pcp = sp[#sp] end if self.cpNum < #sp-1 then ncp = sp[self.cpNum + 2] else ncp = sp[1] end sp[self.cpNum] = 0.9 * cp + 0.1 * pcp sp[self.cpNum + 1] = 0.9 * cp + 0.1 * ncp else assert(sp.type == "curve") local seg = sp[self.segNum] local cp = seg[self.cpNum] if 1 < self.cpNum and self.cpNum < #seg then assert(seg.type == "spline" or seg.type == "oldspline") table.insert(seg, self.cpNum, cp) local pcp = seg[self.cpNum - 1] local ncp = seg[self.cpNum + 2] seg[self.cpNum] = 0.9 * cp + 0.1 * pcp seg[self.cpNum + 1] = 0.9 * cp + 0.1 * ncp else if self.cpNum == #sp[self.segNum] then self.segNum = self.segNum + 1 self.cpNum = 1 end assert(self.cpNum == 1) local seg = { type="segment", cp, cp } table.insert(sp, self.segNum, seg) if self.segNum > 1 then local pseg = sp[self.segNum - 1] seg[1] = 0.9 * cp + 0.1 * pseg[#pseg - 1] pseg[#pseg] = seg[1] end if self.segNum < #sp then local nseg = sp[self.segNum + 1] seg[2] = 0.9 * cp + 0.1 * nseg[2] nseg[1] = seg[2] end end end self.undo[#self.undo + 1] = t end function EDITTOOL:action_cut() local sp = self.shape[self.spNum] local t = { label = "cut at vertex", spNum = self.spNum, original = cloneSubpath(sp), undo = function (t, shape) shape[t.spNum] = t.original if t.newSpNum then table.remove(shape, t.newSpNum) end end } assert(sp.type == "curve") if not sp.closed then -- cannot cut at first or last vertex if self.segNum == 1 and self.cpNum == 1 then return end if self.segNum == #sp and self.cpNum ~= 1 then return end if self.cpNum ~= 1 then self.segNum = self.segNum + 1 self.cpNum = 1 end local nsp = { type = "curve", closed = false } for i = self.segNum,#sp do nsp[#nsp + 1] = sp[i] end for i = #sp,self.segNum,-1 do table.remove(sp, i) end self.spNum = self.spNum + 1 t.newSpNum = self.spNum table.insert(self.shape, t.newSpNum, nsp) self.segNum = 1 else -- sp is closed sp.closed = false local lastseg = sp[#sp] local newseg = { type = "segment", lastseg[#lastseg], sp[1][1] } if self.segNum == 1 and self.cpNum == 1 then sp[#sp + 1] = newseg elseif self.segNum == #sp and self.cpNum ~= 1 then table.insert(sp, 1, newseg) else -- cutting somewhere else if self.cpNum ~= 1 then self.segNum = self.segNum + 1 self.cpNum = 1 end sp[#sp + 1] = newseg -- move self.segNum - 1 segments from front to back for i=1,self.segNum - 1 do local seg = table.remove(sp, 1) sp[#sp + 1] = seg end end self.segNum = 1 self.cpNum = 1 end end function EDITTOOL:action_convert_spline() local sp = self.shape[self.spNum] local t = { label = "convert spline to Beziers", spNum = self.spNum, original = cloneSubpath(sp), undo = revertSubpath } if sp.type == "closedspline" then local beziers = ipe.splineToBeziers(sp, true) beziers.type = "curve" beziers.closed = false self.shape[self.spNum] = beziers else local beziers = ipe.splineToBeziers(sp[self.segNum], false, sp[self.segNum].type == "oldspline") table.remove(sp, self.segNum) for i=1,#beziers do table.insert(sp, self.segNum + i - 1, beziers[i]) end end self.undo[#self.undo + 1] = t end function EDITTOOL:action_insert_knot() local sp = self.shape[self.spNum] local seg = sp[self.segNum] -- Knot sequence: [0, 0, 0, 1, 2, 3, 4, 5, 6, ..., k-2, k-1, k, k, k] -- It has k + 5 = n + 2 knots, so there are k = n-3 knot intervals. -- cps are [0,0,0], [0,0,1], [0,1,2]...[k-2,k-1,k],[k-1,k,k],[k,k,k] -- we are going to insert a vertex at knot t, with 1 <= t <= k-1 local k = #seg - 3 -- we need k >= 3, so handle case n = 5 separately: if k < 3 then self:action_convert_spline() return end local t = self.cpNum - 2 if t < 1 then t = 1 end if t > k - 1 then t = k-1 end local ls = { type = "spline" } local rs = { type = "spline" } if t == 1 then -- we need [0,1,1], [1,1,1] and [1,1,2] -- [0,1,1] = 1/2 [0,0,1] + 1/2 [0,2,1] local q = 0.5 * (seg[2] + seg[3]) -- [1,1,2] = 2/3 [0,1,2] + 1/3 [3,1,2] local r = (1.0/3.0) * (2 * seg[3] + seg[4]) local p = 0.5 * (q + r) -- [1,1,1] ls[1] = seg[1] ls[2] = seg[2] ls[3] = q ls[4] = p rs[1] = p rs[2] = r for i=4,#seg do rs[#rs+1] = seg[i] end elseif t == k-1 then -- we need [k-2,k-1,k-1], [k-1,k-1,k-1] and [k-1,k-1,k] -- [k-2,k-1,k-1] = 1/3 [k-2,k-1,k-3] + 2/3 [k-2,k-1,k] local q = (1.0/3.0) * (seg[k] + 2 * seg[k+1]) -- [k-1,k-1,k] = 1/2 [k-2,k-1,k] + 1/2 [k,k-1,k] local r = 0.5 * (seg[k+1] + seg[k+2]) local p = 0.5 * (q + r) -- [k-1,k-1,k-1] for i = 1,#seg-3 do ls[i] = seg[i] end ls[#ls+1] = q ls[#ls+1] = p rs[1] = p rs[2] = r rs[3] = seg[#seg-1] rs[4] = seg[#seg] else -- 2 <= t <= k-2 -- we need [t-1,t,t], [t,t,t], [t,t,t+1] -- [t-1,t,t] = 1/3 [t-1,t,t-2] + 2/3 [t-1,t,t+1] local q = (1.0/3.0) * (seg[t+1] + 2 * seg[t+2]) -- [t,t,t+1] = 2/3 [t-1,t,t+1] + 1/3 [t+2,t,t+1] local r = (1.0/3.0) * (2 * seg[t+2] + seg[t+3]) -- [t,t,t] = 1/2 [t,t,t-1] + 1/2[t,t,t+1] local p = 0.5 * (q + r) -- copy [0,0,0]...[t-2,t-1,t] for i=1,t+1 do ls[i] = seg[i] end ls[t+2] = q ls[t+3] = p rs[1] = p rs[2] = r -- copy [t,t+1,t+2] ... [k,k,k] for i=t+3,#seg do rs[#rs+1] = seg[i] end end local it = { label = "insert vertex at knot " .. t, spNum = self.spNum, original = cloneSubpath(sp), undo = revertSubpath } table.remove(sp, self.segNum) table.insert(sp, self.segNum, ls) table.insert(sp, self.segNum + 1, rs) self.undo[#self.undo + 1] = it end function EDITTOOL:action_insert_knot_closed() local sp = self.shape[self.spNum] local n = #sp local t = self.cpNum local it = { label = "insert vertex at knot " .. t, spNum = self.spNum, original = cloneSubpath(sp), undo = revertSubpath } -- knot sequence: 0 1 2 3 4 ... n-1 n n+1 n+2 -- where [n n+1 n+2] = [0 1 2], etc. -- rotate knot to the front for i=1,t-1 do local v = table.remove(sp, 1) sp[#sp+1] = v end -- cut at knot 1 -- need [0,1,1], [1,1,1], and [1,1,2] -- [0,1,1] = 1/3 [-1,0,1] + 2/3 [2,0,1] local q = (1.0/3.0) * (sp[n] + 2 * sp[1]) -- [1,1,2] = 2/3 [0,1,2] + 1/3 [3,1,2] local r = (1.0/3.0) * (2 * sp[1] + sp[2]) local p = 0.5 * (q + r) -- [1,1,1] local seg = { type="spline" } seg[1] = p seg[2] = r for i=2,n do seg[#seg+1] = sp[i] end seg[#seg+1] = q seg[#seg+1] = p table.remove(self.shape, self.spNum) table.insert(self.shape, self.spNum, { type="curve", closed=false, seg }) self.cpNum = 1 self.undo[#self.undo + 1] = it end ---------------------------------------------------------------------- -- subdivide at parameter t (0 <= t <= 1) local function subdivideBezier(bez, t) local tt = 1 - t local l = {} local r = {} l[1] = bez[1]; l[2] = tt * bez[1] + t * bez[2] local h = tt * bez[2] + t * bez[3] l[3] = tt * l[2] + t * h r[3] = tt * bez[3] + t * bez[4] r[2] = tt * h + t * r[3] r[1] = tt * l[3] + t * r[2] l[4] = r[1] r[4] = bez[4] return l, r end -- subdivide at parameter t (0 <= t <= 1) local function subdivideQuad(bez, t) local tt = 1 - t local l = {} local r = {} l[1] = bez[1]; l[2] = tt * bez[1] + t * bez[2] r[2] = tt * bez[2] + t * bez[3] r[1] = tt * l[2] + t * r[2] l[3] = r[1] r[3] = bez[3] return l, r end function EDITTOOL:cutter_ellipse() local sp = self.shape[self.spNum] local t = { label = "cut ellipse", spNum = self.spNum, original = cloneSubpath(sp), undo = revertSubpath, } local alpha, _ = self.scissor(self.model.ui:pos()) sp.type = "curve" sp.closed = false local arc = ipe.Arc(sp[1], alpha, alpha - 0.2) local cp1, cp2 = arc:endpoints() sp[1] = { type = "arc", arc = arc, cp1, cp2 } self.undo[#self.undo + 1] = t end function EDITTOOL:cutter_arc() local sp = self.shape[self.spNum] local t = { label = "cut arc", spNum = self.spNum, original = cloneSubpath(sp), undo = function (t, shape) shape[t.spNum] = t.original if t.newSpNum then table.remove(shape, t.newSpNum) end end } local nalpha, _ = self.scissor(self.model.ui:pos()) local seg = sp[self.segNum] local alpha, beta = seg.arc:angles() local narc1 = ipe.Arc(seg.arc:matrix(), alpha, nalpha) local narc2 = ipe.Arc(seg.arc:matrix(), nalpha, beta) local npos, _ = narc2:endpoints() local nseg1 = { type = "arc", arc = narc1, seg[1], npos } local nseg2 = { type = "arc", arc = narc2, npos, seg[2] } if not sp.closed then local nsp = { type = "curve", closed = false, nseg2 } for i = self.segNum+1,#sp do nsp[#nsp + 1] = sp[i] end for i = #sp,self.segNum+1,-1 do table.remove(sp, i) end sp[self.segNum] = nseg1 t.newSpNum = self.spNum + 1 table.insert(self.shape, t.newSpNum, nsp) else -- sp is closed sp.closed = false local lastseg = sp[#sp] local nsp = { type = "curve", closed = false, nseg2 } for i = self.segNum+1,#sp do nsp[#nsp + 1] = sp[i] end nsp[#nsp + 1] = { type = "segment", lastseg[#lastseg], sp[1][1] } for i = 1,self.segNum-1 do nsp[#nsp + 1] = sp[i] end nsp[#nsp + 1] = nseg1 self.shape[self.spNum] = nsp self.segNum = #nsp end self.undo[#self.undo + 1] = t end function EDITTOOL:cutter_bezier() local sp = self.shape[self.spNum] local t = { label = "cut bezier", spNum = self.spNum, original = cloneSubpath(sp), undo = function (t, shape) shape[t.spNum] = t.original if t.newSpNum then table.remove(shape, t.newSpNum) end end } local param, _ = self.scissor(self.model.ui:pos()) local seg = sp[self.segNum] local nseg1, nseg2 if #seg == 4 then nseg1, nseg2 = subdivideBezier(seg, param) else nseg1, nseg2 = subdivideQuad(seg, param) end nseg1.type = "spline" nseg2.type = "spline" if not sp.closed then local nsp = { type = "curve", closed = false, nseg2 } for i = self.segNum+1,#sp do nsp[#nsp + 1] = sp[i] end for i = #sp,self.segNum+1,-1 do table.remove(sp, i) end sp[self.segNum] = nseg1 t.newSpNum = self.spNum + 1 table.insert(self.shape, t.newSpNum, nsp) else -- sp is closed sp.closed = false local lastseg = sp[#sp] local nsp = { type = "curve", closed = false, nseg2 } for i = self.segNum+1,#sp do nsp[#nsp + 1] = sp[i] end nsp[#nsp + 1] = { type = "segment", lastseg[#lastseg], sp[1][1] } for i = 1,self.segNum-1 do nsp[#nsp + 1] = sp[i] end nsp[#nsp + 1] = nseg1 self.shape[self.spNum] = nsp self.segNum = #nsp end self.undo[#self.undo + 1] = t end ---------------------------------------------------------------------- local function scissor_arc(pos, arc) local t, p = arc:snap(pos) return t, p end local function scissor_bezier(pos, bezier) local t, p = bezier:snap(pos) return t, p end function EDITTOOL:action_cut_bezier() local sp = self.shape[self.spNum] local seg = sp[self.segNum] local bezier if #seg == 4 then bezier = ipe.Bezier(seg[1], seg[2], seg[3], seg[4]) else bezier = ipe.Quad(seg[1], seg[2], seg[3]) end self.scissor = function (pos) return scissor_bezier(pos, bezier) end self.scissorPos = sp[self.segNum][1] self.cutter = "cutter_bezier" end function EDITTOOL:action_cut_arc() local sp = self.shape[self.spNum] local arc = sp[self.segNum].arc self.scissor = function (pos) return scissor_arc(pos, arc) end self.scissorPos = sp[self.segNum][1] self.cutter = "cutter_arc" end function EDITTOOL:action_cut_ellipse() local sp = self.shape[self.spNum] local arc = ipe.Arc(sp[1]) self.scissor = function (pos) return scissor_arc(pos, arc) end self.scissorPos = arc:matrix() * V(1,0) self.cutter = "cutter_ellipse" end ---------------------------------------------------------------------- function EDITTOOL:action_undo() self.moving = false self.scissor = false if #self.undo == 0 then self.model:warning("Nothing to undo") return end local t = self.undo[#self.undo] table.remove(self.undo) t.undo(t, self.shape) self:resetCP() self.model.ui:explain("Undo " .. t.label) end ---------------------------------------------------------------------- function EDITTOOL:showMenu() local t = self:type() local m = ipeui.Menu(self.model.ui:win()) local gp = self.model.ui:globalPos() if self:canDelete() then m:add("action_delete", "Delete vertex") end if t == VERTEX or t == SPLINECP then m:add("action_duplicate", "Duplicate vertex") end if t == VERTEX then m:add("action_cut", "Cut at vertex") end if #self.shape > 1 then m:add("action_delete_subpath", "Delete subpath") end if t == SPLINECP then local sp = self.shape[self.spNum] if sp.type == "closedspline" then m:add("action_convert_spline", "Convert spline to Bezier segments") m:add("action_insert_knot_closed", "Cut closed spline at knot " .. self.cpNum) else local n = #(sp[self.segNum]) if n > 4 then m:add("action_convert_spline", "Convert spline to Bezier segments") local t = self.cpNum - 2 if t < 1 then t = 1 end if t > n - 4 then t = n - 4 end m:add("action_insert_knot", "Insert vertex at knot " .. t .. " (of " .. (n-3) .. " knot intervals)") else m:add("action_cut_bezier", "Cut inside Bezier curve") end end end if t == CENTER then if self.shape[self.spNum].type == "ellipse" then m:add("action_cut_ellipse", "Cut ellipse") else m:add("action_cut_arc", "Cut arc") end end m:add("action_undo", "Undo") m:add("accept", "Accept") local item = m:execute(gp.x, gp.y) if item == "accept" then self.moving = false self:acceptEdit() self.model.ui:finishTool() return end if item then self[item](self) self:setShapeMarks() self.model.ui:update(false) -- update tool end end ---------------------------------------------------------------------- function EDITTOOL:mouseButton(button, modifiers, press) self.moving = false if modifiers.control and button == 1 then button = 2 end if self.scissor and press and button == 1 then self[self.cutter](self) self.scissor = nil self:setShapeMarks() self.model.ui:update(false) -- update tool self:explain() return end self.scissor = nil if not press then self.setSnapping(true, false) return end if button == 0x81 then -- previous click must have created a move action, discard table.remove(self.undo) button = 2 end if button == 2 then self.spNum, self.segNum, self.cpNum = self:find(self.model.ui:unsnappedPos()) self:showMenu() return end if button == 1 then self.spNum, self.segNum, self.cpNum = self:find(self.model.ui:unsnappedPos()) self.moving = true -- TODO: avoid the moving vertex snapping to itself self.setSnapping(false, false) local t = { label = "move", original = cloneSubpath(self.shape[self.spNum]), spNum = self.spNum, undo = revertSubpath } self.undo[#self.undo + 1] = t end self:setShapeMarks() self.model.ui:update(false) -- update tool self:explain() end function EDITTOOL:mouseMove(button, modifiers) if self.moving then local pos = self.model.ui:pos() moveCP(self.shape, self.spNum, self.segNum, self.cpNum, pos) self:setShapeMarks() self.model.ui:update(false) -- update tool elseif self.scissor then local t t, self.scissorPos = self.scissor(self.model.ui:pos()) self:setShapeMarks() self.model.ui:update(false) -- update tool end self:explain() end function EDITTOOL:explain() if self.scissor then self.model.ui:explain("Left: cut | Right, ctrl-left, or double-left: menu" .. " | Ctrl+Z: undo | Space: accept") else self.model.ui:explain("Left: move | Right, ctrl-left, or double-left: menu" .. " | Ctrl+Z: undo | Space: accept") end end function EDITTOOL:acceptEdit() local t = { label="edit path", pno=self.model.pno, vno=self.model.vno, primary=self.primary, original=self.obj:clone(), final=self.obj:clone(), } t.final:setShape(self.shape) t.final:setMatrix(ipe.Matrix()) -- already in shape t.undo = function (t, doc) doc[t.pno]:replace(t.primary, t.original) end t.redo = function (t, doc) doc[t.pno]:replace(t.primary, t.final) end self.model:register(t) end function EDITTOOL:key(text, modifiers) -- print("EditTool Key:", text) if text == "\027" then -- Esc self.model.ui:finishTool() return true elseif text == "\026" and modifiers.control then -- Ctrl+Z self:action_undo() self:setShapeMarks() self.model.ui:update(false) -- update tool return true elseif text == " " then -- Space: accept edit self.moving = false self:acceptEdit() self.model.ui:finishTool() return true else -- not consumed return false end end ---------------------------------------------------------------------- function MODEL:action_edit_path(prim, obj) EDITTOOL:new(self, prim, obj) end ---------------------------------------------------------------------- local function flip(sub) sub[1], sub[2] = sub[2], sub[1] sub.flip = not sub.flip end local function findPartner(l, src, beg) local v = l[src][2] while beg <= #l do local w1 = l[beg][1] if (v - w1):sqLen() < prefs.join_threshold then return beg end local w2 = l[beg][2] if (v - w2):sqLen() < prefs.join_threshold then flip(l[beg]) return beg end beg = beg + 1 end return nil end local function reverse_segment(seg) local rseg = { type = seg.type } for i=#seg,1,-1 do rseg[#rseg + 1] = seg[i] -- copy control points in reverse order end if rseg.type == "arc" then -- need to do something special local alpha, beta = seg.arc:angles() rseg.arc = ipe.Arc(seg.arc:matrix() * ipe.Matrix(1, 0, 0, -1), beta, alpha) end return rseg end function MODEL:saction_join() local p = self:page() -- check that all objects consist of open subpaths only local l = {} for i,obj,sel,lay in p:objects() do if sel then if obj:type() ~= "path" then self:warning("Selection contains objects that are not paths.") return end local shape = obj:shape() transformShape(obj:matrix(), shape) for _,sp in ipairs(shape) do if sp.type ~= "curve" or sp.closed then self:warning("A selected object does not consist of open curves.") return end l[#l + 1] = { sp=sp, sp[1][1], sp[#sp][#sp[#sp]] } end end end if #l < 2 then self.ui:explain("only one path, nothing to join") return end local found_endpoint = false -- match up endpoints if not findPartner(l, 1, 2) then -- not found, flip l[1] and try again flip(l[1]) end local i = 1 while i < #l do -- invariant: l[1] .. l[i] form a chain local j = findPartner(l, i, i+1) if not j then if found_endpoint then self:warning("Cannot join paths", "Unable to join paths to a single curve") return end found_endpoint = true -- i is the end of the joined curve local a = 1 local b = i while a < b do -- flip a and b and reverse them l[a], l[b] = l[b], l[a] flip(l[a]); flip(l[b]) a = a + 1; b = b - 1 end else -- flip i+1 and j if j ~= i+1 then l[i+1], l[j] = l[j], l[i+1] end i = i + 1 end end -- now have a chain local nsp = { type = "curve", closed = false } for _, sp in ipairs(l) do if sp.flip then for i=#sp.sp,1,-1 do nsp[#nsp + 1] = reverse_segment(sp.sp[i]) -- because of rounding errors: if #nsp > 1 then nsp[#nsp][1] = nsp[#nsp - 1][#nsp[#nsp - 1]] end end else for i=1,#sp.sp do nsp[#nsp + 1] = sp.sp[i] -- because of rounding errors: if #nsp > 1 then nsp[#nsp][1] = nsp[#nsp - 1][#nsp[#nsp - 1]] end end end end -- check if it is closed if (nsp[1][1] - nsp[#nsp][#nsp[#nsp]]):sqLen() < prefs.join_threshold then nsp.closed = true if nsp[#nsp].type == "segment" then table.remove(nsp) end end local prim = p:primarySelection() local obj = p[prim]:clone() obj:setMatrix( ipe.Matrix() ) obj:setShape( { nsp } ) local t = { label = "join paths", pno = self.pno, vno = self.vno, selection = self:selection(), original = p:clone(), undo = revertOriginal, object = obj, layer = p:active(self.vno), } t.redo = function (t, doc) local p = doc[t.pno] for i = #t.selection,1,-1 do p:remove(t.selection[i]) end p:insert(nil, t.object, 1, t.layer) end self:register(t) end ---------------------------------------------------------------------- function MODEL:saction_compose() local p = self:page() local prim = p:primarySelection() local supershape = {} for i,obj,sel,lay in p:objects() do if sel then if obj:type() ~= "path" then self:warning("Cannot compose objects", "One of the selected objects is not a path object") return end local shape = obj:shape() if i ~= prim then transformShape(obj:matrix(), shape) transformShape(p[prim]:matrix():inverse(), shape) end for _,path in ipairs(shape) do supershape[#supershape + 1] = path end end end local obj = p[prim]:clone() obj:setShape(supershape) local t = { label = "compose paths", pno = self.pno, vno = self.vno, selection = self:selection(), original = p:clone(), undo = revertOriginal, object = obj, layer = p:active(self.vno), } t.redo = function (t, doc) local p = doc[t.pno] for i = #t.selection,1,-1 do p:remove(t.selection[i]) end p:insert(nil, t.object, 1, t.layer) end self:register(t) end ---------------------------------------------------------------------- function MODEL:saction_decompose() local p = self:page() local prim = p:primarySelection() if p[prim]:type() ~= "path" then self:warning("Cannot decompose objects", "Primary selection is not a path object") return end local shape = p[prim]:shape() if #shape <= 1 then self:warning("Cannot decompose objects", "Path object has only one subpath") return end transformShape(p[prim]:matrix(), shape) local objects = {} for _,path in ipairs(shape) do objects[#objects + 1] = ipe.Path(self.attributes, { path }) end local t = { label = "decompose path", pno = self.pno, vno = self.vno, primary = prim, original = p:clone(), undo = revertOriginal, objects = objects, layer = p:active(self.vno), } t.redo = function (t, doc) local p = doc[t.pno] p:remove(t.primary) for _,obj in ipairs(t.objects) do p:insert(nil, obj, 2, t.layer) end p:ensurePrimarySelection() end p:deselectAll() self:register(t) end ---------------------------------------------------------------------- ipe-7.2.13/src/ipe/lua/prefs.lua0000644000175000017500000003155313561570220016212 0ustar otfriedotfried---------------------------------------------------------------------- -- Ipe preference settings ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] local home = os.getenv("HOME") prefs = {} -- List of stylesheets that are added to newly created docs. Without -- a full path, stylesheets are searched for in the standard style -- directory. prefs.styles = { "basic" } -- The TeX engine for new documents -- Possible values are "default", "pdftex", "xetex", and "luatex" prefs.tex_engine = "default" -- URL for a cloud service that provides Latex compilation prefs.latex_service_url = "https://latexonline.cc/compile" -- Interval for autosaving in seconds -- set to nil to disable autosaving prefs.autosave_interval = 600 -- 10 minutes -- Filename for autosaving -- can contain '%s' for the filename of the current file -- can use 'home' for the user's home directory -- prefs.autosave_filename = home .. "/autosave.ipe" if config.platform == "win" then prefs.autosave_filename = config.documents .. "\\%s.autosave" else prefs.autosave_filename = home .. "/%s.autosave" end -- Should Ipe show the Developer menu -- (only useful if you develop ipelets or want to customize Ipe) prefs.developer = false -- Should Ipe terminate when the last window was closed? -- (Currently only on OS X) prefs.terminate_on_close = true -- Enable continuous spell-checking in text fields by default? -- (Currently only on OS X) prefs.spell_check = true -- External editor for editing text objects -- must contain '%s' for the temporary filename -- set this to nil to hide the "Editor" button on text dialogs if os.getenv("EDITOR") then prefs.external_editor = os.getenv("EDITOR") .. " %s" else if config.platform == "win" then prefs.external_editor = "notepad.exe %s" elseif config.platform == "apple" then prefs.external_editor = "open -W -n -e %s" else -- prefs.external_editor = "xed %s" -- prefs.external_editor = "emacsclient %s" prefs.external_editor = nil end end -- The name of the temporary textfile where Ipe will store text to be -- edited with an external editor. If set to nil, the Lua function -- os.tmpname() will be used to create a unique name. if config.platform == "win" then prefs.editable_textfile = config.latexdir .. "/temp.txt" else prefs.editable_textfile = nil end if config.platform == "apple" then prefs.delete_key = "\8" else prefs.delete_key = "\127" end -- Where the tools should be placed (left or right) -- and which ones should be displayed on start-up -- tools_placement is only used with Qt toolkit prefs.tools_placement = { properties = "left", bookmarks = "right", notes = "right", layers = "left" } prefs.tools_visible = { properties = true, bookmarks = false, notes = false, layers = true } -- initial ordering of the toolbars (windows only) prefs.toolbar_order = { "snap", "grid", "angle", "edit", "mode" } -- Should LaTeX be run automatically every time text has changed? prefs.auto_run_latex = true -- Should the external editor be called automatically? prefs.auto_external_editor = nil -- Should closing the external editor immediately close the editing dialog? prefs.editor_closes_dialog = nil -- If the user interface is too small, scale it here (Windows and Qt only) -- 100 is the original size, 150 is 50% larger -- On Windows 10, the system dpi is used automatically if left at 100. prefs.ui_scale = 100 -- The following influences the size of the toolbar buttons prefs.toolbar_scale = 100 -- Minimum size of dialog window for creating/editing text objects prefs.editor_size = { 0, 0 } -- Width of Notes and Bookmarks tools (Windows only) prefs.width_notes_bookmarks = 200 -- Size of main window at startup prefs.window_size = { 1080, 600 } -- Size of Latex error message window prefs.latexlog_size = { 800, 600 } -- Size of page sorter window prefs.page_sorter_size = { 960, 600 } -- Width of page thumbnails (height is computed automatically) prefs.thumbnail_width = 200 -- Canvas customization: prefs.canvas_style = { paper_color = { r = 1.0, g = 1.0, b = 1.0 }, -- white -- paper_color = { r = 1.0, g = 1.0, b = 0.5 } -- classic Ipe 6 yellow -- color of the primary selection: primary_color = { r = 1.0, g = 0.0, b = 0.0 }, -- color of the secondary selection: secondary_color = { r = 1.0, g = 0.0, b = 1.0 }, -- classic grid uses dots instead of lines classic_grid = false, -- line width of grid lines -- if classic_grid is true, then thin_grid_lines is size of grid dots thin_grid_line = 0.1, thick_grid_line = 0.3, -- steps indicate multiples of grid distance where grid lines are drawn thin_step = 1, thick_step = 4, -- e.g. try this: thin_step = 2, thick_step = 5 } -- Snap modes active when Ipe starts: prefs.snap = { vertex = false, ctrlpoints = false, boundary = false, intersection = false, grid = true, angle = false, autoangle = false } -- UI settings when Ipe starts prefs.initial = { grid_size = 16, -- points angle_size = 45, -- degrees grid_visible = true, } -- Attributes set when Ipe starts prefs.initial_attributes = { pathmode = "stroked", stroke = "black", fill = "white", pen = "normal", dashstyle = "normal", farrowshape = "arrow/normal(spx)", rarrowshape = "arrow/normal(spx)", farrowsize = "normal", rarrowsize = "normal", farrow = false, rarrow = false, symbolsize = "normal", textsize = "normal", textstyle = "normal", transformabletext = false, horizontalalignment = "left", verticalalignment = "baseline", pinned = "none", transformations = "affine", linejoin = "normal", linecap = "normal", fillrule = "normal", markshape = "mark/disk(sx)", tiling = "normal", gradient = "normal", opacity = "opaque", strokeopacity = "opaque", } -- Resolution settings -- When you select "normal size" in Ipe, this is the pixels -- per inch you want to see. prefs.normal_resolution = 72 -- Maximum distance in pixels selecting/snapping prefs.select_distance = 36 prefs.snap_distance = 16 -- When transforming objects, if currently select object is further than -- this distance, the closest object is selected instead prefs.close_distance = 48 -- Zoom factors, minimal and maximal possible zoom prefs.zoom_factor = 1.3 prefs.min_zoom = 0.1 prefs.max_zoom = 100 ---------------------------------------------------------------------- -- The following settings determine what the scroll wheel on a mouse or a -- two-finger pan gesture on a touchpad/trackpad do. -- There are two sets of settings: "trackpad_scroll" applies to trackpads under OSX, -- "scroll" applies in all other cases (including external mice in OSX). -- When pan is true, the gesture moves (pans) the canvas around, and -- you can control the speed of panning with pixel_per_degree. -- The direction of the movement is determined by direction.x and direction.y (1 or -1). -- When pan is false, the vertical scroll movement is used to change the zoom level. -- You can control the zoom speed using zoom_per_degree. -- If you want to reverse the direction of zooming, change -- zoom_per_degree to something smaller than one, e.g. 0.9827 prefs.scroll = { pan = true, pixel_per_degree = 2, zoom_per_degree = 1.0176, direction = { x=1, y=1 } } prefs.trackpad_scroll = { pan = true, pixel_per_degree = 2, zoom_per_degree = 1.0176, direction = { x=1, y=1 } } ---------------------------------------------------------------------- -- How close do two vertices need to be to be considered the same -- in the "Join paths" operation? prefs.join_threshold = 1e-6 -- If set to true, then whenever the user edits the title of a page, -- the check box "section: use title" is checked automatically. prefs.automatic_use_title = false -- How to start browser to show Ipe manual: -- (not used with Windows or Cocoa toolkit) prefs.browser = "xdg-open %s" -- On Linux, there are some other options you can try if xdg-open -- doesn't work on your desktop: -- Gnome 2: gnome-open -- Gnome 3: gvfs-open -- KDE: kde-open -- XFCE: exo-open -- Ubuntu/Debian: sensible-browser -- How to start onscreen keyboard if config.platform == "win" then prefs.keyboard = "tabtip.exe" elseif config.platform == "apple" then prefs.keyboard = "open -a KeyboardViewer -n" else -- On Linux, you could use: prefs.keyboard = "onboard &" prefs.keyboard = nil end -- Disable all snap modes in "ink" drawing mode? prefs.no_ink_snap = true ---------------------------------------------------------------------- -- -- The following settings can be used to tune the use of the pen in -- ink mode. It seems digitizers differ a lot, here you can adapt Ipe -- to yours. -- -- If your digitizer generates lots of pen move events, set -- ink_min_movement to avoid making thousands of tiny ink segments -- (start with a value like 0.2). -- -- If there is a lot of noise in pen recognition, try setting -- ink_smoothing to a positive value k (smoothing is then performed -- over 2k+1 samples). Try 3, for instance. -- -- After a complete ink stroke has been drawn, Ipe simplifies it to -- remove excess vertices, by computing a path with the minimal number -- of vertices that differs by at most ink_tolerance. -- -- Ink strokes that are very short (like a dot on an i) tend to appear -- too small. Use ink_dot_length and ink_dot_wider to enlarge them. -- -- Finally, you can set ink_spline to have your ink strokes converted -- to a spline (rather than a polygonal curve). -- ---------------------------------------------------------------------- -- Minimal distance for movement to update ink stroke prefs.ink_min_movement = 0 -- To smooth ink strokes, perform sliding average over how many samples? prefs.ink_smoothing = 0 -- When ink stroke is simplified, what is the tolerance? prefs.ink_tolerance = 0.3 -- Threshold for considering an ink stroke a tap with little movement: prefs.ink_dot_length = 10.0 -- When user taps the screen in ink mode with no or little movement, -- how much should the pen width be enlarged? -- nil means use current pen width prefs.ink_dot_wider = 2.0 -- Turn ink strokes into splines? prefs.ink_spline = false ---------------------------------------------------------------------- -- Auto-exporting when document is being saved -- If this is set, then every time you save in xml format, say to -- mydoc.ipe, the same document is EXPORTED to mydoc.pdf. -- Careful: if mydoc.pdf exists, it is silently overwritten. -- mydoc.pdf cannot be opened by Ipe (it is an exported copy). prefs.auto_export_to_pdf = false ---------------------------------------------------------------------- -- Extended properties menu, perhaps useful for tablets: prefs.tablet_menu = false -- format string for the coordinates in the status bar -- (x, unit, y, unit) -- prefs.coordinates_format = "%g%s, %g%s" prefs.coordinates_format = "(%7.3f%s, %7.3f%s)" -- possible scale factors for coordinates output -- must be integers. -5 means "5:1", +5 means "1:5" prefs.scale_factors = { -100, -5, 10, 100, 1000, 10000 } -- Default directory for "Save as" dialog, when -- the current document does not have a filename -- (or the filename is not absolute) if config.platform == "win" then -- Another reasonable setting: config.desktop prefs.save_as_directory = config.documents else -- If you use Ipe from the commandline, "." is the right value. -- Otherwise, you could use the home directory prefs.save_as_directory = "." -- prefs.save_as_directory = home end -- Pattern for lists of filenames -- The separator is a semicolon on Windows, a colon otherwise if config.platform == "win" then prefs.fsep = "\\" prefs.fname_pattern = "[^;]+" prefs.dir_pattern = "^(.+)\\[^\\]+" prefs.basename_pattern = "\\([^\\]+)$" else prefs.fsep = "/" prefs.fname_pattern = "[^:]+" prefs.dir_pattern = "^(.+)/[^/]+" prefs.basename_pattern = "/([^/]+)$" end ---------------------------------------------------------------------- ipe-7.2.13/src/ipe/lua/mouse.lua0000644000175000017500000000426613561570220016224 0ustar otfriedotfried---------------------------------------------------------------------- -- Ipe mouse buttons ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] -- Available actions are: -- "select" -- "translate", "rotate", "stretch", -- "scale" (like "stretch" with Shift) -- "pan" -- "menu" (opens context menu) -- "shredder" (erases object closest to mouse) -- or write a Lua function with arguments (model, modifiers) -- left and left_shift cannot be remapped -- More than two modifiers are possible in the order -- shift_control_alt_meta -- e.g. left_shift_meta = "rotate" -- If your mouse has additional buttons, then you can also use -- button8, button9, and button10. -- (It seems other buttons are not passed through by Qt.) mouse = { left_alt = "translate", left_control = "select", left_shift_control = "select", middle = "pan", right = "menu", right_alt = "rotate", right_control = "stretch", right_shift_control = "scale", right_shift = "pan", button8 = "shredder", button10 = "translate", } ---------------------------------------------------------------------- ipe-7.2.13/src/ipe/lua/tools.lua0000644000175000017500000013752113561570220016235 0ustar otfriedotfried--[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] ---------------------------------------------------------------------- -- tools.lua ---------------------------------------------------------------------- function externalEditor(d, field) local text = d:get(field) local fname = os.tmpname() if prefs.editable_textfile then fname = prefs.editable_textfile end local f = io.open(fname, "w") f:write(text) f:close() ipeui.waitDialog(d, string.format(prefs.external_editor, fname)) f = io.open(fname, "r") text = f:read("*all") f:close() os.remove(fname) d:set(field, text) if prefs.editor_closes_dialog and not prefs.auto_external_editor then d:accept(true) end end function addEditorField(d, field) if prefs.external_editor then d:addButton("editor", "&Editor", function (d) externalEditor(d, field) end) end end ---------------------------------------------------------------------- local function circleshape(center, radius) return { type="ellipse"; ipe.Matrix(radius, 0, 0, radius, center.x, center.y) } end local function segmentshape(v1, v2) return { type="curve", closed=false; { type="segment"; v1, v2 } } end local function boxshape(v1, v2) return { type="curve", closed=true; { type="segment"; v1, V(v1.x, v2.y) }, { type="segment"; V(v1.x, v2.y), v2 }, { type="segment"; v2, V(v2.x, v1.y) } } end local function arcshape(center, radius, alpha, beta) local a = ipe.Arc(ipe.Matrix(radius, 0, 0, radius, center.x, center.y), alpha, beta) local v1 = center + radius * ipe.Direction(alpha) local v2 = center + radius * ipe.Direction(beta) return { type="curve", closed=false; { type="arc", arc=a; v1, v2 } } end local function rarcshape(center, radius, alpha, beta) local a = ipe.Arc(ipe.Matrix(radius, 0, 0, -radius, center.x, center.y), alpha, beta) local v1 = center + radius * ipe.Direction(alpha) local v2 = center + radius * ipe.Direction(beta) return { type="curve", closed=false; { type="arc", arc=a; v1, v2 } } end ---------------------------------------------------------------------- local VERTEX = 1 local SPLINE = 2 local ARC = 3 LINESTOOL = {} LINESTOOL.__index = LINESTOOL -- mode is one of "lines", "polygons", "splines" function LINESTOOL:new(model, mode) local tool = {} setmetatable(tool, LINESTOOL) tool.model = model tool.mode = mode local v = model.ui:pos() tool.v = { v, v } model.ui:setAutoOrigin(v) if mode == "splines" then tool.t = { VERTEX, SPLINE } else tool.t = { VERTEX, VERTEX } end model.ui:shapeTool(tool) tool.setColor(1.0, 0, 0) tool.setSnapping(true, true) return tool end function LINESTOOL:last() return self.t[#self.t] end function LINESTOOL:has_segs(count) if #self.t < count then return false end local result = true for i = #self.t - count + 1,#self.t do if self.t[i] ~= VERTEX then return false end end return true end local function compute_arc(p0, pmid, p1) if p0 == p1 then return { type="segment", p0, p1 } end local l1 = ipe.Line(p0, (pmid- p0):normalized()) local l2 = ipe.Line(p0, l1:normal()) local bi1 = ipe.Bisector(p0, p1) local center = l2:intersects(bi1) local side = l1:side(p1) if side == 0.0 or not center then return { type="segment", p0, p1 } end local u = p0 - center local alpha = side * u:angle() local beta = side * ipe.normalizeAngle((p1 - center):angle(), alpha) local radius = u:len() local m = { radius, 0, 0, side * radius, center.x, center.y } return { type = "arc", p0, p1, arc = ipe.Arc(ipe.Matrix(m), alpha, beta) } end -- compute orientation of tangent to previous segment at its final point function LINESTOOL:compute_orientation() if self.t[#self.t - 2] ~= ARC then return (self.v[#self.v - 1] - self.v[#self.v - 2]):angle() else -- only arc needs special handling local arc = compute_arc(self.v[#self.v - 3], self.v[#self.v - 2], self.v[#self.v - 1]) if arc.type == "arc" then local alpha, beta = arc.arc:angles() local dir = ipe.Direction(beta + math.pi / 2) return (arc.arc:matrix():linear() * dir):angle() else return (self.v[#self.v - 1] - self.v[#self.v - 3]):angle() end end end function LINESTOOL:compute() self.shape = { type="curve", closed=(self.mode == "polygons") } local i = 2 while i <= #self.v do -- invariant: t[i-1] == VERTEX local seg if self.t[i] == VERTEX then seg = { type="segment", self.v[i-1], self.v[i] } i = i + 1 elseif self.t[i] == SPLINE then local j = i while j <= #self.v and self.t[j] == SPLINE do j = j + 1 end if j > #self.v then j = #self.v end seg = { type="spline" } for k = i-1,j do seg[#seg+1] = self.v[k] end i = j + 1 elseif self.t[i] == ARC then seg = compute_arc(self.v[i-1], self.v[i], self.v[i+1]) i = i + 2 end self.shape[#self.shape + 1] = seg end self.setShape( { self.shape } ) end function LINESTOOL:mouseButton(button, modifiers, press) if not press then return end local v = self.model.ui:pos() self.v[#self.v] = v if button == 0x81 then -- double click -- the first click already added a vertex, do not use second one if #self.v == 2 then return end table.remove(self.v) table.remove(self.t) button = 2 end if modifiers.control and button == 1 then button = 2 end if button == 2 then if self:last() == SPLINE then self.t[#self.t] = VERTEX end self:compute() self.model.ui:finishTool() local obj = ipe.Path(self.model.attributes, { self.shape }, true) -- if it is just a point, force line cap to round if #self.shape == 1 and self.shape[1].type == "segment" and self.shape[1][1] == self.shape[1][2] then obj:set("linecap", "round") end self.model:creation("create path", obj) return end self.v[#self.v + 1] = v self.model.ui:setAutoOrigin(v) if self:last() == SPLINE then local typ = modifiers.shift and VERTEX or SPLINE self.t[#self.t] = typ self.t[#self.t + 1] = typ else self.t[#self.t + 1] = VERTEX end self:compute() self.model.ui:update(false) -- update tool self:explain() end function LINESTOOL:mouseMove() self.v[#self.v] = self.model.ui:pos() self:compute() self.model.ui:update(false) -- update tool self:explain() end function LINESTOOL:explain() local s if self:last() == SPLINE then s = ("Left: add ctrl point | Shift+Left: switch to line mode" .. " | Del: delete ctrl point") else s = "Left: add vtx | Del: delete vtx" end s = s .. " | Right, Ctrl-Left, or Double-Left: final vtx" if self:has_segs(2) then s = s .. " | " .. shortcuts_linestool.spline .. ": spline mode" end if self:has_segs(3) then s = s .. " | " .. shortcuts_linestool.arc .. ": circle arc" end if #self.v > 2 and self.t[#self.t - 1] == VERTEX then s = s .. " | " .. shortcuts_linestool.set_axis ..": set axis" end self.model.ui:explain(s, 0) end function LINESTOOL:key(text, modifiers) if text == prefs.delete_key then -- Delete if #self.v > 2 then table.remove(self.v) table.remove(self.t) if self:last() == ARC then self.t[#self.t] = VERTEX end self:compute() self.model.ui:update(false) self:explain() else self.model.ui:finishTool() end return true elseif text == "\027" then self.model.ui:finishTool() return true elseif self:has_segs(2) and text == shortcuts_linestool.spline then self.t[#self.t] = SPLINE self:compute() self.model.ui:update(false) self:explain() return true elseif self:has_segs(3) and text == shortcuts_linestool.arc then self.t[#self.t - 1] = ARC self:compute() self.model.ui:update(false) self:explain() return true elseif #self.v > 2 and self.t[#self.t - 1] == VERTEX and text == shortcuts_linestool.set_axis then -- set axis self.model.snap.with_axes = true self.model.ui:setActionState("show_axes", self.model.snap.with_axes) self.model.snap.snapangle = true self.model.snap.origin = self.v[#self.v - 1] self.model.snap.orientation = self:compute_orientation() self.model:setSnap() self.model.ui:setActionState("snapangle", true) self.model.ui:update(true) -- redraw coordinate system self:explain() return true else return false end end ---------------------------------------------------------------------- BOXTOOL = {} BOXTOOL.__index = BOXTOOL function BOXTOOL:new(model, square, mode) local tool = {} setmetatable(tool, BOXTOOL) tool.model = model tool.mode = mode tool.square = square local v = model.ui:pos() tool.v = { v, v } model.ui:shapeTool(tool) tool.cur = 2 tool.setColor(1.0, 0, 0) return tool end function BOXTOOL:compute() self.v[self.cur] = self.model.ui:pos() local d = self.v[2] - self.v[1] local sign = V(d.x > 0 and 1 or -1, d.y > 0 and 1 or -1) local dd = math.max(math.abs(d.x), math.abs(d.y)) if self.mode == "rectangles1" or self.mode == "rectangles2" then if self.square then self.v[2] = self.v[1] + dd * sign end if self.mode == "rectangles1" then self.shape = boxshape(self.v[1], self.v[2]) else local u = self.v[2] - self.v[1] self.shape = boxshape(self.v[1] - u, self.v[2]) end elseif self.mode == "rectangles3" and self.square then local u = self.v[2] - self.v[1] local lu = V(-u.y, u.x) self.shape = { type="curve", closed=true; { type="segment"; self.v[1], self.v[2] }, { type="segment"; self.v[2], self.v[2] + lu }, { type="segment"; self.v[2] + lu, self.v[1] + lu } } else if self.cur == 2 and self.square then -- make first-segment axis-parallel if math.abs(d.x) > math.abs(d.y) then self.v[2] = self.v[1] + V(sign.x * dd, 0) else self.v[2] = self.v[1] + V(0, sign.y * dd) end end if self.cur == 2 then self.shape = segmentshape(self.v[1], self.v[2]) else if self.v[2] ~= self.v[1] and self.v[3] ~= self.v[2] and self.mode == "rectangles3" then local l1 = ipe.LineThrough(self.v[1], self.v[2]) local l2 = ipe.Line(self.v[2], l1:normal()) self.v[3] = l2:project(self.v[3]) end local u = self.v[3] - self.v[2] self.shape = { type="curve", closed=true; { type="segment"; self.v[1], self.v[2] }, { type="segment"; self.v[2], self.v[3] }, { type="segment"; self.v[3], self.v[1] + u } } end end end function BOXTOOL:mouseButton(button, modifiers, press) if not press then return end self:compute() if self.cur == 2 and (self.mode == "parallelogram" or (self.mode == "rectangles3" and not self.square)) then self.cur = 3 self.v[3] = self.v[2] return end self.model.ui:finishTool() local obj = ipe.Path(self.model.attributes, { self.shape }) self.model:creation("create box", obj) end function BOXTOOL:mouseMove() self:compute() self.setShape( { self.shape } ) self.model.ui:update(false) -- update tool end function BOXTOOL:key(text, modifiers) if text == "\027" then self.model.ui:finishTool() return true else return false end end ---------------------------------------------------------------------- SPLINEGONTOOL = {} SPLINEGONTOOL.__index = SPLINEGONTOOL function SPLINEGONTOOL:new(model) local tool = {} setmetatable(tool, SPLINEGONTOOL) tool.model = model local v = model.ui:pos() tool.v = { v, v } model.ui:shapeTool(tool) tool.setColor(1.0, 0, 0) return tool end function SPLINEGONTOOL:compute(update) if #self.v == 2 then self.shape = segmentshape(self.v[1], self.v[2]) else self.shape = { type="closedspline" } for _,v in ipairs(self.v) do self.shape[#self.shape + 1] = v end end if update then self.setShape( { self.shape } ) self.model.ui:update(false) -- update tool end end function SPLINEGONTOOL:explain() local s = "Left: Add vertex " .. "| Right, ctrl-left, or double-left: Add final vertex" .. "| Del: Delete vertex" self.model.ui:explain(s, 0) end function SPLINEGONTOOL:mouseButton(button, modifiers, press) if not press then return end local v = self.model.ui:pos() self.v[#self.v] = v if button == 0x81 then -- double click -- the first click already added a vertex, do not use second one if #self.v == 2 then return end table.remove(self.v) button = 2 end if modifiers.control and button == 1 then button = 2 end if button == 2 then self:compute(false) self.model.ui:finishTool() local obj = ipe.Path(self.model.attributes, { self.shape }) self.model:creation("create splinegon", obj) return end self.v[#self.v + 1] = v self:compute(true) self:explain() end function SPLINEGONTOOL:mouseMove() self.v[#self.v] = self.model.ui:pos() self:compute(true) end function SPLINEGONTOOL:key(text, modifiers) if text == prefs.delete_key then -- Delete if #self.v > 2 then table.remove(self.v) self:compute(true) self:explain() else self.model.ui:finishTool() end return true elseif text == "\027" then self.model.ui:finishTool() return true else self:explain() return false end end ---------------------------------------------------------------------- CIRCLETOOL = {} CIRCLETOOL.__index = CIRCLETOOL function CIRCLETOOL:new(model, mode) local tool = {} setmetatable(tool, CIRCLETOOL) tool.model = model tool.mode = mode local v = model.ui:pos() tool.v = { v, v, v } tool.cur = 2 model.ui:shapeTool(tool) tool.setColor(1.0, 0, 0) return tool end function CIRCLETOOL:compute() if self.mode == "circle1" then self.shape = circleshape(self.v[1], (self.v[2] - self.v[1]):len()) elseif self.mode == "circle2" then self.shape = circleshape(0.5 * (self.v[1] + self.v[2]), (self.v[2] - self.v[1]):len() / 2.0) elseif self.mode == "circle3" then if self.cur == 2 or self.v[3] == self.v[2] then self.shape = circleshape(0.5 * (self.v[1] + self.v[2]), (self.v[2] - self.v[1]):len() / 2.0) else local l1 = ipe.LineThrough(self.v[1], self.v[2]) if math.abs(l1:side(self.v[3])) < 1e-9 then self.shape = segmentshape(self.v[1], self.v[2]) else local l2 = ipe.LineThrough(self.v[2], self.v[3]) local bi1 = ipe.Bisector(self.v[1], self.v[2]) local bi2 = ipe.Bisector(self.v[2], self.v[3]) local center = bi1:intersects(bi2) self.shape = circleshape(center, (self.v[1] - center):len()) end end end end function CIRCLETOOL:mouseButton(button, modifiers, press) if not press then return end local v = self.model.ui:pos() -- refuse point identical to previous if v == self.v[self.cur - 1] then return end self.v[self.cur] = v self:compute() if self.cur == 3 or (self.mode ~= "circle3" and self.cur == 2) then self.model.ui:finishTool() local obj = ipe.Path(self.model.attributes, { self.shape }) self.model:creation("create circle", obj) else self.cur = self.cur + 1 self.model.ui:update(false) end end function CIRCLETOOL:mouseMove() self.v[self.cur] = self.model.ui:pos() self:compute() self.setShape({ self.shape }) self.model.ui:update(false) -- update tool end function CIRCLETOOL:key(text, modifiers) if text == "\027" then self.model.ui:finishTool() return true else return false end end ---------------------------------------------------------------------- ARCTOOL = {} ARCTOOL.__index = ARCTOOL function ARCTOOL:new(model, mode) local tool = {} setmetatable(tool, ARCTOOL) tool.model = model tool.mode = mode local v = model.ui:pos() tool.v = { v, v, v } tool.cur = 2 model.ui:shapeTool(tool) tool.setColor(1.0, 0, 0) return tool end function ARCTOOL:compute() local u = self.v[2] - self.v[1] if self.cur == 2 then if self.mode == "arc3" then self.shape = circleshape(0.5 * (self.v[1] + self.v[2]), u:len() / 2.0) else self.shape = circleshape(self.v[1], u:len()) end return end local alpha = u:angle() local beta = (self.v[3] - self.v[1]):angle() if self.mode == "arc1" then self.shape = arcshape(self.v[1], u:len(), alpha, beta) elseif self.mode == "arc2" then self.shape = rarcshape(self.v[1], u:len(), alpha, beta) else local l1 = ipe.LineThrough(self.v[1], self.v[2]) if math.abs(l1:distance(self.v[3])) < 1e-9 or self.v[3] == self.v[2] then self.shape = segmentshape(self.v[1], self.v[3]) else local l2 = ipe.LineThrough(self.v[2], self.v[3]) local bi1 = ipe.Line(0.5 * (self.v[1] + self.v[2]), l1:normal()) local bi2 = ipe.Line(0.5 * (self.v[2] + self.v[3]), l2:normal()) local center = bi1:intersects(bi2) u = self.v[1] - center alpha = u:angle() beta = ipe.normalizeAngle((self.v[2] - center):angle(), alpha) local gamma = ipe.normalizeAngle((self.v[3] - center):angle(), alpha) if gamma > beta then self.shape = arcshape(center, u:len(), alpha, gamma) else self.shape = rarcshape(center, u:len(), alpha, gamma) end end end end function ARCTOOL:mouseButton(button, modifiers, press) if not press then return end local v = self.model.ui:pos() -- refuse point identical to previous if v == self.v[self.cur - 1] then return end self.v[self.cur] = v self:compute() if self.cur == 3 then self.model.ui:finishTool() local obj = ipe.Path(self.model.attributes, { self.shape }, true) self.model:creation("create arc", obj) else self.cur = self.cur + 1 self.model.ui:update(false) end end function ARCTOOL:mouseMove() self.v[self.cur] = self.model.ui:pos() self:compute() self.setShape({ self.shape }) self.model.ui:update(false) -- update tool end function ARCTOOL:key(text, modifiers) if text == "\027" then self.model.ui:finishTool() return true else return false end end ---------------------------------------------------------------------- local function path_len(points) local t = 0 for i=2,#points do t = t + (points[i] - points[i-1]):len() end return t end -- perform moving average local function smooth_path(v) local M = prefs.ink_smoothing local w = { v[1] } for i = 2,#v-1 do local p = V(0,0) for j = i-M, i+M do local q if j < 1 then q = v[1] elseif j > #v then q = v[#v] else q = v[i] end p = p + q end w[#w+1] = (1/(2*M+1)) * p end w[#w+1] = v[#v] return w end local function simplify_path(points, tolerance) local marked = {} marked[1] = true marked[#points] = true local stack = { { 1, #points } } -- mark points to keep while #stack > 0 do local pair = table.remove(stack) local first = pair[1] local last = pair[2] local max_dist = 0 local index = nil local seg = ipe.Segment(points[first], points[last]) for i = first + 1,last do local d = seg:distance(points[i]) if d > max_dist then index = i max_dist = d end end if max_dist > tolerance then marked[index] = true stack[#stack + 1] = { first, index } stack[#stack + 1] = { index, last } end end -- only use marked vertices local out = {} for i, point in ipairs(points) do if marked[i] then out[#out+1] = point end end return out end -- vector for control points around p2 local function tang(p1, p2, p3) return (p2-p1):normalized() + (p3 - p2):normalized() end -- first control point between p2 and p3 local function cp1(p1, p2, p3) local tangent = tang(p1, p2, p3):normalized() local vlen = (p3 - p2):len() / 3.0 return p2 + vlen * tangent end -- second control point between p2 and p3 local function cp2(p2, p3, p4) local tangent = tang(p2, p3, p4):normalized() local vlen = (p3 - p2):len() / 3.0 return p3 - vlen * tangent end local function compute_spline(w) local shape = { } if #w > 2 then local cp = cp2(w[1], w[2], w[3]) local seg = { w[1], cp, w[2] } seg.type = "spline" shape[1] = seg else local seg = { w[1], w[2] } seg.type = "segment" shape[1] = seg end for i = 2,#w-2 do local q1 = w[i-1] local q2 = w[i] local q3 = w[i+1] local q4 = w[i+2] local cpa = cp1(q1, q2, q3) local cpb = cp2(q2, q3, q4) local seg = { q2, cpa, cpb, q3} seg.type = "spline" shape[#shape + 1] = seg end if #w > 2 then local cp = cp1(w[#w-2], w[#w-1], w[#w]) local seg = { w[#w-1], cp, w[#w] } seg.type = "spline" shape[#shape + 1] = seg end return shape end ---------------------------------------------------------------------- INKTOOL = {} INKTOOL.__index = INKTOOL function INKTOOL:new(model) local tool = {} setmetatable(tool, INKTOOL) tool.model = model local v = model.ui:pos() tool.v = { v } -- print("make ink tool") model.ui:shapeTool(tool) local s = model.doc:sheets():find("color", model.attributes.stroke) tool.setColor(s.r, s.g, s.b) tool.w = model.doc:sheets():find("pen", model.attributes.pen) model.ui:setCursor(tool.w, s.r, s.g, s.b) return tool end function INKTOOL:compute(incremental) local v = self.v if incremental and #v > 2 then self.shape[#self.shape+1]={ type="segment", v[#v-1], v[#v]} else self.shape = { type="curve", closed=false } for i = 2, #v do self.shape[#self.shape + 1] = { type="segment", v[i-1], v[i] } end end self.setShape( { self.shape }, 0, self.w * self.model.ui:zoom()) end function INKTOOL:mouseButton(button, modifiers, press) if self.shape then self.v = smooth_path(self.v) self.v = simplify_path(self.v, prefs.ink_tolerance / self.model.ui:zoom()) else self.v = { self.v[1], self.v[1] } end if prefs.ink_spline then self.shape = compute_spline(self.v) self.shape.type = "curve" self.shape.closed = false else self:compute(false) end local obj = ipe.Path(self.model.attributes, { self.shape }) -- round linecaps are prettier for handwriting obj:set("linecap", "round") obj:set("linejoin", "round") if path_len(self.v) * self.model.ui:zoom() < prefs.ink_dot_length then -- pen was pressed and released with no or very little movement if prefs.ink_dot_wider then obj:set("pen", self.w * prefs.ink_dot_wider) end self.model:creation("create ink dot", obj) else self.model:creation("create ink path", obj) end self.model:page():deselectAll() -- ink isn't selected after creation self.model.ui:finishTool() end function INKTOOL:mouseMove() local v1 = self.v[#self.v] local v2 = self.model.ui:pos() if (v1-v2):len() * self.model.ui:zoom() > prefs.ink_min_movement then -- do not update if motion is too small self.v[#self.v + 1] = v2 self:compute(true) local r = ipe.Rect() local offset = V(self.w, self.w) r:add(v1) r:add(v2) r:add(r:bottomLeft() - offset) r:add(r:topRight() + offset) self.model.ui:update(r) -- update rectangle containing new segment end end function INKTOOL:key(text, modifiers) if text == "\027" then self.model.ui:finishTool() return true else return false end end ---------------------------------------------------------------------- function MODEL:shredObject() local bound = prefs.close_distance local pos = self.ui:unsnappedPos() local p = self:page() local closest for i,obj,sel,layer in p:objects() do if p:visible(self.vno, i) and not p:isLocked(layer) then local d = p:distance(i, pos, bound) if d < bound then closest = i; bound = d end end end if closest then local t = { label="shred object", pno = self.pno, vno = self.vno, num = closest, original=self:page():clone(), undo=revertOriginal, } t.redo = function (t, doc) local p = doc[t.pno] p:remove(t.num) p:ensurePrimarySelection() end self:register(t) else self.ui:explain("No object found to shred") end end ---------------------------------------------------------------------- function MODEL:createMark() local obj = ipe.Reference(self.attributes, self.attributes.markshape, self.ui:pos()) self:creation("create mark", obj) end ---------------------------------------------------------------------- function MODEL:createText(mode, pos, width, pinned) local prompt = "Enter Latex source" local stylekind = "labelstyle" local styleatt = self.attributes.labelstyle local explainer = "create text" if mode == "math" then prompt = "Enter Latex source for math formula" end if mode == "paragraph" then styleatt = self.attributes.textstyle stylekind = "textstyle" explainer = "create text paragraph" end local styles = self.doc:sheets():allNames(stylekind) local sizes = self.doc:sheets():allNames("textsize") local d = ipeui.Dialog(self.ui:win(), "Create text object") d:add("label", "label", { label=prompt }, 1, 1, 1, 2) d:add("style", "combo", styles, -1, 3) d:add("size", "combo", sizes, -1, 4) d:add("text", "text", { syntax="latex", focus=true, spell_check=prefs.spell_check }, 0, 1, 1, 4) addEditorField(d, "text") d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("row", 2, 1) d:setStretch("column", 2, 1) d:set("ignore-escape", true) local style = indexOf(styleatt, styles) if not style then style = indexOf("normal", styles) end local size = indexOf(self.attributes.textsize, sizes) if not size then size = indexOf("normal", sizes) end d:set("style", style) d:set("size", size) if mode == "math" then d:set("style", "math") d:setEnabled("style", false) end if prefs.auto_external_editor then externalEditor(d, "text") end if ((prefs.auto_external_editor and prefs.editor_closes_dialog) or d:execute(prefs.editor_size)) then local t = d:get("text") local style = styles[d:get("style")] local size = sizes[d:get("size")] local obj = ipe.Text(self.attributes, t, pos, width) obj:set("textsize", size) obj:set(stylekind, style) if pinned then obj:set("pinned", "horizontal") end self:creation(explainer, obj) self:autoRunLatex() end end ---------------------------------------------------------------------- function MODEL:action_insert_text_box() local layout = self.doc:sheets():find("layout") local p = self:page() local r = ipe.Rect() local m = ipe.Matrix() for i, obj, sel, layer in p:objects() do if p:visible(self.vno, i) and obj:type() == "text" then obj:addToBBox(r, m) end end local y = layout.framesize.y if not r:isEmpty() and r:bottom() < layout.framesize.y then y = r:bottom() - layout.paragraph_skip end self:createText("paragraph", ipe.Vector(0, y), layout.framesize.x, true) end ---------------------------------------------------------------------- PARAGRAPHTOOL = {} PARAGRAPHTOOL.__index = PARAGRAPHTOOL function PARAGRAPHTOOL:new(model) local tool = {} setmetatable(tool, PARAGRAPHTOOL) tool.model = model local v = model.ui:pos() tool.v = { v, v } model.ui:shapeTool(tool) tool.setColor(1.0, 0, 1.0) return tool end function PARAGRAPHTOOL:compute() self.v[2] = V(self.model.ui:pos().x, self.v[1].y - 20) self.shape = boxshape(self.v[1], self.v[2]) end function PARAGRAPHTOOL:mouseButton(button, modifiers, press) if not press then return end self:compute() self.model.ui:finishTool() local pos = V(math.min(self.v[1].x, self.v[2].x), self.v[1].y) local wid = math.abs(self.v[2].x - self.v[1].x) self.model:createText("paragraph", pos, wid) end function PARAGRAPHTOOL:mouseMove() self:compute() self.setShape( { self.shape } ) self.model.ui:update(false) -- update tool end function PARAGRAPHTOOL:key(text, modifiers) if text == "\027" then self.model.ui:finishTool() return true else return false end end ---------------------------------------------------------------------- local function collect_edges(p, box) local edges = {} for i, obj, sel, layer in p:objects() do if obj:type() == "path" then local shape = obj:shape() local m = obj:matrix() if #shape == 1 and shape[1].type == "curve" and shape[1].closed == false then local curve = shape[1] local head = curve[1][1] local seg = curve[#curve] local tail = seg[#seg] if box:contains(m * head) then edges[#edges + 1] = { obj=obj, head=true, objno=i } elseif box:contains(m * tail) then edges[#edges + 1] = { obj=obj, head=false, objno=i } end end end end return edges end ---------------------------------------------------------------------- GRAPHTOOL = {} GRAPHTOOL.__index = GRAPHTOOL local function findClosestVertex(model) local bound = prefs.close_distance local pos = model.ui:unsnappedPos() local p = model:page() local closest for i,obj,sel,layer in p:objects() do if p:visible(model.vno, i) and not p:isLocked(layer) then if obj:type() == "group" or obj:type() == "reference" or obj:type() == "text" then local d = p:distance(i, pos, bound) if d < bound then closest = i; bound = d end end end end if closest then -- deselect all, and select only closest object p:deselectAll() p:setSelect(closest, 1) return true else return p:hasSelection() end end function GRAPHTOOL:new(model) if not findClosestVertex(model) then return end local p = model:page() self.prim = p:primarySelection() local tool = {} setmetatable(tool, GRAPHTOOL) tool.model = model tool.orig = model.ui:pos() tool.box = p:bbox(self.prim) tool.edges = collect_edges(p, tool.box) model.ui:shapeTool(tool) tool.setColor(1.0, 0.0, 0.0) return tool end function GRAPHTOOL:compute() self.t = self.model.ui:pos() - self.orig self.shape = { boxshape(self.box:bottomLeft() + self.t, self.box:topRight() + self.t) } for i = 1,#self.edges do local obj = self.edges[i].obj local shape = obj:shape() transformShape(obj:matrix(), shape) local curve = shape[1] if self.edges[i].head then curve[1][1] = curve[1][1] + self.t else local seg = curve[#curve] seg[#seg] = seg[#seg] + self.t end self.shape[i+1] = curve end end function GRAPHTOOL:mouseMove() self:compute() self.setShape(self.shape) self.model.ui:update(false) -- update tool end local function apply_node_mode(t, doc) local p = doc[t.pno] p:transform(t.primary, ipe.Translation(t.translation)) for _,e in ipairs(t.edges) do local obj = p[e.objno] local shape = obj:shape() transformShape(obj:matrix(), shape) local curve = shape[1] if e.head then curve[1][1] = curve[1][1] + t.translation else local seg = curve[#curve] seg[#seg] = seg[#seg] + t.translation end p[e.objno]:setShape(shape) p[e.objno]:setMatrix(ipe.Matrix()) end end function GRAPHTOOL:mouseButton(button, modifiers, press) if press then return end self:compute() self.model.ui:finishTool() local edges = {} for i = 1,#self.edges do self.edges[i].obj = nil end local t = { label = "move graph vertex", pno = self.model.pno, vno = self.model.vno, primary = self.prim, original = self.model:page():clone(), translation = self.t, edges = self.edges, undo = revertOriginal, redo = apply_node_mode, } self.model:register(t) end function GRAPHTOOL:key(text, modifiers) if text == "\027" then self.model.ui:finishTool() return true else return false end end ---------------------------------------------------------------------- CHANGEWIDTHTOOL = {} CHANGEWIDTHTOOL.__index = CHANGEWIDTHTOOL function CHANGEWIDTHTOOL:new(model, prim, obj) local tool = {} setmetatable(tool, CHANGEWIDTHTOOL) tool.model = model tool.prim = prim tool.obj = obj tool.pos = obj:matrix() * obj:position() tool.wid = obj:get("width") model.ui:shapeTool(tool) tool.setColor(1.0, 0, 1.0) tool.setShape( { boxshape(tool.pos, tool.pos + V(tool.wid, -20)) } ) model.ui:update(false) -- update tool return tool end function CHANGEWIDTHTOOL:compute() local w = self.model.ui:pos() self.nwid = self.wid + (w.x - self.v.x) self.shape = boxshape(self.pos, self.pos + V(self.nwid, -20)) end function CHANGEWIDTHTOOL:mouseButton(button, modifiers, press) if press then if not self.v then self.v = self.model.ui:pos() end else self:compute() self.model.ui:finishTool() self.model:setAttributeOfPrimary(self.prim, "width", self.nwid) self.model:autoRunLatex() end end function CHANGEWIDTHTOOL:mouseMove() if self.v then self:compute() self.setShape( { self.shape } ) self.model.ui:update(false) -- update tool end end function CHANGEWIDTHTOOL:key(text, modifiers) if text == "\027" then self.model.ui:finishTool() return true else return false end end function MODEL:action_change_width() local p = self:page() local prim = p:primarySelection() if not prim or p[prim]:type() ~= "text" or not p[prim]:get("minipage") then self.ui:explain("no selection or not a minipage object") return end CHANGEWIDTHTOOL:new(self, prim, p[prim]) end ---------------------------------------------------------------------- function MODEL:startTransform(mode, withShift) self:updateCloseSelection(false) if mode == "stretch" and withShift then mode = "scale" end self.ui:transformTool(self:page(), self.vno, mode, withShift, function (m) self:transformation(mode, m) end) end function MODEL:startModeTool(modifiers) if self.mode == "select" then self.ui:selectTool(self:page(), self.vno, prefs.select_distance, modifiers.shift) elseif (self.mode == "translate" or self.mode == "stretch" or self.mode == "rotate" or self.mode == "shear") then self:startTransform(self.mode, modifiers.shift) elseif self.mode == "pan" then self.ui:panTool(self:page(), self.vno) elseif self.mode == "shredder" then self:shredObject() elseif self.mode == "graph" then GRAPHTOOL:new(self) elseif self.mode:sub(1,10) == "rectangles" or self.mode == "parallelogram" then BOXTOOL:new(self, modifiers.shift, self.mode) elseif self.mode == "splinegons" then SPLINEGONTOOL:new(self) elseif (self.mode == "lines" or self.mode == "polygons" or self.mode == "splines") then LINESTOOL:new(self, self.mode) elseif self.mode:sub(1,6) == "circle" then CIRCLETOOL:new(self, self.mode) elseif self.mode:sub(1,3) == "arc" then ARCTOOL:new(self, self.mode) elseif self.mode == "ink" then INKTOOL:new(self) elseif self.mode == "marks" then self:createMark() elseif self.mode == "label" or self.mode == "math" then self:createText(self.mode, self.ui:pos()) elseif self.mode == "paragraph" then PARAGRAPHTOOL:new(self) else print("start mode tool:", self.mode) end end local mouse_mappings = { select = function (m, mo) m.ui:selectTool(m:page(), m.vno, prefs.select_distance, mo.shift) end, translate = function (m, mo) m:startTransform("translate", mo.shift) end, rotate = function (m, mo) m:startTransform("rotate", mo.shift) end, stretch = function (m, mo) m:startTransform("stretch", mo.shift) end, scale = function (m, mo) m:startTransform("stretch", true) end, pan = function (m, mo) m.ui:panTool(m:page(), m.vno) end, menu = function (m, mo) m:propertiesPopup() end, shredder = function (m, mo) m:shredObject() end, } function MODEL:mouseButtonAction(button, modifiers) -- print("Mouse button", button, modifiers.alt, modifiers.control) if button == 0x81 then button = 1 end -- left double-click if button == 1 and not modifiers.alt and not modifiers.control and not modifiers.meta then self:startModeTool(modifiers) else local s = "" if button == 1 then s = "left" elseif button == 2 then s = "right" elseif button == 4 then s = "middle" elseif button == 8 then s = "button8" elseif button == 16 then s = "button9" elseif button == 0 then -- This is a hack because of the Qt limitation. -- It really means any other button. s = "button10" end if modifiers.shift then s = s .. "_shift" end if modifiers.control then s = s .. "_control" end if modifiers.alt then s = s .. "_alt" end if modifiers.meta then s = s .. "_meta" end if modifiers.command then s = s .. "_command" end local r = mouse[s] if type(r) == "string" then r = mouse_mappings[r] end if r then r(self, modifiers) else print("No mouse action defined for " .. s) end end end ---------------------------------------------------------------------- function apply_text_edit(d, data, run_latex) -- refuse to do anything with empty text if string.match(d:get("text"), "^%s*$") then return end if data.obj:text() == d:get("text") and (not data.size or data.obj:get("textsize") == data.sizes[d:get("size")]) and (not data.style or data.obj:get(data.stylekind) == data.styles[d:get("style")]) then return -- hasn't changed since last time end local model = data.model local final = data.obj:clone() final:setText(d:get("text")) if data.style then final:set(data.stylekind, data.styles[d:get("style")]) end if data.size then final:set("textsize", data.sizes[d:get("size")]) end local t = { label="edit text", pno=model.pno, vno=model.vno, original=data.obj:clone(), primary=data.prim, final=final, } t.undo = function (t, doc) doc[t.pno]:replace(t.primary, t.original) end t.redo = function (t, doc) doc[t.pno]:replace(t.primary, t.final) end model:register(t) -- need to update data.obj for the next run! data.obj = final if run_latex then model:runLatex() end end function MODEL:action_edit_text(prim, obj) local mp = obj:get("minipage") local stylekind = "labelstyle" if mp then stylekind = "textstyle" end local d = ipeui.Dialog(self.ui:win(), "Edit text object") local data = { model=self, stylekind = stylekind, styles = self.doc:sheets():allNames(stylekind), sizes = self.doc:sheets():allNames("textsize"), prim=prim, obj=obj, } d:add("label", "label", { label="Edit latex source" }, 1, 1, 1, 2) d:add("text", "text", { syntax="latex", focus=true, spell_check=prefs.spell_check}, 0, 1, 1, 4) d:addButton("apply", "&Apply", function (d) apply_text_edit(d, data, true) end) addEditorField(d, "text") d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("row", 2, 1) d:setStretch("column", 2, 1) d:set("text", obj:text()) d:set("ignore-escape", true) data.style = indexOf(obj:get(stylekind), data.styles) if data.style then d:add("style", "combo", data.styles, 1, 3) d:set("style", data.style) end data.size = indexOf(obj:get("textsize"), data.sizes) if data.size then d:add("size", "combo", data.sizes, 1, 4) d:set("size", data.size) end if prefs.auto_external_editor then externalEditor(d, "text") end if ((prefs.auto_external_editor and prefs.editor_closes_dialog) or d:execute(prefs.editor_size)) then if string.match(d:get("text"), "^%s*$") then return end apply_text_edit(d, data, self.auto_latex) end end function MODEL:accept_group_text_edit(prim, group, t, tobj) local els = group:elements() els[t] = tobj local final = ipe.Group(els) -- copy properties final:set("pinned", group:get("pinned")) final:set("transformations", group:get("transformations")) final:setMatrix(group:matrix()) final:setText(group:text()) final:setClip(group:clip()) final:set("decoration", group:get("decoration")) local t = { label="edit text in group", pno=self.pno, vno=self.vno, primary=prim, original=group:clone(), final=final, } t.undo = function (t, doc) doc[t.pno]:replace(t.primary, t.original) end t.redo = function (t, doc) doc[t.pno]:replace(t.primary, t.final) end self:register(t) self:autoRunLatex() end function MODEL:action_edit_group_text(prim, obj) local t = nil for i = 1,obj:count() do if obj:elementType(i) == "text" then t = i end end if not t then self:warning("Cannot edit object", "Only groups containing text can be edited") return end local tobj = obj:element(t) local d = ipeui.Dialog(self.ui:win(), "Edit text in group object") d:add("label", "label", { label="Edit latex source" }, 1, 1, 1, 2) d:add("text", "text", { syntax="latex", focus=true, spell_check=prefs.spell_check}, 0, 1, 1, 4) addEditorField(d, "text") d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("row", 2, 1) d:setStretch("column", 2, 1) d:set("text", tobj:text()) d:set("ignore-escape", true) if prefs.auto_external_editor then externalEditor(d, "text") end if ((prefs.auto_external_editor and prefs.editor_closes_dialog) or d:execute(prefs.editor_size)) then if string.match(d:get("text"), "^%s*$") then return end local final = tobj:clone() final:setText(d:get("text")) self:accept_group_text_edit(prim, obj, t, final) end end function MODEL:action_edit() local p = self:page() local prim = p:primarySelection() if not prim then self.ui:explain("no selection") return end local obj = p[prim] if obj:type() == "text" then self:action_edit_text(prim, obj) elseif obj:type() == "path" then self:action_edit_path(prim, obj) elseif obj:type() == "group" then self:action_edit_group_text(prim, obj) else self:warning("Cannot edit " .. obj:type() .. " object", "Only text objects, path objects, and groups with text can be edited") end end ---------------------------------------------------------------------- local function start_group_edit(t, doc) local p = doc[t.pno] local layers = p:layers() local layerOfPrim = p:layerOf(t.primary) local activeLayer = p:active(t.vno) local activeIndex = indexOf(activeLayer, layers) local g = p[t.primary] local elements = g:elements() local matrix = g:matrix() local layer = "EDIT-GROUP" if g:get("decoration") ~= "normal" then layer = layer .. "<" .. g:get("decoration"):sub(12) .. ">" end if layerOfPrim ~= activeLayer then layer = layer .. "-" .. layerOfPrim end while indexOf(layer, layers) do layer = layer:sub(1,10) .. "*" .. layer:sub(11) end p:remove(t.primary) p:addLayer(layer) p:moveLayer(layer, activeIndex + 1) for _,obj in ipairs(elements) do p:insert(nil, obj, nil, layer) p:transform(#p, matrix) end p:deselectAll() p:setActive(t.vno, layer) p:setVisible(t.vno, layer, true) for _,l in ipairs(layers) do p:setLocked(l, true) end end local function end_group_edit(t, doc) local p = doc[t.pno] local layers = p:layers() local activeLayer = p:active(t.vno) local activeIndex = indexOf(activeLayer, layers) local origActive if activeIndex > 1 then origActive = layers[activeIndex - 1] else origActive = layers[2] end local origGroup = nil local deco, i = string.match(activeLayer, "^EDIT%-GROUP%**<([^>]+)>()") if not deco then deco = "normal" local og = string.match(activeLayer, "^EDIT%-GROUP%**%-(.*)$") if og then origGroup = og end else deco = "decoration/" .. deco local og = string.match(activeLayer, "^EDIT%-GROUP%**<[^>]+>%-(.*)$") if og then origGroup = og end end if not origGroup or not indexOf(origGroup, layers) then origGroup = origActive end local elements = {} for i, obj, sel, layer in p:objects() do if layer == activeLayer then elements[#elements + 1] = obj:clone() end end for i = #p,1,-1 do if p:layerOf(i) == activeLayer then p:remove(i) end end local group = ipe.Group(elements) group:set("decoration", deco) p:setLocked(origActive, false) p:setLocked(origGroup, false) p:setActive(t.vno, origActive) p:removeLayer(activeLayer) p:insert(nil, group, 1, origGroup) if not string.match(origActive, "^EDIT") then for _,l in ipairs(p:layers()) do p:setLocked(l, false) end end end function MODEL:saction_edit_group() local p = self:page() local prim = p:primarySelection() if p[prim]:type() ~= "group" then self.ui:explain("primary selection is not a group") return end local t = { label="start group edit", pno = self.pno, vno = self.vno, primary = prim, original = p:clone(), undo = revertOriginal, redo = start_group_edit, } self:register(t) end function MODEL:action_end_group_edit() local p = self:page() if (not string.match(p:active(self.vno), "^EDIT%-GROUP")) or p:countLayers() < 2 then self:warning("Cannot end group edit", "Active layer is not a group edit layer") return end local t = { label="end group edit", pno = self.pno, vno = self.vno, original = p:clone(), undo = revertOriginal, redo = end_group_edit, } self:register(t) end ---------------------------------------------------------------------- PASTETOOL = {} PASTETOOL.__index = PASTETOOL function PASTETOOL:new(model, elements, pos) local tool = {} _G.setmetatable(tool, PASTETOOL) tool.model = model tool.elements = elements tool.start = model.ui:pos() if pos then tool.start = pos end local obj = ipe.Group(elements) tool.pinned = obj:get("pinned") model.ui:pasteTool(obj, tool) tool.setColor(1.0, 0, 0) tool:computeTranslation() tool.setMatrix(ipe.Translation(tool.translation)) return tool end function PASTETOOL:computeTranslation() self.translation = self.model.ui:pos() - self.start if self.pinned == "horizontal" or self.pinned == "fixed" then self.translation = V(0, self.translation.y) end if self.pinned == "vertical" or self.pinned == "fixed" then self.translation = V(self.translation.x, 0) end end function PASTETOOL:mouseButton(button, modifiers, press) self:computeTranslation() self.model.ui:finishTool() local t = { label="paste objects at cursor", pno = self.model.pno, vno = self.model.vno, elements = self.elements, layer = self.model:page():active(self.model.vno), translation = ipe.Translation(self.translation), } t.undo = function (t, doc) local p = doc[t.pno] for i = 1,#t.elements do p:remove(#p) end end t.redo = function (t, doc) local p = doc[t.pno] for i,obj in ipairs(t.elements) do p:insert(nil, obj, 2, t.layer) p:transform(#p, t.translation) end p:ensurePrimarySelection() end self.model:page():deselectAll() self.model:register(t) end function PASTETOOL:mouseMove() self:computeTranslation() self.setMatrix(ipe.Translation(self.translation)) self.model.ui:update(false) -- update tool end function PASTETOOL:key(text, modifiers) if text == "\027" then self.model.ui:finishTool() return true else return false end end function MODEL:action_paste_at_cursor() local data = self.ui:clipboard(true) -- allow bitmap if not data then self:warning("Nothing to paste") return end if type(data) == "string" then if data:sub(1,13) ~= " 1 then self:multiPopup(sel) elseif #sel == 0 then self:emptyPopup() else self:singlePopup(self:page():primarySelection()) end end function MODEL:emptyPopup() local m = ipeui.Menu(self.ui:win()) m:add("action_paste_at_cursor", "Paste at cursor") m:add("action_pan_here", "Pan canvas") m:add("grid", "Toggle grid") local gp = self.ui:globalPos() local item, num, value = m:execute(gp.x, gp.y) if item then if item:sub(1,7) == "action_" then self:action(item:sub(8)) elseif item == "grid" then self:toggleGrid() end end end function MODEL:singlePopup(prim) local obj = self:page()[prim] local m = ipeui.Menu(self.ui:win()) self["properties_" .. obj:type()](self, obj, m) if prefs.tablet_menu then m:add("action_cut", "Cut") m:add("action_copy", "Copy") m:add("action_paste_at_cursor", "Paste at cursor") m:add("action_pan_here", "Pan canvas") m:add("grid", "Toggle grid") end local gp = self.ui:globalPos() local item, num, value = m:execute(gp.x, gp.y) if item then if item == "layer" then self:changeLayerOfPrimary(prim, value) elseif item:sub(1,7) == "action_" then self:action(item:sub(8)) elseif item == "comment" then -- nothing to do elseif item == "grid" then self:toggleGrid() else self:setAttributeOfPrimary(prim, item, value) end end end -------------------------------------------------------------------- function MODEL:toggleGrid() local t = not self.ui:actionState("grid_visible"); self.ui:setActionState("grid_visible", t) self:action_grid_visible() end function MODEL:changeLayerOfPrimary(prim, layer) local p = self:page() local t = { label="change layer to " .. layer, pno=self.pno, vno=self.vno, primary=prim, original=p:layerOf(prim), toLayer=layer, } t.undo = function (t, doc) doc[t.pno]:setLayerOf(t.primary, t.original) end t.redo = function (t, doc) doc[t.pno]:setLayerOf(t.primary, t.toLayer) end self:register(t) end function MODEL:setAttributeOfPrimary(prim, prop, value) self:deselectSecondary() local p = self:page() local t = { label="set attribute " .. prop .. " to " .. tostring(value), pno=self.pno, vno=self.vno, primary=prim, original=p[prim]:clone(), property=prop, value=value, stroke=self.attributes.stroke, fill=self.attributes.fill, } t.undo = function (t, doc) doc[t.pno]:replace(t.primary, t.original) end t.redo = function (t, doc) doc[t.pno]:setAttribute(t.primary, t.property, t.value, t.stroke, t.fill) end self:register(t) if prop == "minipage" or prop == "textsize" or prop == "textstyle" or prop == "labelstyle" then self:autoRunLatex() end if p[prim]:type() == "text" and prop == "stroke" then self:autoRunLatex() end end ---------------------------------------------------------------------- function MODEL:insertBasic(m, obj) local p = self:page() local layerL = p:layers() local pinnedL = { "none", "horizontal", "vertical", "fixed" } local transformationsL = { "translations", "rigid", "affine" } local layer = p:layerOf(p:primarySelection()) local pinned = obj:get("pinned") local transformations = obj:get("transformations") m:add("layer", "Layer: " .. layer, layerL, nil, layer) m:add("pinned", "Pinned: " .. pinned, pinnedL, nil, pinned) m:add("transformations", "Transformations: " .. transformations, transformationsL, nil, transformations) end function MODEL:insertOpacity(m, obj) local opacityL = self.doc:sheets():allNames("opacity") local opacity = obj:get("opacity") m:add("opacity", "Opacity: " .. opacity, opacityL, nil, opacity) if obj:type() == "path" then local strokeOpacity = obj:get("strokeopacity") m:add("strokeopacity", "Stroke opacity: " .. strokeOpacity, opacityL, nil, strokeOpacity) end end ---------------------------------------------------------------------- local function group_has_text(obj) for i = 1,obj:count() do if obj:elementType(i) == "text" then return true end end return false end local function decorationToName(i, s) if s == "normal" then return "no decoration" else return s:match("^decoration/(.+)$") end end local function decoration_names(model) local symbols = model.doc:sheets():allNames("symbol") local res = { "normal" } for _, name in ipairs(symbols) do if name:match("^decoration/") then res[#res + 1] = name end end return res end function MODEL:properties_group(obj, m) m:add("comment", "Group object") local s = string.format("%d elements", obj:count()) local clip = obj:clip() local link_action = obj:text() if clip then s = s .. ", with clipping" end m:add("comment", s) if link_action == "" then m:add("action_set_link_action", "Set link action") else m:add("action_set_link_action", "Link action: " .. link_action) end m:add("decoration", "Decoration", decoration_names(self), decorationToName, obj:get("decoration")) self:insertBasic(m, obj) m:add("action_apply_properties", "Apply properties") if clip then m:add("action_remove_clipping", "Remove clipping") m:add("action_extract_clipping", "Extract clipping path") end if group_has_text(obj) then m:add("action_edit", "Edit text in group") end m:add("action_edit_group", "Edit group") m:add("action_edit_as_xml", "Edit as XML") m:add("action_ungroup", "Ungroup") end function MODEL:properties_path(obj, m) local sheet = self.doc:sheets() local colors = sheet:allNames("color") local pathmodes = { "stroke only", "stroke && fill", "fill only" } local pathmodeL = { "stroked", "strokedfilled", "filled" } local penL = sheet:allNames("pen") local dashstyleL = sheet:allNames("dashstyle") local arrowsizeL = sheet:allNames("arrowsize") local arrowshapeL = symbolNames(sheet, "arrow/", "(spx)") local tilingL = sheet:allNames("tiling") table.insert(tilingL, 1, "normal") local gradientL = sheet:allNames("gradient") table.insert(gradientL, 1, "normal") local linecapL = { "normal", "butt", "round", "square", } local linejoinL = { "normal", "miter", "round", "bevel", } local fillruleL = { "normal", "wind", "evenodd", } local shape = obj:shape() m:add("comment", "Path object") m:add("comment", string.format("%d subpaths", #shape)) self:insertBasic(m, obj) local pm = obj:get("pathmode") m:add("pathmode", "Stroke && Fill: " .. pathmodes[indexOf(pm, pathmodeL)], pathmodeL, pathmodes, pm) if pm ~= "filled" then m:add("stroke", "Stroke color: " .. colorString(obj:get("stroke")), colors, nil, function (i, name) return color_icon(self.doc:sheets(), name) end) end if pm ~= "stroked" then m:add("fill", "Fill color: " .. colorString(obj:get("fill")), colors, nil, function (i, name) return color_icon(self.doc:sheets(), name) end) end local pen = obj:get("pen") m:add("pen", "Pen width: " .. pen, penL, nil, pen) local dashstyle = obj:get("dashstyle") m:add("dashstyle", "Dash style: " .. dashstyle, dashstyleL, nil, dashstyle) local farr = obj:get("farrow") local rarr = obj:get("rarrow") local boolnames = { "yes", "no" } local boolmap = { "true", "false" } local bool_to_yesno = { [false]="no", [true]="yes" } m:add("farrow", "Forward arrow: " .. bool_to_yesno[farr], boolmap, boolnames, tostring(farr)) if farr then m:add("farrowsize", "Forward arrow size", arrowsizeL, nil, obj:get("farrowsize")) m:add("farrowshape", "Forward arrow shape", arrowshapeL, arrowshapeToName, obj:get("farrowshape")) end m:add("rarrow", "Reverse arrow: " .. bool_to_yesno[rarr], boolmap, boolnames, tostring(rarr)) if rarr then m:add("rarrowsize", "Reverse arrow size", arrowsizeL, nil, obj:get("rarrowsize")) m:add("rarrowshape", "Reverse arrow shape", arrowshapeL, arrowshapeToName, obj:get("rarrowshape")) end local lc = obj:get("linecap") local lj = obj:get("linejoin") local fr = obj:get("fillrule") m:add("linecap", "Line cap: " .. lc, linecapL, nil, lc) m:add("linejoin", "Line join: " .. lj, linejoinL, nil, lj) m:add("fillrule", "Fill rule: " .. fr, fillruleL, nil, fr) if pm ~= "stroked" then local tiling = obj:get("tiling") local gradient = obj:get("gradient") m:add("tiling", "Tiling pattern: " .. tiling, tilingL, nil, tiling) m:add("gradient", "Gradient: " .. gradient, gradientL, nil, gradient) end self:insertOpacity(m, obj) if #shape > 1 then m:add("action_decompose", "Decompose path") end m:add("action_pick_properties", "Pick properties") m:add("action_apply_properties", "Apply properties") m:add("action_edit_as_xml", "Edit as XML") m:add("action_edit", "Edit path") end function MODEL:properties_text(obj, m) local sheet = self.doc:sheets() local minipage = obj:get("minipage") local colors = sheet:allNames("color") local textsizeL = sheet:allNames("textsize") local textstyleL = sheet:allNames("textstyle") local labelstyleL = sheet:allNames("labelstyle") m:add("comment", "Text object") self:insertBasic(m, obj) local t = minipage and "minipage" or "label" m:add("minipage", "Type: " .. t, {"true", "false"}, {"minipage", "label"}, tostring(minipage)) m:add("stroke", "Color: " .. colorString(obj:get("stroke")), colors, nil, function (i, name) return color_icon(self.doc:sheets(), name) end) local ts = obj:get("textsize") m:add("textsize", "Size: " .. ts, textsizeL, nil, ts) if minipage then local ts = obj:get("textstyle") m:add("textstyle", "Style: " .. ts, textstyleL, nil, ts) else local ts = obj:get("labelstyle") m:add("labelstyle", "Style: " .. ts, labelstyleL, nil, ts) local ha = obj:get("horizontalalignment") m:add("horizontalalignment", "Horizontal alignment: " .. ha, {"left", "right", "hcenter"}, nil, ha) end local va = obj:get("verticalalignment") m:add("verticalalignment", "Vertical alignment: " .. va, {"bottom", "baseline", "top", "vcenter"}, nil, va) self:insertOpacity(m, obj) if minipage then m:add("action_change_width", "Change width") end m:add("action_pick_properties", "Pick properties") m:add("action_apply_properties", "Apply properties") m:add("action_edit_as_xml", "Edit as XML") m:add("action_edit", "Edit text") end function MODEL:properties_image(obj, m) m:add("comment", "Image object") local info = obj:info() m:add("comment", string.format("%d x %d pixels", info.width, info.height)) m:add("comment", "Format " .. info.format) self:insertBasic(m, obj) self:insertOpacity(m, obj) end function MODEL:properties_reference(obj, m) local sheet = self.doc:sheets() local colors = sheet:allNames("color") local sizes = sheet:allNames("symbolsize") local pens = sheet:allNames("pen") m:add("comment", "Reference object") m:add("comment", "Symbol name: " .. obj:symbol()) self:insertBasic(m, obj) m:add("stroke", "Stroke color: " .. colorString(obj:get("stroke")), colors, nil, function (i, name) return color_icon(self.doc:sheets(), name) end) m:add("fill", "Fill color: " .. colorString(obj:get("fill")), colors, nil, function (i, name) return color_icon(self.doc:sheets(), name) end) local ss = obj:get("symbolsize") m:add("symbolsize", "Size: " .. ss, sizes, nil, ss) local pen = obj:get("pen") m:add("pen", "Pen: " .. pen, pens, nil, pen) m:add("action_pick_properties", "Pick properties") m:add("action_apply_properties", "Apply properties") m:add("action_edit_as_xml", "Edit as XML") end ---------------------------------------------------------------------- local object_name = { text = "Text", path = "Path", image = "Image", reference = "Reference", group = "Group", } function MODEL:multiAttributes(m, tm) local layers = self:page():layers() local pinned = { "none", "horizontal", "vertical", "fixed" } local transformations = { "translations", "rigid", "affine" } m:add("layer", "Layer", layers) m:add("pinned", "Pinned", pinned) m:add("transformations", "Transformations", transformations) local sheet = self.doc:sheets() local colors = sheet:allNames("color") local sizes = sheet:allNames("symbolsize") local pens = sheet:allNames("pen") local opacity = sheet:allNames("opacity") local pathmodes = { "stroke only", "stroke && fill", "fill only" } local pathmode = { "stroked", "strokedfilled", "filled" } local dashstyle = sheet:allNames("dashstyle") local arrowsizes = sheet:allNames("arrowsize") local arrowshapes = symbolNames(sheet, "arrow/", "(spx)") local tilings = sheet:allNames("tiling") table.insert(tilings, 1, "normal") local gradients = sheet:allNames("gradient") table.insert(gradients, 1, "normal") local linecap = { "normal", "butt", "round", "square", } local linejoin = { "normal", "miter", "round", "bevel", } local fillrule = { "normal", "wind", "evenodd", } local textsize = sheet:allNames("textsize") local textstyle = sheet:allNames("textstyle") if tm.path or tm.text or tm.reference then m:add("stroke", "Stroke color", colors, nil, function (i, name) return color_icon(sheet, name) end) end if tm.path or tm.reference then m:add("fill", "Fill color", colors, nil, function (i, name) return color_icon(sheet, name) end) end if tm.path or tm.reference then m:add("pen", "Pen width", pens) end if tm.path then m:add("pathmode", "Stroke && Fill", pathmode, pathmodes) m:add("dashstyle", "Dash style", dashstyle) local boolnames = { "yes", "no" } local boolmap = { "true", "false" } m:add("farrow", "Forward arrow", boolmap, boolnames) m:add("farrowsize", "Forward arrow size", arrowsizes) m:add("farrowshape", "Forward arrow shape", arrowshapes, arrowshapeToName) m:add("rarrow", "Reverse arrow", boolmap, boolnames) m:add("rarrowsize", "Reverse arrow size", arrowsizes) m:add("rarrowshape", "Reverse arrow shape", arrowshapes, arrowshapeToName) m:add("linecap", "Line cap", linecap) m:add("linejoin", "Line join", linejoin) m:add("fillrule", "Fill rule", fillrule) m:add("tiling", "Tiling pattern", tilings) m:add("gradient", "Gradient", gradients) end if tm.text then m:add("textsize", "Text size", textsize) m:add("textstyle", "Text style", textstyle) m:add("horizontalalignment", "Horizontal alignment", {"left", "right", "hcenter"}) m:add("verticalalignment", "Vertical alignment", {"bottom", "baseline", "top", "vcenter"}) end if tm.reference then m:add("symbolsize", "Size", sizes) end if tm.text or tm.path then m:add("opacity", "Opacity", opacity) end if tm.path then m:add("strokeopacity", "Stroke opacity", opacity) end m:add("action_apply_properties", "Apply properties") end function MODEL:multiPopup() -- collect types of selected objects local p = self:page() local typmap = {} local count = 0 for i,obj,sel,layer in self:page():objects() do if sel then typmap[obj:type()] = true; count = count + 1 end end local typcount = 0 local ttype = nil for t in pairs(typmap) do typcount = typcount + 1; ttype = t end local m = ipeui.Menu(self.ui:win()) if typcount == 1 then m:add("comment", string.format("%d %s objects", count, object_name[ttype])) else m:add("comment", string.format("%d objects", count)) end self:multiAttributes(m, typmap) if count == 2 and typcount == 2 and typmap["group"] and typmap["path"] then m:add("action_add_clipping", "Add clipping path") end if typcount == 1 and ttype == 'path' then m:add("action_join", "Join paths") m:add("action_compose", "Compose paths") end if prefs.tablet_menu then m:add("action_cut", "Cut") m:add("action_copy", "Copy") m:add("action_paste_at_cursor", "Paste at cursor") m:add("action_pan_here", "Pan canvas") m:add("grid", "Toggle grid") end local gp = self.ui:globalPos() local item, num, value = m:execute(gp.x, gp.y) if item then if item == "layer" then self:action_move_to_layer(value) elseif item:sub(1,7) == "action_" then self:action(item:sub(8)) elseif item == "comment" then -- nothing to do elseif item == "grid" then self:toggleGrid() else self:setAttribute(item, value) end end end -------------------------------------------------------------------- function MODEL:saction_pick_properties() local p = self:page() local prim = p:primarySelection() local obj = p[prim] self["pick_properties_" .. obj:type()](self, obj) self.ui:setAttributes(self.doc:sheets(), self.attributes) end function MODEL:pick_properties_group(obj) -- nothing end function MODEL:pick_properties_text(obj) local a = self.attributes a.stroke = obj:get("stroke") a.textsize = obj:get("textsize") if obj:get("minipage") then a.textstyle = obj:get("textstyle") else a.horizontalalignment = obj:get("horizontalalignment") end a.verticalalignment = obj:get("verticalalignment") a.opacity = obj:get("opacity") end function MODEL:pick_properties_path(obj) local a = self.attributes a.pathmode = obj:get("pathmode") if a.pathmode ~= "filled" then a.stroke = obj:get("stroke") end if a.pathmode ~= "stroked" then a.fill = obj:get("fill") end a.pen = obj:get("pen") a.dashstyle = obj:get("dashstyle") a.farrow = obj:get("farrow") a.rarrow = obj:get("rarrow") if a.farrow then a.farrowsize = obj:get("farrowsize") a.farrowshape = obj:get("farrowshape") end if a.rarrow then a.rarrowsize = obj:get("rarrowsize") a.rarrowshape = obj:get("rarrowshape") end a.linecap = obj:get("linecap") a.linejoin = obj:get("linejoin") a.fillrule = obj:get("fillrule") a.tiling = obj:get("tiling") a.gradient = obj:get("gradient") a.opacity = obj:get("opacity") a.strokeopacity = obj:get("strokeopacity") end function MODEL:pick_properties_image(obj) -- nothing end function MODEL:pick_properties_reference(obj) local a = self.attributes a.stroke = obj:get("stroke") a.fill = obj:get("fill") a.pen = obj:get("pen") a.symbolsize = obj:get("symbolsize") end ---------------------------------------------------------------------- function MODEL:saction_apply_properties() local a = { } for k, v in pairs(self.attributes) do a[k] = v end local t = { label="apply properties", pno = self.pno, vno = self.vno, attributes=a, selection=self:selection(), original=self:page():clone(), undo=revertOriginal, } t.redo = function (t, doc) local p = doc[t.pno] for i,obj,sel,layer in p:objects() do if sel then local ty = obj:type() if ty == "text" then apply_properties_text(obj, t.attributes) elseif ty == "path" then apply_properties_path(obj, t.attributes) elseif ty == "reference" then apply_properties_reference(obj, t.attributes) end end end end self:register(t) end function apply_properties_text(obj, a) obj:set("stroke", a.stroke) obj:set("textsize", a.textsize) if obj:get("minipage") then obj:set("textstyle", a.textstyle) else obj:set("horizontalalignment", a.horizontalalignment) end obj:set("verticalalignment", a.verticalalignment) obj:set("opacity", a.opacity) end function apply_properties_path(obj, a) obj:set("pathmode", a.pathmode) if a.pathmode ~= "filled" then obj:set("stroke", a.stroke) end if a.pathmode ~= "stroked" then obj:set("fill", a.fill) end obj:set("pen", a.pen) obj:set("dashstyle", a.dashstyle) obj:set("farrow", a.farrow) obj:set("rarrow", a.rarrow) if a.farrow then obj:set("farrowsize", a.farrowsize) obj:set("farrowshape", a.farrowshape) end if a.rarrow then obj:set("rarrowsize", a.rarrowsize) obj:set("rarrowshape", a.rarrowshape) end obj:set("linecap", a.linecap) obj:set("linejoin", a.linejoin) obj:set("fillrule", a.fillrule) obj:set("tiling", a.tiling) obj:set("gradient", a.gradient) obj:set("opacity", a.opacity) obj:set("strokeopacity", a.strokeopacity) end function apply_properties_reference(obj, a) obj:set("stroke", a.stroke) obj:set("fill", a.fill) obj:set("pen", a.pen) obj:set("symbolsize", a.symbolsize) end ---------------------------------------------------------------------- ipe-7.2.13/src/ipe/lua/model.lua0000644000175000017500000005613413561570220016175 0ustar otfriedotfried---------------------------------------------------------------------- -- model.lua ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] MODEL = {} MODEL.__index = MODEL MODEL.snapmodes = { "snapvtx", "snapctl", "snapbd", "snapint", "snapgrid", "snapangle", "snapauto"} function MODEL:new(fname) local model = {} setmetatable(model, MODEL) model:init(fname) return model end function MODEL:init(fname) self.attributes = prefs.initial_attributes self.snap = { snapvtx = prefs.snap.vertex, snapctl = prefs.snap.ctrlpoints, snapbd = prefs.snap.boundary, snapint = prefs.snap.intersection, snapgrid = prefs.snap.grid, snapangle = prefs.snap.angle, snapauto = prefs.snap.autoangle, grid_visible = prefs.initial.grid_visible, pretty_display = false, gridsize = prefs.initial.grid_size, anglesize = prefs.initial.angle_size, snap_distance = prefs.snap_distance, with_axes = false, origin = ipe.Vector(0,0), orientation = 0 } self.save_timestamp = 0 self.ui = AppUi(self) self.pristine = false self.first_show = true self.auto_latex = prefs.auto_run_latex self.ui:setActionState("auto_latex", self.auto_latex) self.mode = "select" self.ui:setActionState("mode_select", true) self.ui:setActionState("grid_visible", self.snap.grid_visible) self.ui:setActionState("show_axes", self.snap.with_axes) for i,e in ipairs(MODEL.snapmodes) do self.ui:setActionState(e, self.snap[e]) end self:setSnap() self.ui:setFifiVisible(true) for dock, vis in pairs(prefs.tools_visible) do self.ui:showTool(dock, vis) end local err = nil if fname then if ipe.fileExists(fname) then err = self:tryLoadDocument(fname) else self:newDocument() self.file_name = fname self:setCaption() end end if not self.doc then self:newDocument() self.pristine = true end if prefs.autosave_interval then self.timer = ipeui.Timer(self, "autosave") self.timer:setInterval(1000 * prefs.autosave_interval) -- millisecs self.timer:start() end if err then self:warning("Document '" .. fname .. "' could not be opened", err) end end function MODEL:sizeChanged() if self.first_show then self:action_fit_top() end self.first_show = false end ---------------------------------------------------------------------- function MODEL:resetGridSize() self.snap.gridsize = prefs.initial.grid_size self.snap.anglesize = prefs.initial.angle_size local gridsizes = allValues(self.doc:sheets(), "gridsize") if #gridsizes == 0 then gridsizes = { 16 } end if not indexOf(self.snap.gridsize, gridsizes) then self.snap.gridsize = gridsizes[1] end local anglesizes = allValues(self.doc:sheets(), "anglesize") if #anglesizes == 0 then anglesizes = { 45 } end if not indexOf(self.snap.anglesize, anglesizes) then self.snap.anglesize = anglesizes[1] end self.ui:setGridAngleSize(self.snap.gridsize, self.snap.anglesize) end function MODEL:print_attributes() print("----------------------------------------") for k in pairs(self.attributes) do print(k, self.attributes[k]) end print("----------------------------------------") end function MODEL:getString(msg, caption, start) if caption == nil then caption = "Ipe" end local d = ipeui.Dialog(self.ui:win(), caption) d:add("label", "label", {label=msg}, 1, 1) d:add("text", "input", {select_all=true}, 2, 1) d:addButton("ok", "Ok", "accept") d:addButton("cancel", "Cancel", "reject") if start then d:set("text", start) end if d:execute() then return d:get("text") end end function MODEL:getDouble(caption, label, value, minv, maxv) local s = self:getString(label, caption, tostring(value)) if s then local n = tonumber(s) if n and minv <= n and n <= maxv then return n end end end ---------------------------------------------------------------------- -- Return current page function MODEL:page() return self.doc[self.pno] end -- return table with selected objects on current page function MODEL:selection() local t = {} for i,obj,sel,layer in self:page():objects() do if sel then t[#t+1] = i end end return t end function MODEL:markAsUnmodified() self.save_timestamp = self.save_timestamp + 1 self.undo[#self.undo].save_timestamp = self.save_timestamp end -- is document modified? function MODEL:isModified() return (self.undo[#self.undo].save_timestamp ~= self.save_timestamp) end ---------------------------------------------------------------------- -- set window caption function MODEL:setCaption() local s = "Ipe " if config.toolkit == "qt" then s = s .. "[*]" elseif self:isModified() then s = s .. '*' end if self.file_name then s = s .. '"' .. self.file_name .. '" ' else s = s .. "[unsaved] " end --[[ if #self.doc > 1 then s = s .. string.format("Page %d/%d ", self.pno, #self.doc) end if self:page():countViews() > 1 then s = s .. string.format("(View %d/%d) ", self.vno, self:page():countViews()) end --]] self.ui:setWindowTitle(self:isModified(), s) end function MODEL:setSnap() local function ind(is_on, s, letter) if is_on then return s .. letter else return s .. "-" end end self.ui:setSnap(self.snap) local s = ind(self.snap.snapvtx, "", "v") s = ind(self.snap.snapctl, s, "c") s = ind(self.snap.snapbd, s, "b") s = ind(self.snap.snapint, s, "x") s = ind(self.snap.snapgrid, s, "+") s = ind(self.snap.snapangle, s, "r") s = ind(self.snap.snapauto, s, "a") s = s .. " " .. self.snap.gridsize s = s .. " " .. self.snap.anglesize self.ui:setSnapIndicator(s) end -- show a warning messageBox function MODEL:warning(text, details) messageBox(self.ui:win(), "warning", text, details) end -- Set canvas to current page function MODEL:setPage() local p = self:page() self.ui:setPage(p, self.pno, self.vno, self.doc:sheets()) self.ui:setLayers(p, self.vno) self.ui:setNumbering(self.doc:properties().numberpages) self.ui:update() self:setCaption() self:setBookmarks() self.ui:setNotes(p:notes()) local vno if p:countViews() > 1 then vno = string.format("View %d/%d", self.vno, p:countViews()) end local pno if #self.doc > 1 then pno = string.format("Page %d/%d", self.pno, #self.doc) end self.ui:setNumbers(vno, p:markedView(self.vno), pno, p:marked()) end function MODEL:getBookmarks() local b = {} for _,p in self.doc:pages() do local t = p:titles() if t.section then if t.section ~= "" then b[#b+1] = t.section end elseif t.title ~= "" then b[#b+1] = t.title end if t.subsection then if t.subsection ~= "" then b[#b+1] = " " .. t.subsection end elseif t.title ~= "" then b[#b+1] = " " .. t.title end end return b end function MODEL:setBookmarks() self.ui:setBookmarks(self:getBookmarks()) end function MODEL:findPageForBookmark(index) local count = 0 for i,p in self.doc:pages() do local t = p:titles() if t.section then if t.section ~= "" then count = count + 1 end elseif t.title ~= "" then count = count + 1 end if t.subsection then if t.subsection ~= "" then count = count + 1 end elseif t.title ~= "" then count = count + 1 end if count >= index then return i end end end ---------------------------------------------------------------------- -- Deselect all objects not in current view, or in a locked layer. function MODEL:deselectNotInView() local p = self:page() for i,obj,sel,layer in p:objects() do if not p:visible(self.vno, i) or p:isLocked(layer) then p:setSelect(i, nil) end end p:ensurePrimarySelection() end -- Deselect all but primary selection function MODEL:deselectSecondary() local p = self:page() for i,obj,sel,layer in p:objects() do if sel ~= 1 then p:setSelect(i, nil) end end end -- If no selected object is close, select closest object. -- If there is a selected object close enough, returns true. -- Otherwise, check whether the closest object to the current mouse -- position is close enough. If so, unselect everything, make -- this object the primary selection, and return true. -- If not, return whether the page has a selection at all. -- If primaryOnly is true, the primary selection has to be close enough, -- otherwise it'll be replaced as above. function MODEL:updateCloseSelection(primaryOnly) local bound = prefs.close_distance local pos = self.ui:unsnappedPos() local p = self:page() -- is current selection close enough? if primaryOnly then local prim = p:primarySelection() if prim and p:distance(prim, pos, bound) < bound then return true end else for i,obj,sel,layer in p:objects() do if sel and p:distance(i, pos, bound) < bound then return true end end end -- current selection is not close enough: find closest object local closest for i,obj,sel,layer in p:objects() do if p:visible(self.vno, i) and not p:isLocked(layer) then local d = p:distance(i, pos, bound) if d < bound then closest = i; bound = d end end end if closest then -- deselect all, and select only closest object p:deselectAll() p:setSelect(closest, 1) return true else return p:hasSelection() end end ---------------------------------------------------------------------- -- Move to next/previous view function MODEL:nextView(delta) if 1 <= self.vno + delta and self.vno + delta <= self:page():countViews() then self.vno = self.vno + delta; self:deselectNotInView() elseif 1 <= self.pno + delta and self.pno + delta <= #self.doc then self.pno = self.pno + delta if delta > 0 then self.vno = 1; else self.vno = self:page():countViews() end end end -- Move to next/previous page function MODEL:nextPage(delta) if 1 <= self.pno + delta and self.pno + delta <= #self.doc then self.pno = self.pno + delta if delta > 0 then self.vno = 1; else self.vno = self:page():countViews() end end end -- change zoom and pan to fit box on screen function MODEL:fitBox(box) if box:isEmpty() then return end local cs = self.ui:canvasSize() local xfactor = 20.0 local yfactor = 20.0 if box:width() > 0 then xfactor = cs.x / box:width() end if box:height() > 0 then yfactor = cs.y / box:height() end local zoom = math.min(xfactor, yfactor) if zoom > prefs.max_zoom then zoom = prefs.max_zoom end if zoom < prefs.min_zoom then zoom = prefs.min_zoom end self.ui:setPan(0.5 * (box:bottomLeft() + box:topRight())) self.ui:setZoom(zoom) self.ui:update() end ---------------------------------------------------------------------- local function showSource(d) local fname = config.latexdir .. "ipetemp.tex" ipeui.waitDialog(d, string.format(prefs.external_editor, fname)) end function MODEL:latexErrorBox(log) local d = ipeui.Dialog(self.ui:win(), "Ipe: error running Latex") d:add("label", "label", { label="An error occurred during the Pdflatex run. " .. "Please consult the logfile below." }, 1, 1) d:add("text", "text", { read_only=true, syntax="logfile", focus=true }, 2, 1) if prefs.external_editor then d:addButton("editor", "&Source", function (d) showSource(d) end) end d:addButton("ok", "Ok", "accept") d:set("text", log) d:setStretch("row", 2, 1) d:execute(prefs.latexlog_size) end function MODEL:runLatex() local success, errmsg, result, log = self.doc:runLatex(self.file_name) if success then self.ui:setResources(self.doc) self.ui:update() return true elseif result == "latex" then self:latexErrorBox(log) return false elseif result == "runlatex" then local urlFile = config.latexdir .. prefs.fsep .. "url.txt" if ipe.fileExists(urlFile) then self:warning("Ipe did not succeed to run Latex to process your text objects.", "Ipe tried to use Latex in the cloud.\n\n" .. "Perhaps you have no internet connectivity right now?\n\n" .. "If you have a local Latex installation, you can " .. "disable Latex-compilation in the cloud " .. "from the Help menu.") else self:warning("Ipe did not succeed to run Latex to process your text objects.", "You either have no Latex installation on your computer, " .. "or the Latex executable is not on your command path.\n\n" .. "If you prefer, you can enable Latex-compilation in the cloud " .. "from the Help menu.") end else self:warning("An error occurred during the Pdflatex run", errmsg) end end function MODEL:autoRunLatex() if self.auto_latex then self:runLatex() end end -- checks if document is modified, and asks user if it can be discarded -- returns true if object is unmodified or user confirmed discarding function MODEL:checkModified() if self:isModified() then return messageBox(self.ui:win(), "question", "The document has been modified", "Do you wish to discard the current document?", "discardcancel") == 0 else return true end end ---------------------------------------------------------------------- function MODEL:newDocument() self.pno = 1 self.vno = 1 self.file_name = nil self.undo = { {} } self.redo = {} self:markAsUnmodified() self.doc = ipe.Document() for _, w in ipairs(config.styleList) do local sheet = assert(ipe.Sheet(w)) self.doc:sheets():insert(1, sheet) end local p = self.doc:properties() p.tex = prefs.tex_engine self.doc:setProperties(p) self:setPage() self.ui:setupSymbolicNames(self.doc:sheets()) self.ui:setAttributes(self.doc:sheets(), self.attributes) self:resetGridSize() self:action_normal_size() self:setSnap() self.ui:explain("New document") end function MODEL:loadDocument(fname) local err = self:tryLoadDocument(fname) if err then self:warning("Document '" .. fname .. "' could not be opened", err) end end -- returns error message if there was an error function MODEL:tryLoadDocument(fname) local doc, err = ipe.Document(fname) if doc then self.doc = doc self.file_name = fname self.pno = 1 self.vno = 1 self.undo = { {} } self.redo = {} self:markAsUnmodified() self:setPage() self.ui:setupSymbolicNames(self.doc:sheets()) self.ui:setAttributes(self.doc:sheets(), self.attributes) self:resetGridSize() local syms = self.doc:checkStyle() self:action_normal_size() self:setSnap() self.ui:explain("Document '" .. fname .. "' loaded") if self.auto_latex then self:runLatex() end if #syms > 0 then self:warning("The document contains symbolic attributes " .. "that are not defined in the style sheet:", "* " .. table.concat(syms, "\n* ")) end return nil else return err end end function MODEL:saveDocument(fname) if not fname then fname = self.file_name end local fm = formatFromFileName(fname) if not fm then self:warning("File not saved!", "You must save as *.xml, *.ipe, or *.pdf") return end -- run Latex if format is not XML if fm ~= "xml" and not self:runLatex() then self.ui:explain("Latex error - file not saved") return end local props = self.doc:properties() props.modified = "D:" .. ipeui.currentDateTime() if props.created == "" then props.created = props.modified end props.creator = config.version self.doc:setProperties(props) if not self.doc:save(fname, fm) then self:warning("File not saved!", "Error saving the document") return end if fm == "xml" and prefs.auto_export_to_pdf then self:auto_export(fname) end self:markAsUnmodified() self.ui:explain("Saved document '" .. fname .. "'") self.file_name = fname self:setCaption() return true end function MODEL:auto_export(fname) if not self:runLatex() then self.ui:explain("Latex error - could not export to PDF!") else local ename = fname:sub(1,-4) .. "pdf" if not self.doc:save(ename, "pdf", { export=true } ) then self:warning("Auto-exporting failed", "I could not export in PDF format to file '" .. ename .. "'.") end end end ---------------------------------------------------------------------- function MODEL:autosave() -- only autosave if document has been modified if not self:isModified() then return end local f if prefs.autosave_filename:find("%%s") then if self.file_name then f = self.file_name:match(prefs.basename_pattern) or self.file_name else f = "unnamed" end f = string.format(prefs.autosave_filename, f) else f = prefs.autosave_filename end self.ui:explain("Autosaving to " .. f .. "...") if not self.doc:save(f, "xml") then messageBox(self.ui:win(), "critical", "Autosaving failed!\nFilename: " .. f) end end ---------------------------------------------------------------------- function MODEL:closeEvent() if self == first_model then first_model = nil end if self:isModified() then local r = messageBox(self.ui:win(), "question", "The document has been modified", "Do you wish to save the document?", "savediscardcancel") if r == 1 then return self:action_save() else return r == 0 end else return true end end ---------------------------------------------------------------------- -- TODO: limit on undo stack size? function MODEL:registerOnly(t) self.pristine = false -- store it on undo stack self.undo[#self.undo + 1] = t -- flush redo stack self.redo = {} self:setPage() end function MODEL:register(t) -- store selection t.original_selection = self:selection() t.original_primary = self:page():primarySelection() -- perform action t.redo(t, self.doc) self:registerOnly(t) self.ui:explain(t.label) if t.style_sheets_changed then self.ui:setupSymbolicNames(self.doc:sheets()) self.ui:setAttributes(self.doc:sheets(), self.attributes) self:resetGridSize() end end function MODEL:creation(label, obj) local t = { label=label, pno=self.pno, vno=self.vno, layer=self:page():active(self.vno), object=obj } t.undo = function (t, doc) doc[t.pno]:remove(#doc[t.pno]) end t.redo = function (t, doc) doc[t.pno]:deselectAll() doc[t.pno]:insert(nil, t.object, 1, t.layer) end self:register(t) end function MODEL:transformation(mode, m) local t = { label = mode, pno = self.pno, vno = self.vno, selection = self:selection(), original = self:page():clone(), matrix = m, undo = revertOriginal, } t.redo = function (t, doc) local p = doc[t.pno] for _,i in ipairs(t.selection) do p:transform(i, t.matrix) end end self:register(t) end function MODEL:setAttribute(prop, value) local t = { label="set attribute " .. prop .. " to " .. tostring(value), pno=self.pno, vno=self.vno, selection=self:selection(), original=self:page():clone(), property=prop, value=value, undo=revertOriginal, stroke=self.attributes.stroke, fill=self.attributes.fill, } t.redo = function (t, doc) local p = doc[t.pno] local changed = false for _,i in ipairs(t.selection) do if p:setAttribute(i, t.property, t.value, t.stroke, t.fill) then changed = true end end return changed end if (t.redo(t, self.doc)) then t.original_selection = t.selection t.original_primary = self:page():primarySelection() self:registerOnly(t) end end ---------------------------------------------------------------------- HELPER = {} HELPER.__index = HELPER function HELPER.new(model, parameters) local helper = {} setmetatable(helper, HELPER) helper.model = model helper.parameters = parameters return helper end function HELPER:message(m) self.model.ui:explain(m) end function HELPER:messageBox(text, details, buttons) return messageBox(self.model.ui:win(), nil, text, details, buttons) end function HELPER:getString(m, s) return self.model:getString(m, nil, s) end function MODEL:runIpelet(label, ipelet, num, parameters) local helper = HELPER.new(self, parameters) local t = { label="ipelet '" .. label .."'", pno=self.pno, vno=self.vno, original=self:page():clone(), undo=revertOriginal, redo=revertFinal, original_selection = self:selection(), original_primary = self:page():primarySelection(), } local need_undo = ipelet:run(num or 1, self:page(), self.doc, self.pno, self.vno, self:page():active(self.vno), self.attributes, self.snap, helper) if need_undo then t.final = self:page():clone() self:registerOnly(t) end self:setPage() end ---------------------------------------------------------------------- function MODEL:action_undo() if #self.undo <= 1 then self.ui:explain("No more undo information available") return end t = self.undo[#self.undo] table.remove(self.undo) t.undo(t, self.doc) self.ui:explain("Undo '" .. t.label .. "'") self.redo[#self.redo + 1] = t if t.pno then self.pno = t.pno elseif t.pno0 then self.pno = t.pno0 end if t.vno then self.vno = t.vno elseif t.vno0 then self.vno = t.vno0 end local p = self:page() p:deselectAll() if t.original_selection then for _, no in ipairs(t.original_selection) do p:setSelect(no, 2) end end if t.original_primary then p:setSelect(t.original_primary, 1) end self:setPage() if t.style_sheets_changed then self.ui:setupSymbolicNames(self.doc:sheets()) self.ui:setAttributes(self.doc:sheets(), self.attributes) self:resetGridSize() end end function MODEL:action_redo() if #self.redo == 0 then self.ui:explain("No more redo information available") return end t = self.redo[#self.redo] table.remove(self.redo) t.redo(t, self.doc) self.ui:explain("Redo '" .. t.label .. "'") self.undo[#self.undo + 1] = t if t.pno then self.pno = t.pno elseif t.pno1 then self.pno = t.pno1 end if t.vno then self.vno = t.vno elseif t.vno1 then self.vno = t.vno1 end self:page():deselectAll() self:setPage() if t.style_sheets_changed then self.ui:setupSymbolicNames(self.doc:sheets()) self.ui:setAttributes(self.doc:sheets(), self.attributes) self:resetGridSize() end end ---------------------------------------------------------------------- ipe-7.2.13/src/ipe/lua/actions.lua0000644000175000017500000021640013561570220016527 0ustar otfriedotfried---------------------------------------------------------------------- -- actions.lua ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] -- main entry point to all actions -- (except mouseaction, selector) -- protects call, then distributes to action_xxx method or -- saction_xxx methods (the latter are only called if a selection exists) function MODEL:action(a) local result, err = xpcall(function () self:paction(a) end, debug.traceback) if not result then messageBox(nil, "critical", "Lua error\n\n".. "Data may have been corrupted. \n" .. "Save your file!", err) end end function MODEL:paction(a1) -- work-around for bug in Qt 5.5, to be replaced with something better: local a = a1:gsub("&", "") -- print("MODEL:paction(" .. a .. ")") if a:sub(1,5) == "mode_" then self.mode = a:sub(6) self.ui:setInkMode(self.mode == "ink") if prefs.no_ink_snap then -- disable snapping in ink mode if self.mode == "ink" then self.savedsnap = {} for i,e in ipairs(MODEL.snapmodes) do self.savedsnap[e] = self.snap[e] self.snap[e] = false end elseif self.savedsnap then -- reenable snapping when switching back to another mode for i,e in ipairs(MODEL.snapmodes) do self.snap[e] = self.savedsnap[e] end self.savedsnap = nil end for i,e in ipairs(MODEL.snapmodes) do self.ui:setActionState(e, self.snap[e]) end self:setSnap() end elseif a:sub(1,4) == "snap" then self.snap[a] = self.ui:actionState(a) self:setSnap() self.ui:setFifiVisible(true) elseif a:sub(1,7) == "ipelet_" then self:action_ipelet(a) elseif a:sub(1,14) == "selectinlayer-" then self:action_select_in_layer(a:sub(15)) elseif a:sub(1,12) == "movetolayer-" then self:action_move_to_layer(a:sub(13)) else local f = self["action_" .. a] local ff = self["saction_" .. a] if f then f(self) elseif ff then if not self:page():hasSelection() then self.ui:explain("no selection") return end ff(self) else self:warning("Operation '" .. a .. "' is not yet implemented") end end end local function has_text(page) for i,obj,sel,layer in page:objects() do if sel and obj:type() == "text" then return true end end return false end -- Attribute selector function MODEL:selector(prop, value) if prop == "gridsize" or prop == "anglesize" then local abs = self.doc:sheets():find(prop, value) self.snap[prop] = abs self:setSnap() self:setPage() self.ui:setGridAngleSize(self.snap.gridsize, self.snap.anglesize) return end if prop == "markshape" then local s = "mark/" .. value local name for _, ms in ipairs(self.doc:sheets():allNames("symbol")) do if ms:sub(1, #s) == s then name = ms break end end if not name then return end -- not found value = name end self.attributes[prop] = value self.ui:setAttributes(self.doc:sheets(), self.attributes) if self:page():hasSelection() then self:setAttribute(prop, value) if prop == "textsize" or has_text(self:page()) then self:autoRunLatex() end end -- self:print_attributes() end function MODEL:set_absolute(prop, value) if self:page():hasSelection() then self:setAttribute(prop, value) end end function MODEL:layerAction(a, layer, target) local name = a local arg = nil if a:sub(-2) == "on" then name = a:sub(1,-3) arg = true elseif a:sub(-3) == "off" then name = a:sub(1,-4) arg = false else arg = target end local f = self["layeraction_" .. name] if f then f(self, layer, arg) else print("Unimplemented layer action:", a, layer, name, arg) end end function MODEL:bookmark(index) -- print("Bookmark", index) self.pno = self:findPageForBookmark(index) self.vno = 1 self:setPage() end function MODEL:findOldValue(button, btype) local old = self.attributes[button] if type(old) == "string" then old = self.doc:sheets():find(btype, old) end return old end function MODEL:absoluteButton(button) -- print("Button:", button) if button == "stroke" or button == "fill" then local old = self:findOldValue(button, "color") r, g, b = ipeui.getColor(self.ui:win(), "Select " .. button .. " color", old.r, old.g, old.b) if r then self:set_absolute(button, { r = r, g = g, b = b }); end elseif button == "pen" then local old = self:findOldValue(button, button) local d = self:getDouble("Select pen", "Pen width:", old, 0, 1000) if d then self:set_absolute(button, d) end elseif button == "textsize" then local old = self:findOldValue(button, button) local d = self:getDouble("Select text size", "Text size in points:", 10, 2, 1000) if d then self:set_absolute(button, d) self:autoRunLatex() end elseif button == "symbolsize" then local old = self:findOldValue(button, button) local d = self:getDouble("Select symbol size", "Symbol size:", old, 0, 1000) if d then self:set_absolute(button, d) end elseif button == "view" then self:action_jump_view() elseif button == "page" then self:action_jump_page() elseif button == "viewmarked" then self:action_mark_view(self.ui:actionState(button)) elseif button == "pagemarked" then self:action_mark_page(self.ui:actionState(button)) else print("Unknown button: ", button) end end function MODEL:action_jump_view() local d = self.ui:selectPage(self.doc, self.pno, self.vno) if d then self.vno = d self:setPage() end end function MODEL:action_jump_page() local d = self.ui:selectPage(self.doc, nil, self.pno) if d then self.pno = d self.vno = 1 self:setPage() end end function MODEL:action_mark_view(m) local t = { label="set view mark to " .. tostring(m), pno=self.pno, vno=self.vno, original=self:page():markedView(self.vno), final=m, } t.undo = function (t, doc) doc[t.pno]:setMarkedView(t.vno, t.original) end t.redo = function (t, doc) doc[t.pno]:setMarkedView(t.vno, t.final) end self:register(t) end function MODEL:action_mark_page(m) local t = { label="set page mark to " .. tostring(m), pno=self.pno, original=self:page():marked(), final=m, } t.undo = function (t, doc) doc[t.pno]:setMarked(t.original) end t.redo = function (t, doc) doc[t.pno]:setMarked(t.final) end self:register(t) end function MODEL:action_stop() self.ui:finishTool() end ---------------------------------------------------------------------- function MODEL:showPathStylePopup(v) local a = self.attributes local m = ipeui.Menu(self.ui:win()) local sheet = self.doc:sheets() m:add("pathmode", "Stroke && Fill", { "stroked", "strokedfilled", "filled"}, { "stroke only", "stroke && fill", "fill only" }, a.pathmode) local dashstyles = sheet:allNames("dashstyle") m:add("dashstyle", "Dash style", dashstyles, nil, a.dashstyle) local arrowsizes = sheet:allNames("arrowsize") m:add("farrowsize", "Forward arrow size", arrowsizes, nil, a.farrowsize) m:add("rarrowsize", "Reverse arrow size", arrowsizes, nil, a.rarrowsize) local arrowshapes = symbolNames(sheet, "arrow/", "(spx)") m:add("farrowshape", "Forward arrow shape", arrowshapes, arrowshapeToName, a.farrowshape) m:add("rarrowshape", "Reverse arrow shape", arrowshapes, arrowshapeToName, a.rarrowshape) local opacities = sheet:allNames("opacity") m:add("opacity", "Opacity", opacities, nil, a.opacity) m:add("strokeopacity", "Stroke opacity", opacities, nil, a.strokeopacity) local tilings = sheet:allNames("tiling") table.insert(tilings, 1, "normal") m:add("tiling", "Tiling pattern", tilings, nil, a.tiling) local gradients = sheet:allNames("gradient") table.insert(gradients, 1, "normal") m:add("gradient", "Gradient pattern", gradients, nil, a.gradient) m:add("linejoin", "Line join", { "normal", "miter", "round", "bevel" }, nil, a.linejoin) m:add("linecap", "Line cap", { "normal", "butt", "round", "square" }, nil, a.linecap) m:add("fillrule", "Fill rule", { "normal", "evenodd", "wind" }, nil, a.fillrule) local r, n, value = m:execute(v.x, v.y) if r then self:selector(r, value) end end ---------------------------------------------------------------------- function MODEL:showLayerBoxPopup(v, layer) local p = self:page() local m = ipeui.Menu(self.ui:win()) local active = p:active(self.vno) m:add("visible", "Make " .. layer .. " visible from view " .. self.vno .. " onwards") m:add("invisible", "Make " .. layer .. " invisible from view " .. self.vno .. " onwards") m:add("rename", "Rename " .. layer) m:add("delete", "Delete " .. layer) if layer ~= active then m:add("merge", "Merge into " .. active) end if p:isLocked(layer) then m:add("lockoff", "Unlock " .. layer) else m:add("lockon", "Lock " .. layer) end if p:hasSnapping(layer) then m:add("snapoff", "Disable snapping for " .. layer) else m:add("snapon", "Enable snapping for " .. layer) end local layers = p:layers() if #layers > 1 then local targets = {} local i0 = indexOf(layer,layers) if i0 ~= 1 then targets[1] = "_top_" end for i,l in ipairs(layers) do if i ~= i0 - 1 and i ~= i0 then targets[#targets + 1] = l end end m:add("move", "Move " .. layer, targets, function (i, l) if l == "_top_" then return "to top" else return "after " .. l end end) end local r, no, subitem = m:execute(v.x, v.y) if r then self:layerAction(r, layer, subitem) end end ---------------------------------------------------------------------- function MODEL:layeraction_make_visible(layer, arg, vis) local p = self:page() local label if vis then label = "make layer " .. layer .. " visible from view " .. self.vno .. " onwards" else label = "make layer " .. layer .. " invisible from view " .. self.vno .. " onwards" end local t = { label=label, pno=self.pno, vno=self.vno, original=p:clone(), layer=layer, undo=revertOriginal } t.redo = function (t, doc) for j = t.vno, doc[t.pno]:countViews() do doc[t.pno]:setVisible(j, t.layer, vis) end end self:register(t) end function MODEL:layeraction_visible(layer, arg) self:layeraction_make_visible(layer, arg, true) end function MODEL:layeraction_invisible(layer, arg) self:layeraction_make_visible(layer, arg, false) end function MODEL:layeraction_select(layer, arg) local p = self:page() local t = { label="set visibility of layer " .. layer, pno=self.pno, vno=self.vno, layer=layer, original=p:visible(self.vno, layer), visible=arg, } t.undo = function (t, doc) doc[t.pno]:setVisible(t.vno, t.layer, t.original) end t.redo = function (t, doc) doc[t.pno]:setVisible(t.vno, t.layer, t.visible) end self:register(t) self:deselectNotInView() end function MODEL:layeraction_lock(layer, arg) local p = self:page() for j = 1, p:countViews() do if layer == p:active(j) then self:warning("Cannot lock layer '" .. layer .. "'.", "Layer '" .. layer .. "' is the active layer of view " .. j .. ".") return end end local t = { label="set locking of layer " .. layer, pno=self.pno, vno=self.vno, layer=layer, original=p:isLocked(layer), locked=arg, } t.undo = function (t, doc) doc[t.pno]:setLocked(t.layer, t.original) end t.redo = function (t, doc) doc[t.pno]:setLocked(t.layer, t.locked) end self:register(t) self:deselectNotInView() self:setPage() end function MODEL:layeraction_snap(layer, arg) local p = self:page() local t = { label="set snapping in layer " .. layer, pno=self.pno, vno=self.vno, layer=layer, original=p:hasSnapping(layer), snapping=arg, } t.undo = function (t, doc) doc[t.pno]:setSnapping(t.layer, t.original) end t.redo = function (t, doc) doc[t.pno]:setSnapping(t.layer, t.snapping) end self:register(t) end function MODEL:layeraction_move(layer, arg) local p = self:page() local target = 1 local current = indexOf(layer, p:layers()) if arg ~= "_top_" then target = indexOf(arg, p:layers()) if target < current then target = target + 1 end end local t = { label="move layer " .. layer, pno=self.pno, vno=self.vno, original=p:clone(), layer=layer, target=target, undo=revertOriginal } t.redo = function (t, doc) doc[t.pno]:moveLayer(t.layer, t.target) end self:register(t) end function MODEL:layeraction_active(layer) local p = self:page() if p:isLocked(layer) then self:warning("Cannot change active layer", "A locked layer cannot be the active layer") return end local t = { label="select active layer " .. layer, pno=self.pno, vno=self.vno, original=p:active(self.vno), final=layer, } t.undo = function (t, doc) doc[t.pno]:setActive(t.vno, t.original) end t.redo = function (t, doc) doc[t.pno]:setActive(t.vno, t.final) end self:register(t) end function MODEL:layeraction_rename(layer) local p = self:page() local name = self:getString("Enter new name for layer '" .. layer .. "'", nil, layer) if not name then return end name = string.gsub(name, "%s+", "_") if indexOf(name, p:layers()) then self:warning("Cannot rename layer '" .. layer .. "'.", "The name '" .. name .. "' is already in use.") return end local t = { label="rename layer " .. layer .. " to " .. name, pno=self.pno, vno=self.vno, original=layer, final=name, } t.undo = function (t, doc) doc[t.pno]:renameLayer(t.final, t.original) for i = 1,p:countViews() do if p:active(i) == t.final then p:setActive(i, t.original) end end end t.redo = function (t, doc) doc[t.pno]:renameLayer(t.original, t.final) for i = 1,p:countViews() do if p:active(i) == t.original then p:setActive(i, t.final) end end end self:register(t) end function MODEL:layeraction_delete(layer) local p = self:page() for j = 1, p:countViews() do if layer == p:active(j) then self:warning("Cannot delete layer '" .. layer .. "'.", "Layer '" .. layer .. "' is the active layer of view " .. j .. ".") return end end local t = { label="delete layer " .. layer, pno=self.pno, vno=self.vno, original=p:clone(), layer=layer, undo=revertOriginal } t.redo = function (t, doc) local p = doc[t.pno] for i = #p,1,-1 do if p:layerOf(i) == t.layer then p:remove(i) end end p:removeLayer(t.layer) end self:register(t) end function MODEL:layeraction_merge(layer) local p = self:page() local active = p:active(self.vno) for j = 1, p:countViews() do if layer == p:active(j) then self:warning("Cannot remove layer '" .. layer .. "'.", "Layer '" .. layer .. "' is the active layer of view " .. j .. ".") return end end local t = { label="merge layer " .. layer .. " into " .. active, pno=self.pno, vno=self.vno, original=p:clone(), layer=layer, target=active, undo=revertOriginal } t.redo = function (t, doc) local p = doc[t.pno] for i = 1,#p do if p:layerOf(i) == t.layer then p:setLayerOf(i, t.target) end end p:removeLayer(t.layer) end self:register(t) end ---------------------------------------------------------------------- function MODEL:action_ipelet(a) local i = a:find("_",8) local method = tonumber(a:sub(8,i-1)) local name = a:sub(i+1) for _, ipelet in ipairs(ipelets) do if ipelet.name == name then if (ipelet.methods and ipelet.methods[method] and ipelet.methods[method].run) then ipelet.methods[method].run(self, method) else ipelet.run(self, method) end break end end self.ui:update() end ---------------------------------------------------------------------- function action_new_window() MODEL.new() end function MODEL:action_new_window() MODEL.new() end function MODEL:action_run_latex() self:runLatex() end function MODEL:action_close() self.ui:close() end function MODEL:action_auto_latex() self.auto_latex = self.ui:actionState("auto_latex") print("Auto is", self.auto_latex) end ---------------------------------------------------------------------- function MODEL:action_new() if not self:checkModified() then return end self:newDocument() end function action_open() local s, f = ipeui.fileDialog(nil, "open", "Open file", filter_ipe) if s then MODEL.new(nil, s) end end function MODEL:action_open() if not self:checkModified() then return end local s, f = ipeui.fileDialog(self.ui:win(), "open", "Open file", filter_ipe) if s then self:loadDocument(s) else self.ui:explain("Loading canceled") end end function MODEL:action_save() if not self.file_name then return self:action_save_as() else return self:saveDocument() end end function MODEL:action_save_as() local dir if self.file_name then dir = self.file_name:match(prefs.dir_pattern) end if not dir then dir = prefs.save_as_directory end local name local filter if self.file_name then name = self.file_name local fmt = formatFromFileName(self.file_name) if fmt then filter = indexOf(fmt, { "xml", "pdf" }) name = self.file_name:sub(1,-5) end end local s, f = ipeui.fileDialog(self.ui:win(), "save", "Save file as", filter_save, dir, name, filter) local fmap = { ".ipe", ".pdf" } if s then if not formatFromFileName(s) then s = s .. fmap[f] end -- Cocoa handles the overwrite dialog itself if config.toolkit ~= "cocoa" and ipe.fileExists(s) then local b = messageBox(self.ui:win(), "question", "File already exists!", "Do you wish to overwrite '" .. s .. "' ?", "okcancel") if b ~= 1 then self.ui:explain("File not saved") return end end return self:saveDocument(s) end end function MODEL:compute_rect(w, h, res) if res == V(0,0) then res = V(72.0, 72.0) end local frame = self.doc:sheets():find("layout").framesize local dx = (w * 72.0) / res.x local dy = (h * 72.0) / res.y local xfactor = 1.0 if (dx > frame.x) then xfactor = frame.x / dx end local yfactor = 1.0 if (dy > frame.y) then yfactor = frame.y / dy end local factor = yfactor if (xfactor < yfactor) then factor = xfactor end dx = dx * factor dy = dy * factor local v = 0.5 * V(frame.x - dx, frame.y - dy) local rect = ipe.Rect() rect:add(v) rect:add(v + V(dx, dy)) return rect end function MODEL:export(format) local dir if self.file_name then dir = self.file_name:match(prefs.dir_pattern) end if not dir then dir = prefs.save_as_directory end local title, filter if format == "png" then title = "Export to PNG" filter = filter_png elseif format == "eps" then title = "Export to EPS" filter = filter_eps else title = "Export to SVG" filter = filter_svg end local s, f = ipeui.fileDialog(self.ui:win(), "save", title, filter, dir) if s then if config.toolkit ~= "cocoa" and ipe.fileExists(s) then local b = messageBox(self.ui:win(), "question", "File already exists!", "Do you wish to overwrite?\n\n" .. s, "okcancel") if b ~= 1 then self.ui:explain("Document not exported") return end end self.ui:renderPage(self.doc, self.pno, self.vno, format, s, self.ui:zoom(), true, false) -- transparent, nocrop end end function MODEL:action_export_eps() self:export("eps") end function MODEL:action_export_png() self:export("png") end function MODEL:action_export_svg() self:export("svg") end function MODEL:action_insert_image() if not self.insert_image_dir and self.file_name then self.insert_image_dir = self.file_name:match(prefs.dir_pattern) end local s, f = ipeui.fileDialog(self.ui:win(), "open", "Insert image", filter_images, self.insert_image_dir) if s then self.insert_image_dir = s:match(prefs.dir_pattern) local format = "png" if s:sub(-4):lower() == ".jpg" or s:sub(-5):lower() == ".jpeg" then format = "jpeg" end local bitmap, res = ipe.readImage(s, format) if not bitmap then messageBox(self.ui:win(), "warning", "Could not read image", res, "ok") else local info = bitmap:info() local r = self:compute_rect(info.width, info.height, res) local obj = ipe.Image(r, bitmap) self:creation("insert image", obj) end else self.ui:explain("Insert image canceled") end end ---------------------------------------------------------------------- function action_manual() local url = config.docdir .. "/manual.html" if ipeui.startBrowser then if not ipeui.startBrowser("file:///" .. url) then messageBox(nil, "warning", "Manual not available!", url) end else os.execute(prefs.browser:format(url)) end end function MODEL:action_manual() action_manual() end function action_show_libraries(win) local s = "Ipe relies on the following fine pieces of software:\n" s = s .. "\n * Pdftex, Xetex, or Luatex" s = s .. "\n * " .. _VERSION .. " (" .. math.floor(collectgarbage("count")) .. " kB used)" s = s .. "\n * The font rendering library " .. config.freetype_version s = s .. "\n * The rendering library Cairo " .. config.cairo_version if config.qt_version then s = s .. "\n * The GUI toolkit Qt " .. config.qt_version end s = s .. "\n * The compression library zlib " .. config.zlib_version messageBox(win, "information", "Ipe libraries", s) end function action_show_configuration(win) local s = "" s = s .. " * Lua code: " .. package.path s = s .. "\n * Style directories:\n - " .. table.concat(config.styleDirs, "\n - ") s = s .. "\n * Styles for new documents: " .. table.concat(prefs.styles, ", ") s = s .. "\n * Autosave file: " .. prefs.autosave_filename s = s .. "\n * Save-as directory: " .. prefs.save_as_directory s = s .. "\n * Documentation: " .. config.docdir s = s .. "\n * Ipelets:\n - " .. table.concat(config.ipeletDirs, "\n - ") s = s .. "\n * Latex program path: " .. config.latexpath s = s .. "\n * Latex directory: " .. config.latexdir s = s .. "\n * Icons: " .. config.icons s = s .. "\n * External editor: " .. (prefs.external_editor or "none") messageBox(win, "information", "Ipe configuration", s) end function MODEL:action_show_configuration() action_show_configuration(self.ui:win()) end function MODEL:action_show_libraries() action_show_libraries(self.ui:win()) end function action_about_ipelets(win) local s = "" for i,v in ipairs(ipelets) do if v.label and v.about then s = s .. "### " .. v.label .. " ###\n\n" .. v.about .. "\n" end end local d = ipeui.Dialog(win, "Ipe: About the ipelets") d:add("text", "text", { read_only=true }, 1, 1) d:set("text", s) d:addButton("ok", "Ok", "accept") d:execute(prefs.latexlog_size) end function MODEL:action_about_ipelets() action_about_ipelets(self.ui:win()) end function MODEL:action_preferences() local d = ipeui.Dialog(win, "Ipe: Preferences") local s = "Ipe preferences are changed by creating a Lua source file.\n\n" s = s .. "You can find the available options in 'prefs.lua', 'shortcuts.lua', and 'mouse.lua'" s = s .. " (all on the path '" .. package.path .. "').\n\n" s = s .. "Normally, you would not modify those files directly.\n\nInstead, create a new file '" if config.platform == "win" then s = s .. config.ipeletDirs[#config.ipeletDirs] .. "\\" .. "customization.lua" else s = s .. "~/.ipe/ipelets/customization.lua" end s = s .. "', place your changes in this file, and restart Ipe.\n\n" s = s .. "For further details, please read the manual." d:add("text", "text", { read_only=true }, 1, 1) d:set("text", s) d:addButton("ok", "Ok", "accept") d:execute(prefs.latexlog_size) end function MODEL:action_keyboard() local s = prefs.keyboard if s then if config.platform == "win" then ipeui.startBrowser(s) else os.execute(s) end else self:warning("No onscreen keyboard defined.", "Edit preferences to define an onscreen keyboard.") end end function MODEL:action_developer_reload_ipelets() load_ipelets() self.ui:explain("Ipelets reloaded") end function MODEL:action_developer_list_shortcuts() local keys = {} for n,k in pairs(shortcuts) do if type(k) == "table" then for _,k1 in ipairs(k) do keys[#keys+1] = k1 end else keys[#keys+1] = k end end table.sort(keys) printTable(keys) local dupl = 0 local prev = nil for _, k in ipairs(keys) do if k == prev then print("Duplicate shortcut assignment: ", k) dupl = dupl + 1 end prev = k end print(dupl, " duplicate shortcuts found") end function MODEL:action_cloud_latex() local d = ipeui.Dialog(win, "Ipe: Latex in the cloud") local urlFile = config.latexdir .. "url.txt" if ipe.fileExists(urlFile) then local f = ipe.openFile(urlFile, "r") local url = f:read("a") url = url:match("^(%S+)%s*$") f:close() d:add("label1", "label", { label="You are currently using the following online Latex-compilation service:" }, 1, 1, 1, 3) d:add("url", "label", { label=url }, 2, 2) d:add("label2", "label", { label="Please keep in mind that the contents of all your text objects " .. "is transmitted to this service at every Latex compilation." }, 3, 1, 1, 3) d:add("label3", "label", { label = "You may not want to use online compilation for confidential information." }, 4, 1, 1, 3) d:addButton("ok", "Disable online compilation", "accept") d:addButton("cancel", "&Cancel", "reject") if d:execute() then os.remove(urlFile) end else d:add("label1", "label", { label="Would you like to use the following online Latex-compilation service?" }, 1, 1, 1, 3) d:add("url", "label", { label=prefs.latex_service_url }, 2, 2) d:add("label2", "label", { label="Please keep in mind that the contents of all your text objects " .. "is transmitted to this service at every Latex compilation." }, 3, 1, 1, 3) d:add("label3", "label", { label = "You may not want to use online compilation for confidential information." }, 4, 1, 1, 3) d:addButton("ok", "Enable online compilation", "accept") d:addButton("cancel", "&Cancel", "reject") if d:execute() then local f = ipe.openFile(urlFile, "w") f:write(prefs.latex_service_url, "\n") f:close() end end end ---------------------------------------------------------------------- function MODEL:setOrigin(snapping) self.snap.origin = self.ui:simpleSnapPos() self.snap.with_axes = true self.ui:setActionState("show_axes", self.snap.with_axes) if snapping then self.snap.snapangle = true self.ui:setActionState("snapangle", true) end self:setSnap() self.ui:setFifiVisible(true) self.ui:update() end function MODEL:action_set_origin() self:setOrigin(false) end function MODEL:action_set_origin_snap() self:setOrigin(true) end function MODEL:action_show_axes() self.snap.with_axes = self.ui:actionState("show_axes"); if not self.snap.with_axes then self.snap.snapangle = false self.ui:setActionState("snapangle", false) end self:setSnap() self.ui:update() end function MODEL:action_set_direction() self.snap.with_axes = true; self.ui:setActionState("show_axes", self.snap.with_axes) self.snap.orientation = (self.ui:simpleSnapPos() - self.snap.origin):angle() self.ui:setSnap(self.snap) self.ui:update() end local function find_arc_under_point_in_object(obj, m, pos) if obj:type() == "group" then local m1 = m * obj:matrix() for i = 1,obj:count() do local t = obj:elementType(i) if t == "path" or t == "group" then local obj1 = obj:element(i) local r = ipe.Rect() obj1:addToBBox(r, m1) if r:contains(pos) then local arc = find_arc_under_point_in_object(obj1, m1, pos) if arc then return arc end end end end elseif obj:type() == "path" then local m1 = m * obj:matrix() local shape = obj:shape() for _, sp in ipairs(shape) do if sp.type == "ellipse" then local m2 = m1 * sp[1] local post = m2:inverse() * pos if math.abs(post:sqLen() - 1.0) < 1e-3 then return m2 end elseif sp.type == "curve" then for i = 1,#sp do if sp[i].type == "arc" then local m2 = m1 * sp[i].arc:matrix() local post = m2:inverse() * pos if math.abs(post:sqLen() - 1.0) < 1e-3 then return m2 end end end end end end end local function find_arc_under_point(p, pos) local m = ipe.Matrix() for i, obj, sel, layer in p:objects() do if p:bbox(i):contains(pos) then local arc = find_arc_under_point_in_object(obj, m, pos) if arc then return arc end end end end function MODEL:action_set_tangent_direction() local p = self:page() local pos, dir = p:findEdge(self.vno, self.ui:unsnappedPos()) if not pos then self.ui:explain("Mouse is not on an edge") return false end local arc = find_arc_under_point(p, pos) if not arc then self.ui:explain("Mouse is not on a circular arc") return false end local p = arc:inverse() * self.snap.origin local d = p:len() if d < 1.0 then self.ui:explain("Origin is inside the ellipse") return false end local r = math.sqrt(d * d - 1.0) local c = ipe.Arc(ipe.Matrix(r, 0, 0, r, p.x, p.y)) local qs = c:intersect(ipe.Arc(ipe.Matrix())) if #qs ~= 2 then return false end local pos1 = arc:inverse() * pos local q = qs[1] if (pos1 - qs[2]):sqLen() < (pos1 - q):sqLen() then q = qs[2] end self.snap.with_axes = true; self.ui:setActionState("show_axes", self.snap.with_axes) self.snap.orientation = (arc * q - self.snap.origin):angle() self.ui:setSnap(self.snap) self.ui:update() return true end function MODEL:action_reset_direction() self.snap.orientation = 0 self:setSnap() self.ui:update() end function MODEL:setLine(snapping) local origin, dir = self:page():findEdge(self.vno, self.ui:unsnappedPos()) if not origin then self.ui:explain("Mouse is not on an edge") else self.snap.with_axes = true; self.ui:setActionState("show_axes", self.snap.with_axes) self.snap.orientation = dir self.snap.origin = origin self.ui:update() if snapping then self.snap.snapangle = true self.ui:setFifiVisible(true) self.ui:setActionState("snapangle", true) end self:setSnap() end end function MODEL:action_set_line() self:setLine(false) end function MODEL:action_set_line_snap() self:setLine(true) end ---------------------------------------------------------------------- function MODEL:action_select_all() local p = self:page() for i,obj,sel,layer in p:objects() do if not sel and p:visible(self.vno, i) and not p:isLocked(layer) then self:page():setSelect(i, 2) end end p:ensurePrimarySelection() self.ui:update(false) end function MODEL:action_select_in_active_layer() local p = self:page() local active = p:active(self.vno) p:deselectAll() for i,obj,sel,layer in p:objects() do if layer == active then self:page():setSelect(i, 2) end end p:ensurePrimarySelection() self.ui:update(false) end function MODEL:action_select_in_layer(lay) local p = self:page() p:deselectAll() for i,obj,sel,layer in p:objects() do if layer == lay then self:page():setSelect(i, 2) end end p:ensurePrimarySelection() self.ui:update(false) end function MODEL:saction_move_to_active_layer() local p = self:page() local active = p:active(self.vno) local t = { label="move to layer " .. active, pno = self.pno, vno = self.vno, selection=self:selection(), original=p:clone(), active=active, undo=revertOriginal, } t.redo = function (t, doc) local p = doc[t.pno] for _,i in ipairs(t.selection) do p:setLayerOf(i, t.active) end end self:register(t) end function MODEL:action_move_to_layer(lay) local p = self:page() if not p:hasSelection() then self.ui:explain("no selection") return end local t = { label="move to layer " .. lay, pno = self.pno, vno = self.vno, selection=self:selection(), original=p:clone(), layer=lay, undo=revertOriginal, } t.redo = function (t, doc) local p = doc[t.pno] for _,i in ipairs(t.selection) do p:setLayerOf(i, t.layer) end end self:register(t) end ---------------------------------------------------------------------- function MODEL:action_grid_visible() self.snap.grid_visible = self.ui:actionState("grid_visible"); self:setSnap() self.ui:update() end function MODEL:action_pretty_display() self.ui:setPretty(self.ui:actionState("pretty_display")); self.ui:update() end function MODEL:action_zoom_in() local nzoom = prefs.zoom_factor * self.ui:zoom() if nzoom > prefs.max_zoom then nzoom = prefs.max_zoom end self.ui:setZoom(nzoom) self.ui:update() end function MODEL:action_zoom_out() local nzoom = self.ui:zoom() / prefs.zoom_factor if nzoom < prefs.min_zoom then nzoom = prefs.min_zoom end self.ui:setZoom(nzoom) self.ui:update() end -- kind is usually 0 except: -- kind == 1 on OSX when using a trackpad, -- and kind == 2 when holding control function MODEL:wheel_zoom(xdelta, ydelta, kind) -- print("wheel_zoom", xdelta, ydelta, kind) local zoom = self.ui:zoom() local opts = prefs.scroll if kind == 1 then opts = prefs.trackpad_scroll end if kind ~= 2 and opts.pan then local p = self.ui:pan() local ppd = opts.pixel_per_degree / zoom p = p + V(opts.direction.x * xdelta * ppd, opts.direction.y * ydelta * ppd) self.ui:setPan(p) else local origin = self.ui:unsnappedPos() local offset = zoom * (self.ui:pan() - origin) local base = opts.zoom_per_degree local nzoom = zoom * base ^ ydelta if nzoom > prefs.max_zoom then nzoom = prefs.max_zoom end if nzoom < prefs.min_zoom then nzoom = prefs.min_zoom end self.ui:setZoom(nzoom) self.ui:setPan(origin + (1/nzoom) * offset) end self.ui:update() end -- Change resolution to 72 dpi and maximize interesting visible area. -- As suggested by Rene: -- 1) scale to the proper size, with the center of the canvas as the -- origin of the scaling. -- 2) If there is a horizontal and/or vertical translation that makes -- a larger part of the *bounding box* of the objects visible, then -- translate (and maximize the part of the bounding box that is -- visible). -- 3) If there is a horizontal and/or vertical translation that makes -- a larger part of the paper visible, then translate (and maximize -- the part of the paper that is visible), under the restriction -- that no part of the bounding box of the objects may be moved -- `out of sight' in this step. (Note that there may be objects -- outside the paper). local function adjustPan(cmin, cmax, omin, omax, pmin, pmax) local dx = 0; -- if objects stick out on both sides, there is nothing we can do if omin <= cmin and omax >= cmax then return dx end if omax > cmax and omin > cmin then -- we can see more objects if we shift canvas right dx = math.min(omin - cmin, omax - cmax) elseif omin < cmin and omax < cmax then -- we can see more objects if we shift canvas left dx = -math.min(cmin - omin, cmax - omax) end -- shift canvas cmin = cmin + dx cmax = cmax + dx -- if canvas fully contained in media, done if pmin <= cmin and pmax >= cmax then return dx end -- if media contained in canvas, can't improve if cmin < pmin and pmax < cmax then return dx end if pmin > cmin then -- improvement possible by shifting canvas right if omin > cmin then dx = dx + math.min(omin - cmin, pmin - cmin, pmax - cmax) end else -- improvement possible by shifting canvas left if omax < cmax then dx = dx - math.min(cmax - omax, cmax - pmax, cmin - pmin) end end return dx end function MODEL:action_normal_size() local p = self:page() self.ui:setZoom(prefs.normal_resolution / 72.0) local layout = self.doc:sheets():find("layout") local paper = ipe.Rect() paper:add(-layout.origin) paper:add(-layout.origin + layout.papersize) local bbox = ipe.Rect() for i = 1,#p do bbox:add(p:bbox(i)) end local canvas = ipe.Rect() canvas:add(self.ui:pan() - 0.5 * self.ui:canvasSize()) canvas:add(self.ui:pan() + 0.5 * self.ui:canvasSize()) local pan = V(adjustPan(canvas:left(), canvas:right(), bbox:left(), bbox:right(), paper:left(), paper:right()), adjustPan(canvas:bottom(), canvas:top(), bbox:bottom(), bbox:top(), paper:bottom(), paper:top())) self.ui:setPan(self.ui:pan() + pan) self.ui:update() end function MODEL:action_fit_page() local layout = self.doc:sheets():find("layout") local box = ipe.Rect() box:add(-layout.origin - V(2,2)) box:add(-layout.origin + layout.papersize + V(2,2)) self:fitBox(box); end function MODEL:action_fit_width() local layout = self.doc:sheets():find("layout") local box = ipe.Rect() local y0 = self.ui:pan().y box:add(V(-layout.origin.x - 2, y0 - 2)) box:add(V(-layout.origin.x + layout.papersize.x + 2, y0 + 2)) self:fitBox(box); end function MODEL:action_fit_top() self:action_fit_width() -- sets zoom and x-pan correctly local layout = self.doc:sheets():find("layout") local x0 = self.ui:pan().x local ht = 0.5 * self.ui:canvasSize().y / self.ui:zoom() local y0 = -layout.origin.y + layout.papersize.y + 2 - ht self.ui:setPan(V(x0, y0)) end function MODEL:action_fit_objects() local box = ipe.Rect() local m = ipe.Matrix() local p = self:page() for i,obj,_,layer in p:objects() do if p:visible(self.vno, i) then obj:addToBBox(box, m, false) end end self:fitBox(box); end function MODEL:saction_fit_selection() local box = ipe.Rect() local m = ipe.Matrix() local p = self:page() for i,obj,sel,_ in p:objects() do if sel then obj:addToBBox(box, m, false) end end self:fitBox(box); end function MODEL:action_pan_here() v = self.ui:unsnappedPos() self.ui:setPan(v) self.ui:update() end ---------------------------------------------------------------------- function MODEL:action_next_view() self:nextView(1) self:setPage() end function MODEL:action_previous_view() self:nextView(-1) self:setPage() end function MODEL:action_first_view() self.vno = 1 self:setPage() end function MODEL:action_last_view() self.vno = self:page():countViews() self:setPage() end function MODEL:action_new_view() local t = { label="new view", pno = self.pno, vno0 = self.vno, vno1 = self.vno + 1, } t.undo = function (t, doc) doc[t.pno]:removeView(t.vno1) end t.redo = function (t, doc) local p = doc[t.pno] p:insertView(t.vno1, p:active(t.vno0)) for i,layer in ipairs(p:layers()) do p:setVisible(t.vno1, layer, p:visible(t.vno0, layer)) end end self:register(t) self:nextView(1) self:setPage() end function MODEL:action_new_layer_view() local t = { label="new layer and view", pno = self.pno, vno0 = self.vno, vno1 = self.vno + 1, } t.undo = function (t, doc) doc[t.pno]:removeLayer(t.layer) doc[t.pno]:removeView(t.vno1) end t.redo = function (t, doc) local p = doc[t.pno] p:insertView(t.vno1, p:active(t.vno0)) for i,layer in ipairs(p:layers()) do p:setVisible(t.vno1, layer, p:visible(t.vno0, layer)) end t.layer = doc[t.pno]:addLayer() p:setVisible(t.vno1, t.layer, true) p:setActive(t.vno1, t.layer) end self:register(t) self:nextView(1) self:setPage() end function MODEL:action_delete_view() local p = self:page() if p:countViews() < 2 then self.ui:explain("cannot delete single view of a page") return end local t = { label="delete view", pno = self.pno, vno0 = self.vno, vno1 = self.vno, original = p:clone(), undo = revertOriginal, } if self.vno == p:countViews() then t.vno1 = self.vno - 1 end t.redo = function (t, doc) doc[t.pno]:removeView(t.vno0) end t.redo(t, self.doc) self.vno = t.vno1 self:registerOnly(t) self.ui:explain(t.label) end function MODEL:action_edit_view() local p = self:page() local effect0 = p:effect(self.vno) local name0 = p:viewName(self.vno) local list = self.doc:sheets():allNames("effect") table.insert(list, 1, "normal") local d = ipeui.Dialog(self.ui:win(), "Edit view") local label = "View " .. self.vno .. " of " .. p:countViews() d:add("label", "label", { label=label }, 1, 1, 2, 1) d:add("name-label", "label", { label="Name" }, 0, 1) d:add("name", "input", {}, -1, 2) d:add("effect-label", "label", { label="Effect" }, 0, 1) d:add("combo", "combo", list, -1, 2) d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:set("name", name0) d:set("combo", indexOf(effect0, list)) if not d:execute() then return end local name1 = d:get("name") local effect1 = list[d:get("combo")] local t = { label="modify view " .. self.vno, pno = self.pno, vno = self.vno, name0 = name0, effect0 = effect0, name1 = name1, effect1 = effect1, } t.undo = function (t, doc) p:setEffect(t.vno, t.effect0) p:setViewName(t.vno, t.name0) end t.redo = function (t, doc) p:setEffect(t.vno, t.effect1) p:setViewName(t.vno, t.name1) end self:register(t) end ---------------------------------------------------------------------- function MODEL:action_next_page() self:nextPage(1) self:setPage() end function MODEL:action_previous_page() self:nextPage(-1) self:setPage() end function MODEL:action_first_page() self.pno = 1 self.vno = 1 self:setPage() end function MODEL:action_last_page() self.pno = #self.doc self.vno = 1 self:setPage() end function MODEL:action_copy_page() local data = self:page():xml("ipepage") self.ui:setClipboard(data) self.ui:explain("page copied to clipboard") end function MODEL:action_cut_page() if #self.doc == 1 then self:warning("Cannot cut page", "This is the only page of the document.") return end local t = { label="cut page " .. self.pno, pno0 = self.pno, pno1 = self.pno, vno = 1, original = self:page():clone(), } if self.pno == #self.doc then t.pno1 = self.pno - 1 end t.undo = function (t, doc) doc:insert(t.pno0, t.original) end t.redo = function (t, doc) doc:remove(t.pno0) end t.redo(t, self.doc) self.pno = t.pno1 self.vno = 1 self:registerOnly(t) self.ui:explain(t.label .. " and copied to clipboard") local data = t.original:xml("ipepage") self.ui:setClipboard(data) end function MODEL:action_new_page() local t = { label="new page", pno0 = self.pno, pno1 = self.pno + 1, vno0 = self.vno, vno1 = 1, } t.undo = function (t, doc) doc:remove(t.pno1) end t.redo = function (t, doc) doc:insert(t.pno1, ipe.Page()) end self:register(t) self:nextPage(1) self:setPage() end function MODEL:action_paste_page() local data = self.ui:clipboard() if data:sub(1,9) ~= "" then self:warning("No Ipe page to paste") return end local p = ipe.Page(data) if not p then self:warning("Could not parse Ipe page on clipboard") return end local t = { label="paste page", pno0 = self.pno, pno1 = self.pno + 1, vno0 = self.vno, vno1 = 1, page = p, } t.undo = function (t, doc) doc:remove(t.pno1) end t.redo = function (t, doc) doc:insert(t.pno1, t.page) end self:register(t) self:nextPage(1) self:setPage() end function MODEL:action_delete_page() if #self.doc == 1 then self:warning("Cannot delete page", "This is the only page of the document.") return end local t = { label="delete page " .. self.pno, pno0 = self.pno, pno1 = self.pno, vno = 1, original = self:page():clone(), } if self.pno == #self.doc then t.pno1 = self.pno - 1 end t.undo = function (t, doc) doc:insert(t.pno0, t.original) end t.redo = function (t, doc) doc:remove(t.pno0) end t.redo(t, self.doc) self.pno = t.pno1 self.vno = 1 self:registerOnly(t) self.ui:explain(t.label) end local function update_dialog(d, sec) local on = d:get("t" .. sec) d:setEnabled(sec, not on) if on then d:set(sec, "") end end function MODEL:action_edit_title() local d = ipeui.Dialog(self.ui:win(), "Ipe: Edit page title and sections") d:add("label1", "label", { label="Page title"}, 1, 1, 1, 4) d:add("title", "text", {}, 0, 1, 1, 4) d:add("label2", "label", { label="Sections"}, 0, 1, 1, 4) d:add("label3", "label", { label="Section:" }, 0, 1) d:add("tsection", "checkbox", { label="Use &title", action=function (d) update_dialog(d, "section") end } , -1, 2) d:add("section", "input", {}, 0, 2, 1, 3) d:add("label4", "label", { label="Subsection:" }, 0, 1) d:add("tsubsection", "checkbox", { label="Use titl&e", action=function (d) update_dialog(d, "subsection") end } , -1, 2) d:add("subsection", "input", {}, 0, 2, 1, 3) d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("row", 2, 1) d:setStretch("column", 2, 1) -- setup original values local ti = self:page():titles() d:set("title", ti.title) if ti.section then d:set("section", ti.section) else d:set("tsection", true) d:setEnabled("section", false) end if ti.subsection then d:set("subsection", ti.subsection) else d:set("tsubsection", true) d:setEnabled("subsection", false) end if not d:execute() then return end local final = { title = d:get("title") } if not d:get("tsection") then final.section = d:get("section") end if not d:get("tsubsection") then final.subsection = d:get("subsection") end if prefs.automatic_use_title and ti.title ~= final.title then final.section = true final.tsection = true end local t = { label="change title and sections of page " .. self.pno, pno = self.pno, vno = self.vno, original = ti, final = final, } t.undo = function (t, doc) doc[t.pno]:setTitles(t.original) end t.redo = function (t, doc) doc[t.pno]:setTitles(t.final) end self:register(t) self:autoRunLatex() end function MODEL:action_edit_notes() local d = ipeui.Dialog(self.ui:win(), "Ipe: Edit page notes") d:add("label1", "label", { label="Page notes"}, 1, 1) d:add("notes", "text", {}, 0, 1) d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("row", 2, 1) d:setStretch("column", 1, 1) -- setup original values local n = self:page():notes() d:set("notes", n) if not d:execute() then return end local final = d:get("notes") if string.match(final, "^%s*$") then final = "" end local t = { label="change notes on page " .. self.pno, pno = self.pno, vno = self.vno, original = n, final = final, } t.undo = function (t, doc) doc[t.pno]:setNotes(t.original) end t.redo = function (t, doc) doc[t.pno]:setNotes(t.final) end self:register(t) end -- rearrange pages of document -- new order is given by arr -- 0 entries in arr are taken from newpages -- returns list of pages that remained unused function arrange_pages(doc, arr, newpages) -- take all pages from document local pg = {} while #doc > 0 do pg[#pg+1] = doc:remove(1) end -- insert pages again in new order for i = 1,#arr do local no = arr[i] if no > 0 then doc:append(pg[no]) -- clones the page pg[no] = nil -- mark as used else doc:append(table.remove(newpages, 1)) end end -- return unused pages local unused = {} for i = 1,#pg do if pg[i] then unused[#unused+1] = pg[i] end end return unused end function MODEL:action_page_sorter() local arr = self.ui:pageSorter(self.doc) if not arr then return end -- canceled if #arr == 0 then self:warning("You cannot delete all pages of the document") return end printTable(arr) -- compute reverse 'permutation' local rev = {} for i = 1,#self.doc do rev[i] = 0 end for i = 1,#arr do rev[arr[i]] = i end local t = { label="rearrangement of pages", pno = 1, vno = 1, arr = arr, rev = rev, } t.undo = function (t, doc) arrange_pages(doc, t.rev, t.deleted) end t.redo = function (t, doc) t.deleted = arrange_pages(doc, t.arr, {}) end self.pno = 1 self.vno = 1 self:register(t) end function MODEL:action_toggle_notes() self.ui:showTool("notes", self.ui:actionState("toggle_notes")) self.ui:setNotes(self:page():notes()) end function MODEL:action_toggle_bookmarks() self.ui:showTool("bookmarks", self.ui:actionState("toggle_bookmarks")) self:setBookmarks() end ---------------------------------------------------------------------- function MODEL:action_new_layer() local t = { label="new layer", pno = self.pno, vno = self.vno, } t.redo = function (t, doc) t.layer = doc[t.pno]:addLayer() end t.undo = function (t, doc) doc[t.pno]:removeLayer(t.layer) end self:register(t) end function MODEL:action_rename_active_layer() local p = self:page() local active = p:active(self.vno) self:layeraction_rename(active) end ---------------------------------------------------------------------- function MODEL:saction_delete() local t = { label="delete", pno = self.pno, vno = self.vno, selection=self:selection(), original=self:page():clone(), undo=revertOriginal, } t.redo = function (t, doc) local p = doc[t.pno] for i = #t.selection,1,-1 do p:remove(t.selection[i]) end end self:register(t) end function MODEL:saction_edit_as_xml() local prim = self:page():primarySelection() local xml = self:page()[prim]:xml() local d = ipeui.Dialog(self.ui:win(), "Edit as XML") d:add("xml", "text", { syntax="xml", focus=true }, 1, 1) addEditorField(d, "xml") d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("row", 1, 1); d:set("xml", xml) if prefs.auto_external_editor then externalEditor(d, "xml") end if ((prefs.auto_external_editor and prefs.editor_closes_dialog) or d:execute(prefs.editor_size)) then local obj = ipe.Object(d:get("xml")) if not obj then self:warning("Cannot parse XML") return end local t = { label="edit object in XML", pno = self.pno, vno = self.vno, primary = prim, original = self:page()[prim]:clone(), final = obj, } t.undo = function (t, doc) doc[t.pno]:replace(t.primary, t.original) end t.redo = function (t, doc) doc[t.pno]:replace(t.primary, t.final) end self:register(t) if obj:type() == "text" then self:autoRunLatex() end end end ---------------------------------------------------------------------- function MODEL:saction_group() local p = self:page() local selection = self:selection() local elements = {} for _,i in ipairs(selection) do elements[#elements + 1] = p[i]:clone() end local final = ipe.Group(elements) p:deselectAll() local t = { label="group", pno = self.pno, vno = self.vno, original = p:clone(), selection = selection, layer = p:active(self.vno), final = final, undo = revertOriginal, } t.redo = function (t, doc) local p = doc[t.pno] for i = #t.selection,1,-1 do p:remove(t.selection[i]) end p:insert(nil, t.final, 1, t.layer) end self:register(t) end -- does not pass pinning and allowed transformation to elements function MODEL:saction_ungroup() local p = self:page() local prim = p:primarySelection() if p[prim]:type() ~= "group" then self.ui:explain("primary selection is not a group") return end p:deselectAll() local t = { label="ungroup", pno = self.pno, vno = self.vno, original = p[prim]:clone(), primary = prim, originalLayer = p:layerOf(prim), layer = p:active(self.vno), elements = p[prim]:elements(), matrix = p[prim]:matrix(), } t.undo = function (t, doc) local p = doc[t.pno] for i = 1,#t.elements do p:remove(#p) end p:insert(t.primary, t.original, nil, t.originalLayer) end t.redo = function (t, doc) local p = doc[t.pno] p:remove(t.primary) for _,obj in ipairs(t.elements) do p:insert(nil, obj, 2, t.layer) p:transform(#p, t.matrix) end p:ensurePrimarySelection() end self:register(t) end function MODEL:saction_front() local p = self:page() local selection = self:selection() local t = { label="front", pno = self.pno, vno = self.vno, original = p:clone(), selection = selection, primary = indexOf(p:primarySelection(), selection), undo = revertOriginal, } p:deselectAll() t.redo = function (t, doc) local p = doc[t.pno] local r,l = extractElements(p, t.selection) for i,obj in ipairs(r) do p:insert(nil, obj, (i == t.primary) and 1 or 2, l[i]) end end self:register(t) end function MODEL:saction_back() local p = self:page() local selection = self:selection() local t = { label="back", pno = self.pno, vno = self.vno, original = p:clone(), selection = selection, primary = indexOf(p:primarySelection(), selection), undo = revertOriginal, } p:deselectAll() t.redo = function (t, doc) local p = doc[t.pno] local r,l = extractElements(p, t.selection) for i,obj in ipairs(r) do p:insert(i, obj, (i == t.primary) and 1 or 2, l[i]) end end self:register(t) end function MODEL:saction_duplicate() local p = self:page() local t = { label="duplicate", pno = self.pno, vno = self.vno, selection = self:selection(), primary = self:page():primarySelection(), layer = self:page():active(self.vno), } t.undo = function (t, doc) local p = doc[t.pno] for i = 1,#t.selection do p:remove(#p) end end t.redo = function (t, doc) local p = doc[t.pno] for _,i in ipairs(t.selection) do p:insert(nil, p[i]:clone(), 2, t.layer) p:setSelect(i, nil) if i == t.primary then p:setSelect(#p, 1) end end end self:register(t) end local function moveTargetToSource (t, doc) local p = doc[t.pno] local target = (t.target > t.source) and (t.target - 1) or t.target local obj = p[target]:clone() local layer = p:layerOf(target) p:remove(target) p:insert(t.source, obj, nil, layer) end local function moveSourceToTarget (t, doc) local p = doc[t.pno] local obj = p[t.source]:clone() local layer = p:layerOf(t.source) p:insert(t.target, obj, t.select, layer) p:remove((t.target < t.source) and (t.source + 1) or t.source) end -- Move selection one step forward -- In other words: -- take object in front of nearest selection and -- place it behind furthest selection function MODEL:saction_forward() local p = self:page() local selection = self:selection() local furthest = nil local nearest = nil for i,obj,sel,layer in p:objects() do if sel then nearest = i if not furthest then furthest = i end end end if nearest == #p then self.ui:explain("already at front") return end local t = { label="move selection forward", pno = self.pno, vno = self.vno, source = nearest + 1, target = furthest, select = nil, undo = moveTargetToSource, redo = moveSourceToTarget, } self:register(t) end -- Move selection one step back -- In other words: -- take object behind furthest selection and -- place it in front of nearest selection function MODEL:saction_backward() local p = self:page() local selection = self:selection() local furthest = nil local nearest = nil for i,obj,sel,layer in p:objects() do if sel then nearest = i if not furthest then furthest = i end end end if furthest == 1 then self.ui:explain("already at back") return end local t = { label="move selection backward", pno = self.pno, vno = self.vno, source = furthest - 1, target = nearest + 1, select = nil, undo = moveTargetToSource, redo = moveSourceToTarget, } self:register(t) end -- Moves the primary selection just before the highest secondary. function MODEL:saction_before() local p = self:page() local prim = p:primarySelection() local sec = nil for i,obj,sel,layer in p:objects() do if sel == 2 then sec = i end end if not sec then self.ui:explain("no secondary selection") return end if prim == sec + 1 then self.ui:explain("nothing to do") return end local t = { label="move just before secondary selection", pno = self.pno, vno = self.vno, source = prim, target = sec + 1, select = 1, undo = moveTargetToSource, redo = moveSourceToTarget, } self:register(t) end -- Moves the primary selection just behind the lowest secondary. function MODEL:saction_behind() local p = self:page() local prim = p:primarySelection() local sec = nil for i,obj,sel,layer in p:objects() do if sel == 2 then sec = i break end end if not sec then self.ui:explain("no secondary selection") return end if prim == sec - 1 then self.ui:explain("nothing to do") return end local t = { label="move just behind secondary selection", pno = self.pno, vno = self.vno, source = prim, target = sec, select = 1, undo = moveTargetToSource, redo = moveSourceToTarget, } self:register(t) end function MODEL:selectionWithCursor() local data = self:page():xml("ipeselection") assert(data:sub(1,13) == "\n') f:write('\n') f:write(data) f:close() dd.model.ui:explain("Stylesheet saved to " .. s) end end function MODEL:action_style_sheets() local sheets = self.doc:sheets() local dd = { list = {}, model = self, modified = false } for i = 1,sheets:count() do dd.list[i] = sheets:sheet(i):clone() end local d = ipeui.Dialog(self.ui:win(), "Ipe style sheets") d:add("label1", "label", { label="Style sheets"}, 1, 1, 1, 4) d:add("list", "list", sheets_namelist(dd.list), 2, 1, 7, 3) d:add("add", "button", { label="&Add", action=function (d) sheets_add(d, dd) end }, 2, 4) d:add("del", "button", { label="Del", action=function (d) sheets_del(d, dd) end }, 3, 4) d:add("edit", "button", { label="Edit", action=function (d) sheets_edit(d, dd) end }, 4, 4) d:add("up", "button", { label="&Up", action=function (d) sheets_up(d, dd) end }, 5, 4) d:add("down", "button", { label="&Down", action=function (d) sheets_down(d, dd) end }, 6, 4) d:add("save", "button", { label="&Save", action=function (d) sheets_save(d, dd) end }, 7, 4) d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("column", 2, 1) if not d:execute() or not dd.modified then return end local t = { label="modify style sheets", final = ipe.Sheets(), style_sheets_changed = true, } for i,s in ipairs(dd.list) do t.final:insert(i, s) end t.undo = function (t, doc) t.final = doc:replaceSheets(t.original) end t.redo = function (t, doc) t.original = doc:replaceSheets(t.final) end self:register(t) self:action_check_style() end ---------------------------------------------------------------------- function MODEL:action_document_properties() local engines = { "default", "pdftex", "xetex", "luatex" } local p = self.doc:properties() local d = ipeui.Dialog(self.ui:win(), "Ipe document properties") d:add("label1", "label", { label="Title"}, 1, 1) d:add("title", "input", {}, -1, 2, 1, 6) d:add("label2", "label", { label="Author"}, 0, 1) d:add("author", "input", {}, -1, 2, 1, 6) d:add("label3", "label", { label="Subject"}, 0, 1) d:add("subject", "input", {}, -1, 2, 1, 6) d:add("label4", "label", { label="Keywords"}, 0, 1) d:add("keywords", "input", {}, -1, 2, 1, 6) d:add("label5", "label", { label="Latex engine"}, 0, 1) d:add("tex", "combo", engines, -1, 2, 1, 6) d:add("label6", "label", { label="Latex preamble"}, 0, 1) d:add("preamble", "text", {}, -1, 2, 2, 6) d:add("label7", "label", { label="Page mode"}, 8, 1) d:add("fullscreen", "checkbox", { label="&Full screen"}, -1, 2) d:add("numberpages", "checkbox", { label="&Number pages"}, -1, 3) d:add("label8", "label", { label="Created"}, 0, 1) d:add("created", "label", { label="" }, -1, 2) d:add("label9", "label", { label="Modified"}, 0, 1) d:add("modified", "label", { label="" }, -1, 2) d:add("label10", "label", { label="Creator" }, 0, 1) d:add("creator", "label", { label="" }, -1, 2) d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("column", 5, 1) d:setStretch("row", 7, 1) addEditorField(d, "preamble") for n in pairs(p) do d:set(n, p[n]) end if not d:execute() then return end local t = { label="modify document properties", original = p, final = {}, } for n in pairs(p) do if n == "creator" or n == "created" or n == "modified" then t.final[n] = p[n] elseif n == "tex" then t.final[n] = engines[d:get(n)] else t.final[n] = d:get(n) end end t.undo = function (t, doc) doc:setProperties(t.original) end t.redo = function (t, doc) doc:setProperties(t.final) end self:register(t) end ---------------------------------------------------------------------- function MODEL:saction_set_link_action() local p = self:page() local prim = p:primarySelection() local obj = p[prim] assert(obj:type() == "group") local link_action = self:getString("Enter link action", nil, obj:text()) if not link_action then return end if link_action:match("^%s*$)") then link_action = "" end local t = { label="set link action", pno=self.pno, vno=self.vno, primary=prim, original=obj:clone(), link_action=link_action, } t.undo = function (t, doc) doc[t.pno]:replace(t.primary, t.original) end t.redo = function (t, doc) doc[t.pno][t.primary]:setText(t.link_action) end self:register(t) end function MODEL:saction_remove_clipping() local p = self:page() local prim = p:primarySelection() local obj = p[prim] assert(obj:type() == "group") local t = { label="remove clipping", pno=self.pno, vno=self.vno, primary=prim, original=obj:clone(), } t.undo = function (t, doc) doc[t.pno]:replace(t.primary, t.original) end t.redo = function (t, doc) doc[t.pno][t.primary]:setClip() doc[t.pno]:invalidateBBox(t.primary) end self:register(t) end function MODEL:saction_extract_clipping() local p = self:page() local prim = p:primarySelection() local obj = p[prim] assert(obj:type() == "group") local shape = obj:clip() transformShape(obj:matrix(), shape) local obj = ipe.Path(self.attributes, shape) self:creation("extract clipping path", obj) end function MODEL:saction_add_clipping() local p = self:page() local sel = self:selection() if #sel ~= 2 then self:warning("Must have exactly one two selected objects") return end local prim = sel[1] local sec = sel[2] if p[prim]:type() ~= "group" then prim = sel[2] sec = sel[1] end local obj = p[prim] if obj:type() ~= "group" or p[sec]:type() ~= "path" then self:warning("Must select exactly one group and one path") return end local shape = p[sec]:shape() transformShape(p[sec]:matrix(), shape) transformShape(obj:matrix():inverse(), shape) local t = { label = "add clipping", pno = self.pno, vno = self.vno, primary = prim, secondary = sec, original = obj:clone(), path = p[sec]:clone(), shape = shape, layer = p:layerOf(sec) } t.undo = function (t, doc) doc[t.pno]:insert(t.secondary, t.path, nil, t.layer) doc[t.pno]:replace(t.primary, t.original) end t.redo = function (t, doc) doc[t.pno][t.primary]:setClip(t.shape) doc[t.pno]:invalidateBBox(t.primary) doc[t.pno]:remove(t.secondary) end self:register(t) end ---------------------------------------------------------------------- ipe-7.2.13/src/ipe/lua/main.lua0000644000175000017500000003230113561570220016007 0ustar otfriedotfried---------------------------------------------------------------------- -- Ipe ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] -- order is important require "prefs" require "model" require "actions" require "tools" require "editpath" require "properties" require "shortcuts" require "mouse" ---------------------------------------------------------------------- -- short names V = ipe.Vector -- store the model for the first window -- Used only by OSX file_open_event -- must be global, as it's changed from model.lua first_model = nil ---------------------------------------------------------------------- function printTable(t) for k in pairs(t) do print(k, t[k]) end end -- only used for saving function formatFromFileName(fname) local s = string.lower(fname:sub(-4)) if s == ".xml" or s == ".ipe" then return "xml" end if s == ".pdf" then return "pdf" end return nil end function revertOriginal(t, doc) doc:set(t.pno, t.original) end function revertFinal(t, doc) doc:set(t.pno, t.final) end function indexOf(el, list) for i,n in ipairs(list) do if n == el then return i end end return nil end function symbolNames(sheet, prefix, postfix) local list = sheet:allNames("symbol") local result = {} for _, n in ipairs(list) do if n:sub(1, #prefix) == prefix and n:sub(-#postfix) == postfix then result[#result + 1] = n end end return result end function stripPrefixPostfix(list, m, mm) local result = {} for _, n in ipairs(list) do result[#result + 1] = n:sub(m, -mm-1) end return result end function arrowshapeToName(i, s) return s:match("^arrow/(.+)%(s?f?p?x%)$") end function colorString(color) if type(color) == "string" then return color end -- else must be table return string.format("(%g,%g,%g)", color.r, color.g, color.b) end function extractElements(p, selection) local r = {} local l = {} for i,j in ipairs(selection) do r[#r + 1] = p[j-i+1]:clone() l[#l + 1] = p:layerOf(j-i+1) p:remove(j-i+1) end return r, l end -- make a list of all values from stylesheets function allValues(sheets, kind) local syms = sheets:allNames(kind) local values = {} for _,sym in ipairs(syms) do values[#values + 1] = sheets:find(kind, sym) end return values end -- apply transformation to a shape function transformShape(matrix, shape) local result = {} for _,path in ipairs(shape) do if path.type == "ellipse" or path.type == "closedspline" then for i = 1,#path do path[i] = matrix * path[i] end else -- must be "curve" for _,seg in ipairs(path) do for i = 1,#seg do seg[i] = matrix * seg[i] end if seg.type == "arc" then seg.arc = matrix * seg.arc end end end end end function findStyle(w, dir) if dir and ipe.fileExists(dir .. prefs.fsep .. w) then return dir .. prefs.fsep .. w end for _, d in ipairs(config.styleDirs) do local s = d .. prefs.fsep .. w if ipe.fileExists(s) then return s end end end -- show a message box -- type is one of "none" "warning" "information" "question" "critical" -- details may be nil -- buttons may be nil (for "ok") or one of -- "ok" "okcancel" "yesnocancel", "discardcancel", "savediscardcancel", -- or a number from 0 to 4 corresponding to these -- return 1 for ok/yes/save, 0 for no/discard, -1 for cancel function messageBox(parent, type, text, details, buttons) if config.toolkit == "win" and buttons and (buttons == 3 or buttons == 4 or buttons == "discardcancel" or buttons == "savediscardcancel") then -- native Windows messagebox does not support these -- so we build our own dialog - this one has no icon, though local result = 0 local d = ipeui.Dialog(parent, "Ipe") d:add("text", "label", {label=text .. "\n\n" .. details}, 1, 1) if buttons == 4 or buttons == "savediscardcancel" then d:addButton("ok", "&Save", function (d) result=1; d:accept(true) end) end d:addButton("discard", "&Discard", "accept") d:addButton("cancel", "&Cancel", "reject") local r = d:execute() if r then return result else return -1 end else return ipeui.messageBox(parent, type, text, details, buttons) end end filter_ipe = { "Ipe files (*.ipe *.pdf *.eps *.xml)", "*.ipe;*.pdf;*.eps;*.xml", "All files (*.*)", "*.*" } filter_save = { "XML (*.ipe *.xml)", "*.ipe;*.xml", "PDF (*.pdf)", "*.pdf" } filter_stylesheets = { "Ipe stylesheets (*.isy)", "*.isy" } if config.platform == "win" then filter_images = { "Images (*.png *.jpg *.jpeg *.bmp *.gif *.tiff)", "*.png;*.jpg;*.jpeg;*.bmp;*.gif;*.tiff" } else filter_images = { "Images (*.png *.jpg *.jpeg)", "*.png;*.jpg;*.jpeg" } end filter_png = { "Images (*.png)", "*.png" } filter_eps = { "Postscript files (*.eps)", "*.eps" } filter_svg = { "SVG files (*.svg)", "*.svg" } ---------------------------------------------------------------------- -- This function is called to launch a file on MacOS X function file_open_event(fname) if first_model and first_model.pristine then first_model:loadDocument(fname) first_model:action_fit_top() else local m = MODEL.new(nil, fname) m:action_fit_top() end end ---------------------------------------------------------------------- -- msdn.microsoft.com/en-us/library/windows/desktop/dd375731(v=vs.85).aspx local win32_conversions = { PgDown=0x22, PgUp=0x21, Home=0x24, End=0x23, Left=0x25, Up=0x26, Right=0x27, Down=0x28, insert=0x2d, delete=0x2e } function win32_shortcut_convert(s) local k = 0 local done = false while not done do if s:sub(1,5) == "Ctrl+" then s = s:sub(6) k = k + 0x20000 elseif s:sub(1,6) == "Shift+" then s = s:sub(7) k = k + 0x40000 elseif s:sub(1,4) == "Alt+" then s = s:sub(5) k = k + 0x10000 else done = true end end if s ~= "F" and s:sub(1,1) == "F" and tonumber(s:sub(2)) then return k + 0x6f + tonumber(s:sub(2)) elseif win32_conversions[s] then return k + win32_conversions[s] elseif ("0" <= s and s <= "9") or ("A" <= s and s <= "Z") then return k + string.byte(s:sub(1,1)) else return k + string.byte(s:sub(1,1)) + 0x80000 end end function win32_shortcut_append(t, ts, s, id, ao) local sc = win32_shortcut_convert(s) t[#t+1] = sc t[#t+1] = id if ao then ts[#ts+1] = sc ts[#ts+1] = id end end function win32_shortcuts(ui) if config.toolkit ~= "win" then return end local accel = {} local accelsub = {} for i in pairs(shortcuts) do local id, alwaysOn = ui:actionInfo(i) local s = shortcuts[i] if type(s) == "table" then for j,s1 in ipairs(s) do win32_shortcut_append(accel, accelsub, s1, id, alwaysOn) end elseif s then win32_shortcut_append(accel, accelsub, s, id, alwaysOn) end end return accel, accelsub end ---------------------------------------------------------------------- local function show_configuration() local s = config.version s = s .. "\nLua code: " .. package.path s = s .. "\nStyle directories: " .. table.concat(config.styleDirs, ", ") s = s .. "\nStyles for new documents: " .. table.concat(prefs.styles, ", ") s = s .. "\nAutosave file: " .. prefs.autosave_filename s = s .. "\nSave-as directory: " .. prefs.save_as_directory s = s .. "\nDocumentation: " .. config.docdir s = s .. "\nIpelets: " .. table.concat(config.ipeletDirs, ", ") s = s .. "\nLatex program path: " .. config.latexpath s = s .. "\nLatex directory: " .. config.latexdir s = s .. "\nIcons: " .. config.icons s = s .. "\nExternal editor: " .. (prefs.external_editor or "none") s = s .. "\n" io.stdout:write(s) end local function usage() io.stderr:write("Usage: ipe { -sheet } [ ]\n") io.stderr:write("or: ipe -show-configuration\n") io.stderr:write("or: ipe --help\n") end -------------------------------------------------------------------- -- set locale so that "tonumber" will work right with decimal points os.setlocale("C", "numeric") local test1 = string.format("%g", 1.5) local test2 = string.format("%g", tonumber("1.5")) if test1 ~= "1.5" or test2 ~= "1.5" then m = "Formatting the number '1.5' results in '" .. test1 .. "'. " .. "Reading '1.5' results in '" .. test2 .. "'\n" .. "Therefore Ipe will not work correctly when loading or saving files. " .. "PLEASE REPORT THIS PROBLEM!\n" .. "As a workaround, you can start Ipe from the commandline like this: " .. "export LANG=C\nexport LC_NUMERIC=C\nipe" ipeui.messageBox(nil, "critical", "Ipe is running with an incorrect locale", m) return end -------------------------------------------------------------------- local home = os.getenv("HOME") local ipeletpath = os.getenv("IPELETPATH") if ipeletpath then config.ipeletDirs = {} for w in string.gmatch(ipeletpath, prefs.fname_pattern) do if w == "_" then w = config.system_ipelets end if w:sub(1,4) == "ipe:" then w = config.ipedrive .. w:sub(5) end config.ipeletDirs[#config.ipeletDirs + 1] = w end else config.ipeletDirs = { config.system_ipelets } if config.platform == "win" then local userdir = os.getenv("USERPROFILE") if userdir then config.ipeletDirs[#config.ipeletDirs + 1] = userdir .. "\\Ipelets" end else config.ipeletDirs[#config.ipeletDirs + 1] = home .. "/.ipe/ipelets" if config.platform == "apple" then config.ipeletDirs[#config.ipeletDirs + 1] = home.."/Library/Ipe/Ipelets" end end end local ipestyles = os.getenv("IPESTYLES") if ipestyles then config.styleDirs = {} for w in string.gmatch(ipestyles, prefs.fname_pattern) do if w == "_" then w = config.system_styles end if w:sub(1,4) == "ipe:" then w = config.ipedrive .. w:sub(5) end config.styleDirs[#config.styleDirs + 1] = w end else config.styleDirs = { config.system_styles } if config.platform ~= "win" then table.insert(config.styleDirs, 1, home .. "/.ipe/styles") if config.platform == "apple" then table.insert(config.styleDirs, 2, home .. "/Library/Ipe/Styles") end end end -------------------------------------------------------------------- function load_ipelets() for _,ft in ipairs(ipelets) do local fd = ipe.openFile(ft.path, "rb") local ff = assert(load(function () return fd:read("*L") end, ft.path, "bt", ft)) ff() end end -- look for ipelets ipelets = {} for _,w in ipairs(config.ipeletDirs) do if ipe.fileExists(w) then local files = ipe.directory(w) for i, f in ipairs(files) do if f:sub(-4) == ".lua" then ft = {} ft.name = f:sub(1,-5) ft.path = w .. prefs.fsep .. f ft.dllname = w .. prefs.fsep .. ft.name ft._G = _G ft.ipe = ipe ft.ipeui = ipeui ft.math = math ft.string = string ft.table = table ft.assert = assert ft.shortcuts = shortcuts ft.prefs = prefs ft.config = config ft.mouse = mouse ft.ipairs = ipairs ft.pairs = pairs ft.print = print ft.tonumber = tonumber ft.tostring = tostring ipelets[#ipelets + 1] = ft end end end end load_ipelets() -------------------------------------------------------------------- if #argv == 1 and argv[1] == "-show-configuration" then show_configuration() return end if #argv == 1 and (argv[1] == "--help" or argv[1] == "-h") then usage() return end -------------------------------------------------------------------- local first_file = nil local i = 1 local style_sheets = {} while i <= #argv do if argv[i] == "-sheet" then if i == #argv then usage() return end style_sheets[#style_sheets + 1] = argv[i+1] i = i + 2 else if i ~= #argv then usage() return end first_file = ipe.realPath(argv[i]) i = i + 1 end end -- Cocoa handles opening files itself, using open_file_event if config.toolkit == "cocoa" then first_file = nil end if #style_sheets > 0 then prefs.styles = style_sheets end config.styleList = {} for _,w in ipairs(prefs.styles) do if w:sub(-4) ~= ".isy" then w = w .. ".isy" end if not w:find(prefs.fsep) then w = findStyle(w) end config.styleList[#config.styleList + 1] = w end first_model = MODEL:new(first_file) first_model:action_fit_top() local acc, accsub = win32_shortcuts(first_model.ui) mainloop(acc, accsub) ---------------------------------------------------------------------- ipe-7.2.13/src/ipe/lua/shortcuts.lua0000644000175000017500000001306513561570220017127 0ustar otfriedotfried---------------------------------------------------------------------- -- Ipe keyboard shortcuts ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] -- on OSX, Ctrl means the Command key (for platform compatibility) -- if you really want the Control key, write "Control" -- you can also write "Command" for the Command key for clarity. shortcuts = { new_window = nil, open = "Ctrl+O", close = "Ctrl+W", save = "Ctrl+S", save_as = nil, export_png = nil, export_eps = nil, export_svg = nil, insert_image = "Ctrl+Shift+O", run_latex = "Ctrl+L", absolute = "Ctrl+T", undo = "Ctrl+Z", redo = "Ctrl+Y", copy = "Ctrl+C", paste = nil, paste_at_cursor = "Ctrl+V", cut = "Ctrl+X", delete = "delete", group = "Ctrl+G", ungroup = "Ctrl+U", front = "Ctrl+F", back = "Ctrl+B", forward = "Ctrl+Shift+F", backward = "Ctrl+Shift+B", before = nil, behind = nil, duplicate = "D", select_all = "Ctrl+A", join_paths = "Ctrl+J", pick_properties = "Q", apply_properties = "Ctrl+Q", insert_text_box = "F10", edit = "Ctrl+E", edit_as_xml = nil, change_width = "Alt+W", document_properties = "Ctrl+Shift+P", style_sheets = "Ctrl+Shift+S", update_style_sheets = "Ctrl+Shift+U", mode_select = "S", mode_translate = "T", mode_rotate = "R", mode_stretch = "E", mode_pan = nil, mode_shredder = nil, mode_label = "L", mode_math = "Shift+4", mode_paragraph = "G", mode_marks = "M", mode_rectangles1 = "B", mode_rectangles2 = nil, mode_rectangles3 = nil, mode_parallelogram = nil, mode_lines = "P", mode_polygons = "Shift+P", mode_arc1 = "A", mode_arc2 = "Shift+A", mode_arc3 = "Alt+A", mode_circle1 = "O", mode_circle2 = "Shift+O", mode_circle3 = "Alt+O", mode_splines = "I", mode_splinegons = "Shift+I", mode_ink = "K", snapvtx = "F4", snapctl = "Shift+F4", snapbd = "F5", snapint = "F6", snapgrid = "F7", snapangle = "F8", snapauto = "F9", set_origin = "F1", set_origin_snap = "Ctrl+Shift+F1", show_axes = "Ctrl+F1", set_direction = "F2", reset_direction = "Ctrl+F2", set_tangent_direction = "Ctrl+F3", set_line = "F3", set_line_snap = "Shift+F3", fullscreen = "F11", normal_size = "/", grid_visible = "F12", zoom_in = "Ctrl+PgUp", zoom_out = "Ctrl+PgDown", fit_page = "\\", fit_width = "-", fit_top = nil, fit_objects = "=", fit_selection = "@", pan_here = "X", new_layer = "Ctrl+Shift+N", rename_active_layer = "Ctrl+Shift+R", select_in_active_layer = "Ctrl+Shift+A", move_to_active_layer = "Ctrl+Shift+M", next_view = "PgDown", previous_view = "PgUp", first_view = "Home", last_view = "End", new_layer_view = "Ctrl+Shift+I", new_view = nil, delete_view = nil, edit_effects = nil, next_page = "Shift+PgDown", previous_page = "Shift+PgUp", first_page = "Shift+Home", last_page = "Shift+End", new_page = "Ctrl+I", cut_page = "Ctrl+Shift+X", copy_page = "Ctrl+Shift+C", paste_page = "Ctrl+Shift+V", delete_page = nil, edit_title = "Ctrl+P", edit_notes = "Ctrl+N", page_sorter = nil, jump_view = "V", jump_page = "J", ipelet_1_goodies = nil, -- Mirror horizontal ipelet_2_goodies = nil, -- Mirror vertical ipelet_3_goodies = nil, -- Mirror at x-axis ipelet_4_goodies = nil, -- Turn 90 degrees ipelet_5_goodies = nil, -- Turn 180 degrees ipelet_6_goodies = nil, -- Turn 270 degrees ipelet_7_goodies = "Ctrl+R", -- Precise rotate ipelet_8_goodies = "Ctrl+K", -- Precise stretch ipelet_9_goodies = nil, -- Insert precise box ipelet_10_goodies = nil, -- Insert bounding box ipelet_11_goodies = nil, -- Insert media box ipelet_12_goodies = nil, -- Mark circle center ipelet_13_goodies = nil, -- Make parabolas ipelet_14_goodies = nil, -- Regular k-gon ipelet_2_symbols = "Alt+Y", -- Use current symbol } if config.platform == "apple" then shortcuts.delete = "backspace" shortcuts.fullscreen = "Control+Command+F" end -- These are the shortcuts for the lines/polylines, polygons and splines -- functions. -- Contrary to the above, global shortcuts, the following rules apply: -- + Use small letters ("a") for normal keys -- + Use capital letters ("A") for Shift+A -- + Any special keys (F1, Delete, ...) are not possible -- + Any combination with the Ctrl key is not possible -- + If you use a shortcut that is already in the global shortcut list, -- it won't work! shortcuts_linestool = { spline = "s", arc = "a", set_axis = "y", } ---------------------------------------------------------------------- ipe-7.2.13/src/ipe/tools.cpp0000644000175000017500000001757313561570220015461 0ustar otfriedotfried// -------------------------------------------------------------------- // Canvas tools used from Lua // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "tools.h" extern "C" { #include #include #include } #include "ipecanvas.h" #include "ipepainter.h" #include "ipelua.h" using namespace ipe; using namespace ipelua; // -------------------------------------------------------------------- IpeTransformTool::IpeTransformTool(CanvasBase *canvas, Page *page, int view, TType type, bool withShift, lua_State *L0, int method) : TransformTool(canvas, page, view, type, withShift) { L = L0; iMethod = method; } IpeTransformTool::~IpeTransformTool() { luaL_unref(L, LUA_REGISTRYINDEX, iMethod); } void IpeTransformTool::report() { // call back to Lua to report final transformation lua_rawgeti(L, LUA_REGISTRYINDEX, iMethod); push_matrix(L, iTransform); lua_callk(L, 1, 0, 0, nullptr); } // -------------------------------------------------------------------- static void push_modifiers(lua_State *L, int button) { lua_createtable(L, 0, 4); lua_pushboolean(L, (button & CanvasBase::EShift)); lua_setfield(L, -2, "shift"); lua_pushboolean(L, (button & CanvasBase::EControl)); lua_setfield(L, -2, "control"); lua_pushboolean(L, (button & CanvasBase::ECommand)); lua_setfield(L, -2, "command"); lua_pushboolean(L, (button & CanvasBase::EAlt)); lua_setfield(L, -2, "alt"); lua_pushboolean(L, (button & CanvasBase::EMeta)); lua_setfield(L, -2, "meta"); } void push_button(lua_State *L, int button) { lua_pushinteger(L, (button & 0xff)); // button number push_modifiers(L, button); } // -------------------------------------------------------------------- LuaTool::LuaTool(CanvasBase *canvas, lua_State *L0, int luatool) : Tool(canvas) { L = L0; iLuaTool = luatool; iColor = Color(0, 0, 0); } LuaTool::~LuaTool() { luaL_unref(L, LUA_REGISTRYINDEX, iLuaTool); } void LuaTool::mouseButton(int button, bool press) { lua_rawgeti(L, LUA_REGISTRYINDEX, iLuaTool); lua_getfield(L, -1, "mouseButton"); lua_pushvalue(L, -2); // model lua_remove(L, -3); push_button(L, button); lua_pushboolean(L, press); lua_callk(L, 4, 0, 0, nullptr); } void LuaTool::mouseMove() { lua_rawgeti(L, LUA_REGISTRYINDEX, iLuaTool); lua_getfield(L, -1, "mouseMove"); lua_pushvalue(L, -2); // model lua_remove(L, -3); lua_callk(L, 1, 0, 0, nullptr); } bool LuaTool::key(String text, int modifiers) { lua_rawgeti(L, LUA_REGISTRYINDEX, iLuaTool); lua_getfield(L, -1, "key"); lua_pushvalue(L, -2); // model lua_remove(L, -3); push_string(L, text); push_modifiers(L, modifiers); lua_State *L0 = L; // need to save L since lua_callk(L, 3, 1, 0, nullptr); // this may delete tool bool used = lua_toboolean(L0, -1); return used; } // -------------------------------------------------------------------- ShapeTool::ShapeTool(CanvasBase *canvas, lua_State *L0, int luatool) : LuaTool(canvas, L0, luatool) { iPen = 1.0; iSnap = false; iSkipLast = false; } void ShapeTool::draw(Painter &painter) const { double z = 1.0 / iCanvas->zoom(); painter.setPen(Attribute(Fixed::fromDouble(iPen))); painter.setStroke(Attribute(iColor)); painter.setLineCap(TLineCap::ERoundCap); painter.setLineJoin(TLineJoin::ERoundJoin); painter.newPath(); iShape.draw(painter); painter.drawPath(EStrokedOnly); painter.setStroke(Attribute(Color(0, 1000, 0))); painter.setPen(Attribute(Fixed::fromDouble(1.0))); painter.newPath(); iAuxShape.draw(painter); painter.drawPath(EStrokedOnly); for (int i = 0; i < size(iMarks); ++i) { switch (iMarks[i].t) { case EVertex: painter.setFill(Attribute(Color(1000, 0, 1000))); break; case ECenter: case ERadius: painter.setFill(Attribute(Color(0, 0, 1000))); break; case ESplineCP: painter.setFill(Attribute(Color(0, 0, 800))); break; case EMinor: painter.setFill(Attribute(Color(0, 800, 0))); break; case ECurrent: painter.setStroke(Attribute(Color(1000, 0, 0))); break; case EScissor: painter.setFill(Attribute(Color(1000, 0, 0))); break; default: break; } painter.pushMatrix(); painter.translate(iMarks[i].v); painter.untransform(ETransformationsTranslations); switch (iMarks[i].t) { case EVertex: case ECenter: default: painter.newPath(); painter.moveTo(Vector(6*z, 0)); painter.drawArc(Arc(Matrix(6*z, 0, 0, 6*z, 0, 0))); painter.closePath(); painter.drawPath(EFilledOnly); break; case ECurrent: painter.newPath(); painter.moveTo(Vector(9*z, 0)); painter.drawArc(Arc(Matrix(9*z, 0, 0, 9*z, 0, 0))); painter.closePath(); painter.drawPath(EStrokedOnly); break; case ESplineCP: case ERadius: case EMinor: painter.newPath(); painter.moveTo(Vector(-4*z, -4*z)); painter.lineTo(Vector(4*z, -4*z)); painter.lineTo(Vector(4*z, 4*z)); painter.lineTo(Vector(-4*z, 4*z)); painter.closePath(); painter.drawPath(EFilledOnly); break; case EScissor: painter.newPath(); painter.moveTo(Vector(5*z, 0)); painter.lineTo(Vector(0, 5*z)); painter.lineTo(Vector(-5*z, 0)); painter.lineTo(Vector(0, -5*z)); painter.closePath(); painter.drawPath(EFilledOnly); break; } painter.popMatrix(); } } void ShapeTool::setSnapping(bool snap, bool skipLast) { iSnap = snap; iSkipLast = skipLast; } void ShapeTool::setShape(Shape shape, int which, double pen) { if (which == 1) iAuxShape = shape; else iShape = shape; iPen = pen; } void ShapeTool::clearMarks() { iMarks.clear(); } void ShapeTool::addMark(const Vector &v, TMarkType t) { SMark m; m.v = v; m.t = t; iMarks.push_back(m); } void ShapeTool::snapVtx(const Vector &mouse, Vector &pos, double &bound, bool cp) const { if (!iSnap) return; Matrix m; if (iSkipLast && iShape.countSubPaths() == 1 && iShape.subPath(0)->asCurve()) { const Curve *c = iShape.subPath(0)->asCurve(); if (!cp) c->segment(0).cp(0).snap(mouse, pos, bound); // skip last vertex of curve for (int i = 0; i < c->countSegments() - 1; ++i) c->segment(i).snapVtx(mouse, m, pos, bound, cp); } else iShape.snapVtx(mouse, m, pos, bound, cp); } // -------------------------------------------------------------------- PasteTool::PasteTool(CanvasBase *canvas, lua_State *L0, int luatool, Object *obj) : LuaTool(canvas, L0, luatool) { iObject = obj; } PasteTool::~PasteTool() { delete iObject; } void PasteTool::draw(Painter &painter) const { painter.transform(iMatrix); painter.setStroke(Attribute(iColor)); iObject->drawSimple(painter); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipe/appui.h0000644000175000017500000001507513561570220015077 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Appui // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef APPUI_H #define APPUI_H #include "ipecanvas.h" // avoid including Lua headers here typedef struct lua_State lua_State; #ifdef IPEUI_GTK #include typedef GtkWidget *WINID; typedef GtkMenu *MENUHANDLE; #endif #ifdef IPEUI_WIN32 #include #include typedef HWND WINID; typedef HMENU MENUHANDLE; #endif #ifdef IPEUI_QT #include #include typedef QWidget *WINID; typedef QMenu *MENUHANDLE; #endif #ifdef IPEUI_COCOA #include typedef NSWindow *WINID; typedef NSMenu *MENUHANDLE; #endif using namespace ipe; constexpr int COPYRIGHT_YEAR = 2019; class AppUiBase; extern WINID check_winid(lua_State *L, int i); extern void push_winid(lua_State *L, WINID win); extern String ipeIconDirectory(); extern AppUiBase *createAppUi(lua_State *L0, int model); // -------------------------------------------------------------------- class AppUiBase : public CanvasObserver { public: enum { EFileMenu, EEditMenu, EPropertiesMenu, ESnapMenu, EModeMenu, EZoomMenu, ELayerMenu, EViewMenu, EPageMenu, EIpeletMenu, EHelpMenu, ENumMenu }; // change list selectorNames if enum changes enum { EUiStroke, EUiFill, EUiPen, EUiTextSize, EUiMarkShape, EUiSymbolSize, EUiGridSize, EUiAngleSize, EUiView, EUiPage, EUiViewMarked, EUiPageMarked }; // tags for submenus enum { ESubmenuGridSize = 1000, ESubmenuAngleSize, ESubmenuTextStyle, ESubmenuLabelStyle, ESubmenuSelectLayer, ESubmenuMoveLayer, ESubmenuFin }; public: virtual ~AppUiBase(); CanvasBase *canvas() { return iCanvas; } void setupSymbolicNames(const Cascade *sheet); void setGridAngleSize(Attribute abs_grid, Attribute abs_angle); void setAttributes(const AllAttributes &all, Cascade *sheet); void luaShowPathStylePopup(Vector v); void luaBookmarkSelected(int index); inline void setInkMode(bool ink) { isInkMode = ink; } public: // What platforms must implement: virtual WINID windowId() = 0; virtual void closeWindow() = 0; virtual bool actionState(const char *name) = 0; virtual void setActionState(const char *name, bool value) = 0; virtual void setNumbers(String vno, bool vm, String pno, bool pm) = 0; virtual void setLayers(const Page *page, int view) = 0; virtual void setZoom(double zoom) = 0; virtual void setWindowCaption(bool mod, const char *s) = 0; virtual void setNotes(String notes) = 0; virtual void explain(const char *s, int t) = 0; virtual void showWindow(int width, int height) = 0; virtual void action(String name) = 0; virtual void setActionsEnabled(bool mode) = 0; virtual void setMouseIndicator(const char *s) = 0; virtual void setSnapIndicator(const char *s) = 0; virtual void setBookmarks(int no, const String *s) = 0; virtual void setToolVisible(int m, bool vis) = 0; virtual int pageSorter(lua_State *L, Document *doc, int width, int height, int thumbWidth) = 0; virtual int clipboard(lua_State *L) = 0; virtual int setClipboard(lua_State *L) = 0; // Only used on Windows to compute shortcuts: virtual int actionInfo(lua_State *L) const; protected: // What platforms must implement: virtual void addRootMenu(int id, const char *name) = 0; // if title == 0, add separator virtual void addItem(int id, const char *title = nullptr, const char *name = nullptr) = 0; virtual void startSubMenu(int id, const char *name, int tag = 0) = 0; virtual void addSubItem(const char *title, const char *name) = 0; virtual MENUHANDLE endSubMenu() = 0; virtual void addCombo(int sel, String s) = 0; virtual void resetCombos() = 0; virtual void addComboColors(AttributeSeq &sym, AttributeSeq &abs) = 0; virtual void setComboCurrent(int sel, int idx) = 0; virtual void setPathView(const AllAttributes &all, Cascade *sheet) = 0; virtual void setCheckMark(String name, Attribute a) = 0; virtual void setButtonColor(int sel, Color color) = 0; protected: virtual void canvasObserverWheelMoved(double xDegrees, double yDegrees, int kind); virtual void canvasObserverMouseAction(int button); virtual void canvasObserverPositionChanged(); virtual void canvasObserverToolChanged(bool hasTool); virtual void canvasObserverSizeChanged(); protected: AppUiBase(lua_State *L0, int model); static const char * const selectorNames[]; void luaSelector(String name, String value); void luaAction(String name); void luaShowLayerBoxPopup(Vector v, String layer); void luaLayerAction(String name, String layer); void luaAbsoluteButton(const char *s); void buildMenus(); void showInCombo(const Cascade *sheet, Kind kind, int sel, const char *deflt = nullptr); void showMarksInCombo(const Cascade *sheet); void setAttribute(int sel, Attribute a); protected: lua_State *L; int iModel; // reference to Lua model MENUHANDLE iSelectLayerMenu; MENUHANDLE iMoveToLayerMenu; MENUHANDLE iTextStyleMenu; MENUHANDLE iLabelStyleMenu; MENUHANDLE iGridSizeMenu; MENUHANDLE iAngleSizeMenu; Cascade *iCascade; AllAttributes iAll; // current settings in UI std::vector iComboContents[EUiView]; CanvasBase *iCanvas; int iWidthNotesBookmarks; std::vector iScalings; String iCoordinatesFormat; int iMouseIn; double iMouseFactor; int iUiScale; int iToolbarScale; int iUiGap; bool isMiniEdit; bool iLeftDockFloats; bool isInkMode; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipe/Info.plist0000644000175000017500000000445613561570220015561 0ustar otfriedotfried CFBundleDocumentTypes CFBundleTypeName Ipe figure CFBundleTypeIconFile ipe.icns LSHandlerRank Owner CFBundleTypeRole Editor CFBundleTypeExtensions ipe IPE CFBundleTypeName PDF document CFBundleTypeIconFile ipe.icns LSHandlerRank Alternate CFBundleTypeRole Editor CFBundleTypeExtensions pdf PDF CFBundleTypeMIMETypes application/pdf CFBundleDevelopmentRegion English CFBundleExecutable ipe CFBundleIconFile ipe CFBundleIdentifier org.otfried.ipe.Ipe CFBundleInfoDictionaryVersion 6.0 LSEnvironment PATH /Library/TeX/texbin:/usr/texbin:/usr/local/texbin:/usr/local/bin:/opt/local/bin:/usr/bin:/bin LSApplicationCategoryType public.app-category.graphics-design LSMinimumSystemVersion 10.10 NSPrincipalClass NSApplication NSMainNibFile mainmenu NSHighResolutionCapable True CFBundleName Ipe CFBundlePackageType APPL CFBundleShortVersionString 7.2.13 CFBundleSignature Ipe CFBundleVersion 7.2.13 NSHumanReadableCopyright Copyright © 1993-2019 Otfried Cheong ipe-7.2.13/src/ipetoipe/0000755000175000017500000000000013561570220014641 5ustar otfriedotfriedipe-7.2.13/src/ipetoipe/Makefile0000644000175000017500000000133213561570220016300 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for Ipetoipe # -------------------------------------------------------------------- OBJDIR = $(BUILDDIR)/obj/ipetoipe include ../common.mak TARGET = $(call exe_target,ipetoipe) CPPFLAGS += -I../include LIBS += -L$(buildlib) -lipe all: $(TARGET) sources = ipetoipe.cpp $(TARGET): $(objects) $(MAKE_BINDIR) $(CXX) $(LDFLAGS) -o $@ $^ $(LIBS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPEBINDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPEBINDIR) # -------------------------------------------------------------------- ipe-7.2.13/src/ipetoipe/ipetoipe.cpp0000644000175000017500000001552313561570220017171 0ustar otfriedotfried// -------------------------------------------------------------------- // ipetoipe // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipedoc.h" #include #include using ipe::Document; using ipe::String; using ipe::FileFormat; using ipe::SaveFlag; static int topdf(Document *doc, String src, String dst, uint32_t flags, int fromPage = -1, int toPage = -1, int viewNo = -1) { int res = doc->runLatex(src); if (res) return res; bool result = false; if (viewNo >= 0) { result = doc->exportView(dst.z(), FileFormat::Pdf, flags, fromPage, viewNo); } else if (toPage >= 0) { result = doc->exportPages(dst.z(), flags, fromPage, toPage); } else { result = doc->save(dst.z(), FileFormat::Pdf, flags); } if (!result) { fprintf(stderr, "Failed to save or export document!\n"); return 1; } if (flags & SaveFlag::Export) fprintf(stderr, "Warning: the exported file contains no Ipe markup.\n" "It cannot be read by Ipe - make sure you keep the original!\n"); return 0; } static void usage() { fprintf(stderr, "Usage: ipetoipe ( -xml | -pdf ) " "infile [ outfile ]\n" "Ipetoipe converts between the different Ipe file formats.\n" " -export : output contains no Ipe markup.\n" " -pages : export only these pages (implies -export).\n" " -view : export only this view (implies -export).\n" " -markedview : export only marked views on marked pages (implies -export).\n" " -runlatex : run Latex even for XML output.\n" " -nozip : do not compress PDF streams.\n" " -keepnotes : save page notes as PDF annotations even when exporting.\n" "Pages can be specified by page number or by section title.\n" ); exit(1); } int main(int argc, char *argv[]) { ipe::Platform::initLib(ipe::IPELIB_VERSION); // ensure at least two arguments (handles -help as well :-) if (argc < 3) usage(); FileFormat frm = FileFormat::Unknown; if (!strcmp(argv[1], "-xml")) frm = FileFormat::Xml; else if (!strcmp(argv[1], "-pdf")) frm = FileFormat::Pdf; if (frm == FileFormat::Unknown) usage(); uint32_t flags = SaveFlag::SaveNormal; bool runLatex = false; const char *pages = nullptr; const char *view = nullptr; int i = 2; String infile; String outfile; while (i < argc) { if (!strcmp(argv[i], "-export")) { flags |= SaveFlag::Export; ++i; } else if (!strcmp(argv[i], "-view")) { flags |= SaveFlag::Export; if (i + 1 == argc) usage(); view = argv[i+1]; i += 2; } else if (!strcmp(argv[i], "-pages")) { flags |= SaveFlag::Export; if (i + 1 == argc) usage(); pages = argv[i+1]; i += 2; } else if (!strcmp(argv[i], "-markedview")) { flags |= SaveFlag::MarkedView; flags |= SaveFlag::Export; ++i; } else if (!strcmp(argv[i], "-runlatex")) { runLatex = true; ++i; } else if (!strcmp(argv[i], "-nozip")) { flags |= SaveFlag::NoZip; ++i; } else if (!strcmp(argv[i], "-keepnotes")) { flags |= SaveFlag::KeepNotes; ++i; } else { // last one or two arguments must be filenames infile = argv[i]; ++i; if (i < argc) { outfile = argv[i]; ++i; } if (i != argc) usage(); } } if (infile.empty()) usage(); if ((flags & SaveFlag::Export) && frm == FileFormat::Xml) { fprintf(stderr, "-export only available with -pdf.\n"); exit(1); } if (pages && frm != FileFormat::Pdf) { fprintf(stderr, "-pages only available with -pdf.\n"); exit(1); } if (pages && view) { fprintf(stderr, "cannot specify both -pages and -view.\n"); exit(1); } if (outfile.empty()) { outfile = infile; String ext = infile.right(4); if (ext == ".ipe" || ext == ".pdf" || ext == ".xml") outfile = infile.left(infile.size() - 4); switch (frm) { case FileFormat::Xml: outfile += ".ipe"; break; case FileFormat::Pdf: outfile += ".pdf"; default: break; } if (outfile == infile) { fprintf(stderr, "Cannot guess output filename.\n"); exit(1); } } std::unique_ptr doc(Document::loadWithErrorReport(infile.z())); if (!doc) return 1; fprintf(stderr, "Document %s has %d pages (%d views)\n", infile.z(), doc->countPages(), doc->countTotalViews()); // parse pages and view int fromPage = -1; int toPage = -1; int viewNo = -1; if (pages) { String p(pages); int j = p.find('-'); if (j >= 0) { fromPage = (j > 0) ? doc->findPage(p.left(j)) : 0; toPage = (j < p.size() - 1) ? doc->findPage(p.substr(j+1)) : doc->countPages() - 1; } if (fromPage < 0 || fromPage > toPage) { fprintf(stderr, "incorrect -pages specification.\n"); exit(1); } } else if (view) { String v(view); int j = v.find('-'); if (j > 0) { fromPage = doc->findPage(v.left(j)); if (fromPage >= 0) viewNo = doc->page(fromPage)->findView(v.substr(j+1)); } if (fromPage < 0 || viewNo < 0) { fprintf(stderr, "incorrect -view specification.\n"); exit(1); } } char buf[64]; sprintf(buf, "ipetoipe %d.%d.%d", ipe::IPELIB_VERSION / 10000, (ipe::IPELIB_VERSION / 100) % 100, ipe::IPELIB_VERSION % 100); Document::SProperties props = doc->properties(); props.iCreator = buf; doc->setProperties(props); switch (frm) { case FileFormat::Xml: if (runLatex) return topdf(doc.get(), infile, outfile, flags); else doc->save(outfile.z(), FileFormat::Xml, SaveFlag::SaveNormal); default: return 0; case FileFormat::Pdf: return topdf(doc.get(), infile, outfile, flags, fromPage, toPage, viewNo); } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecairo/0000755000175000017500000000000013561570220014616 5ustar otfriedotfriedipe-7.2.13/src/ipecairo/ipecairopainter.cpp0000644000175000017500000011172013561570220020502 0ustar otfriedotfried// -------------------------------------------------------------------- // Painter using Cairo library // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipetext.h" #include "ipepdfparser.h" #include "ipecairopainter.h" #include "ipefonts.h" // for std::memset #include using namespace ipe; // in ipebitmap: extern bool dctDecode(Buffer dctData, Buffer pixelData); // -------------------------------------------------------------------- /*! \defgroup cairo Ipe Cairo interface \brief Drawing Ipe objects using the Cairo library. This module contains the classes needed to render Ipe objects using the Cairo and Freetype libraries. These classes are not in Ipelib, but in a separate library libipecairo. */ // -------------------------------------------------------------------- static void cairoMatrix(cairo_matrix_t &cm, const Matrix &m) { cm.xx = m.a[0]; cm.yx = m.a[1]; cm.xy = m.a[2]; cm.yy = m.a[3]; cm.x0 = m.a[4]; cm.y0 = m.a[5]; } static void cairoTransform(cairo_t *cr, const Matrix &m) { cairo_matrix_t cm; cairoMatrix(cm, m); cairo_transform(cr, &cm); } // -------------------------------------------------------------------- // not checking /Domain and /N static bool getFunctionType2(const PdfObj *obj, std::vector &fun) { if (!obj || !obj->dict()) return false; for (int i = 0; i < 2; ++i) { std::vector c; if (!obj->dict()->getNumberArray(i ? "C1" : "C0", nullptr, c) || c.size() != 3) return false; for (int j = 0; j < 3; ++j) fun.push_back(c[j]); } return true; } static void drawShading(cairo_t *cr, const PdfDict *d, const PdfResourceBase *r) { // ipeDebug("drawShading: %s", d->dictRepr().z()); double type; if (!d->getNumber("ShadingType", type, nullptr) || type < 2.0 || type > 3.0) return; bool axial = (type == 3.0); std::vector coords; if (!d->getNumberArray("Coords", nullptr, coords) || coords.size() != (axial ? 6 : 4)) return; bool extend[2] = { false, false }; const PdfObj *extObj = r->getDeep(d, "Extend"); if (extObj && extObj->array() && extObj->array()->count() == 2) { for (int i = 0; i < 2; ++i) { const PdfObj *el = extObj->array()->obj(i, nullptr); if (el && el->boolean()) extend[i] = el->boolean()->value(); } } const PdfDict *f = r->getDict(d, "Function"); if (!f) return; double ftype; std::vector funs; std::vector domain; std::vector bounds; if (!f->getNumber("FunctionType", ftype, nullptr)) return; if (ftype == 2.0) { if (!getFunctionType2(f, funs)) return; } else if (ftype == 3.0) { if (!f->getNumberArray("Domain", nullptr, domain) || domain.size() != 2) { domain.clear(); domain.push_back(0.0); domain.push_back(1.0); } if (!f->getNumberArray("Bounds", nullptr, bounds)) return; const PdfObj *a = r->getDeep(f, "Functions"); if (!a || !a->array() || a->array()->count() != size(bounds) + 1) return; for (int i = 0; i < a->array()->count(); ++i) { const PdfObj *af = a->array()->obj(i, nullptr); if (af && af->ref()) af = r->object(af->ref()->value()); if (!getFunctionType2(af, funs)) return; } } else return; // cannot handle cairo_pattern_t *p = axial ? cairo_pattern_create_radial(coords[0], coords[1], coords[2], coords[3], coords[4], coords[5]) : cairo_pattern_create_linear(coords[0], coords[1], coords[2], coords[3]); if (extend[0] && extend[1]) // Cairo cannot control this individually, would have // to simulate using transparency or something cairo_pattern_set_extend(p, CAIRO_EXTEND_PAD); else cairo_pattern_set_extend(p, CAIRO_EXTEND_NONE); int fi = 0; cairo_pattern_add_color_stop_rgb(p, 0.0, funs[fi+0], funs[fi+1], funs[fi+2]); for (int i = 0; i < size(bounds); ++i) { fi += 6; double x = (bounds[i] - domain[0]) / (domain[1] - domain[0]); cairo_pattern_add_color_stop_rgb(p, x, funs[fi+0], funs[fi+1], funs[fi+2]); } cairo_pattern_add_color_stop_rgb(p, 1.0, funs[fi+3], funs[fi+4], funs[fi+5]); cairo_set_source(cr, p); cairo_paint(cr); cairo_pattern_destroy(p); } static void drawImage(cairo_t *cr, const PdfDict *d, const PdfResourceBase *r, double opacity) { // ipeDebug("Image: %s", d->dictRepr().z()); double width, height, bpc; const PdfObj *cs = d->get("ColorSpace", nullptr); if (!d->getNumber("Width", width, nullptr) || !d->getNumber("Height", height, nullptr) || !d->getNumber("BitsPerComponent", bpc, nullptr) || !cs || !cs->name() || (cs->name()->value() != "DeviceRGB" && cs->name()->value() != "DeviceGray") || bpc != 8) { ipeDebug("Unsupported image: %s", d->dictRepr().z()); return; } int components = 3; if (cs->name()->value() == "DeviceGray") components = 1; bool jpg = false; const PdfObj *filter = d->get("Filter", nullptr); if (filter && filter->name()) { String fn = filter->name()->value(); if (fn == "DCTDecode") jpg = true; else if (fn != "FlateDecode") { ipeDebug("Unsupported filter in image: %s", d->dictRepr().z()); return; } } Buffer stream = d->inflate(); Buffer pixels(4 * width * height); if (jpg) { if (!dctDecode(stream, pixels)) return; } else { const char *p = stream.data(); uint32_t *q = (uint32_t *) pixels.data(); if (components == 3) { for (int y = 0; y < height; ++y) { for (int x = 0; x < width; ++x) { uint8_t r = uint8_t(*p++); uint8_t g = uint8_t(*p++); uint8_t b = uint8_t(*p++); uint32_t pixel = 0xff000000 | (r << 16) | (g << 8) | b; *q++ = pixel; } } } else { for (int y = 0; y < height; ++y) { for (int x = 0; x < width; ++x) { uint8_t r = uint8_t(*p++); uint32_t pixel = 0xff000000 | (r << 16) | (r << 8) | r; *q++ = pixel; } } } } cairo_surface_t *image = cairo_image_surface_create_for_data((uint8_t *) pixels.data(), CAIRO_FORMAT_ARGB32, width, height, 4 * width); cairo_save(cr); Matrix tf = Matrix(1.0 / width, 0.0, 0.0, -1.0 / height, 0.0, 1.0); cairoTransform(cr, tf); cairo_set_source_surface(cr, image, 0, 0); cairo_pattern_set_filter(cairo_get_source(cr), CAIRO_FILTER_FAST); cairo_paint_with_alpha(cr, opacity); cairo_restore(cr); } // -------------------------------------------------------------------- /*! \class ipe::CairoPainter \ingroup cairo \brief Ipe Painter using Cairo and Freetype as a backend. This painter draws to a Cairo surface. */ //! Construct a painter. /*! \a zoom one means 72 pixels per inch. Set \a pretty to true to avoid drawing text without Latex. */ CairoPainter::CairoPainter(const Cascade *sheet, Fonts *fonts, cairo_t *cc, double zoom, bool pretty) : Painter(sheet), iFonts(fonts), iCairo(cc), iZoom(zoom), iPretty(pretty) { iDimmed = false; } void CairoPainter::doPush() { cairo_save(iCairo); } void CairoPainter::doPop() { cairo_restore(iCairo); } void CairoPainter::doMoveTo(const Vector &u) { cairo_move_to(iCairo, u.x, u.y); iAfterMoveTo = true; } void CairoPainter::doLineTo(const Vector &u) { cairo_line_to(iCairo, u.x, u.y); iAfterMoveTo = false; } void CairoPainter::doCurveTo(const Vector &u1, const Vector &u2, const Vector &u3) { cairo_curve_to(iCairo, u1.x, u1.y, u2.x, u2.y, u3.x, u3.y); iAfterMoveTo = false; } void CairoPainter::doClosePath() { cairo_close_path(iCairo); } void CairoPainter::doDrawArc(const Arc &arc) { cairo_save(iCairo); Matrix m = matrix() * arc.iM; cairoTransform(iCairo, m); if (arc.isEllipse()) { cairo_new_sub_path(iCairo); cairo_arc(iCairo, 0.0, 0.0, 1.0, 0.0, IpeTwoPi); cairo_close_path(iCairo); } else { // this is necessary because of rounding errors: // otherwise cairo may insert a near-zero-length segment that messes // up line cap if (iAfterMoveTo) cairo_new_sub_path(iCairo); cairo_arc(iCairo, 0.0, 0.0, 1.0, arc.iAlpha, arc.iBeta); } iAfterMoveTo = false; cairo_restore(iCairo); } void CairoPainter::doDrawPath(TPathMode mode) { cairo_save(iCairo); if (mode >= EStrokedAndFilled) { Color fillColor = fill(); cairo_set_fill_rule(iCairo, (fillRule() == EEvenOddRule) ? CAIRO_FILL_RULE_EVEN_ODD : CAIRO_FILL_RULE_WINDING); const Tiling *t = nullptr; if (!tiling().isNormal()) t = cascade()->findTiling(tiling()); const Gradient *g = nullptr; if (!gradient().isNormal()) g = cascade()->findGradient(gradient()); if (t == nullptr && g == nullptr) { // no tiling, no gradient cairo_set_source_rgba(iCairo, fillColor.iRed.toDouble(), fillColor.iGreen.toDouble(), fillColor.iBlue.toDouble(), opacity().toDouble()); if (mode == EStrokedAndFilled) cairo_fill_preserve(iCairo); else cairo_fill(iCairo); } else if (t == nullptr) { // gradient cairo_pattern_t *p; if (g->iType == Gradient::ERadial) p = cairo_pattern_create_radial(g->iV[0].x, g->iV[0].y, g->iRadius[0], g->iV[1].x, g->iV[1].y, g->iRadius[1]); else p = cairo_pattern_create_linear(g->iV[0].x, g->iV[0].y, g->iV[1].x, g->iV[1].y); cairo_pattern_set_extend(p, g->iExtend ? CAIRO_EXTEND_PAD : CAIRO_EXTEND_NONE); for (const auto & stop : g->iStops) { cairo_pattern_add_color_stop_rgb(p, stop.offset, stop.color.iRed.toDouble(), stop.color.iGreen.toDouble(), stop.color.iBlue.toDouble()); } const Matrix &m0 = (matrix()* g->iMatrix).inverse(); cairo_matrix_t m; cairoMatrix(m, m0); cairo_pattern_set_matrix(p, &m); cairo_set_source(iCairo, p); if (mode == EStrokedAndFilled) cairo_fill_preserve(iCairo); else cairo_fill(iCairo); cairo_pattern_destroy(p); } else { // tiling cairo_surface_t *s = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, 32, 32); uint8_t *data = cairo_image_surface_get_data(s); memset(data, 0, 4 * 32 * 32); cairo_t *cc = cairo_create(s); cairo_set_source_rgba(cc, fillColor.iRed.toDouble(), fillColor.iGreen.toDouble(), fillColor.iBlue.toDouble(), opacity().toDouble()); cairo_rectangle(cc, 0, 0, 32, 32 * t->iWidth / t->iStep); cairo_fill(cc); cairo_destroy(cc); cairo_pattern_t *p = cairo_pattern_create_for_surface(s); cairo_pattern_set_extend(p, CAIRO_EXTEND_REPEAT); cairo_matrix_t m; cairo_matrix_init_scale(&m, 1.0, 32.0 / t->iStep); cairo_matrix_rotate(&m, -double(t->iAngle)); cairo_pattern_set_matrix(p, &m); cairo_set_source(iCairo, p); if (mode == EStrokedAndFilled) cairo_fill_preserve(iCairo); else cairo_fill(iCairo); cairo_pattern_destroy(p); cairo_surface_destroy(s); } } if (mode <= EStrokedAndFilled) { Color strokeColor = stroke(); cairo_set_source_rgba(iCairo, strokeColor.iRed.toDouble(), strokeColor.iGreen.toDouble(), strokeColor.iBlue.toDouble(), strokeOpacity().toDouble()); cairo_set_line_width(iCairo, pen().toDouble()); switch (lineJoin()) { case EMiterJoin: cairo_set_line_join(iCairo, CAIRO_LINE_JOIN_MITER); break; case ERoundJoin: case EDefaultJoin: cairo_set_line_join(iCairo, CAIRO_LINE_JOIN_ROUND); break; case EBevelJoin: cairo_set_line_join(iCairo, CAIRO_LINE_JOIN_BEVEL); break; } switch (lineCap()) { case EButtCap: cairo_set_line_cap(iCairo, CAIRO_LINE_CAP_BUTT); break; case ERoundCap: case EDefaultCap: cairo_set_line_cap(iCairo, CAIRO_LINE_CAP_ROUND); break; case ESquareCap: cairo_set_line_cap(iCairo, CAIRO_LINE_CAP_SQUARE); break; } if (dashStyle() != "[]0") { std::vector dashes; double offset; dashStyle(dashes, offset); cairo_set_dash(iCairo, &dashes[0], dashes.size(), offset); } cairo_stroke(iCairo); } cairo_restore(iCairo); } void CairoPainter::doAddClipPath() { cairo_clip(iCairo); } // -------------------------------------------------------------------- void CairoPainter::doDrawBitmap(Bitmap bitmap) { Buffer data = bitmap.pixelData(); if (!data.size()) return; // is this legal? I don't want cairo to modify my bitmap temporarily. cairo_surface_t *image = cairo_image_surface_create_for_data((uint8_t *) data.data(), CAIRO_FORMAT_ARGB32, bitmap.width(), bitmap.height(), 4 * bitmap.width()); cairo_save(iCairo); Matrix tf = matrix() * Matrix(1.0 / bitmap.width(), 0.0, 0.0, -1.0 / bitmap.height(), 0.0, 1.0); cairoTransform(iCairo, tf); cairo_set_source_surface(iCairo, image, 0, 0); cairo_pattern_set_filter(cairo_get_source(iCairo), CAIRO_FILTER_FAST); cairo_paint_with_alpha(iCairo, opacity().toDouble()); cairo_restore(iCairo); } void CairoPainter::doDrawText(const Text *text) { // Current origin is lower left corner of text box // Draw bounding box rectangle if (!iPretty && !iDimmed) { cairo_save(iCairo); cairo_set_source_rgb(iCairo, 0.0, 1.0, 0.0); cairo_set_line_width(iCairo, 1.0 / iZoom); double dash = 3.0 / iZoom; cairo_set_dash(iCairo, &dash, 1, 0.0); Vector u0 = matrix() * Vector::ZERO; Vector u1 = matrix() * Vector(0, text->totalHeight()); Vector u2 = matrix() * Vector(text->width(), text->totalHeight()); Vector u3 = matrix() * Vector(text->width(), 0); cairo_move_to(iCairo, u0.x, u0.y); cairo_line_to(iCairo, u1.x, u1.y); cairo_line_to(iCairo, u2.x, u2.y); cairo_line_to(iCairo, u3.x, u3.y); cairo_close_path(iCairo); cairo_stroke(iCairo); Vector ref = matrix() * text->align(); cairo_rectangle(iCairo, ref.x - 3.0/iZoom, ref.y - 3.0/iZoom, 6.0/iZoom, 6.0/iZoom); cairo_fill(iCairo); cairo_restore(iCairo); } const Text::XForm *xf = text->getXForm(); if (!xf || !iFonts) { String s = text->text(); int i = s.find('\n'); if (i < 0 || i > 30) i = 30; if (i < s.size()) s = s.left(i) + "..."; Vector pt = matrix().translation(); // pt.y = pt.y - iPainter->fontMetrics().descent(); cairo_font_face_t *font = Fonts::screenFont(); if (font) { cairo_save(iCairo); cairo_set_font_face(iCairo, font); cairo_set_font_size(iCairo, 9.0); Color col = stroke(); cairo_set_source_rgba(iCairo, col.iRed.toDouble(), col.iGreen.toDouble(), col.iBlue.toDouble(), opacity().toDouble()); cairo_translate(iCairo, pt.x, pt.y); cairo_scale(iCairo, 1.0, -1.0); cairo_show_text(iCairo, s.z()); cairo_restore(iCairo); } } else { transform(Matrix(xf->iStretch, 0, 0, xf->iStretch, 0, 0)); translate(xf->iTranslation); const PdfDict *form = findResource("XObject", xf->iName); if (form) executeStream(form, form); } } void CairoPainter::executeStream(const PdfDict *stream, const PdfDict *resources) { cairo_save(iCairo); cairoTransform(iCairo, matrix()); PdfState ps; ps.iFont = nullptr; ps.iFillRgb[0] = ps.iFillRgb[1] = ps.iFillRgb[2] = 0.0; ps.iStrokeRgb[0] = ps.iStrokeRgb[1] = ps.iStrokeRgb[2] = 0.0; ps.iStrokeOpacity = ps.iFillOpacity = opacity().toDouble(); ps.iCharacterSpacing = 0.0; ps.iWordSpacing = 0.0; ps.iHorizontalScaling = 1.0; ps.iLeading = 0.0; ps.iTextRise = 0.0; iPdfState.push_back(ps); execute(stream, resources); cairo_restore(iCairo); } // -------------------------------------------------------------------- //! Clear PDF argument stack void CairoPainter::clearArgs() { while (!iArgs.empty()) { delete iArgs.back(); iArgs.pop_back(); } } const PdfDict *CairoPainter::findResource(String kind, String name) { if (iResourceStack.size() > 0) { const PdfDict *res = iFonts->resources()->findResource(iResourceStack.back(), kind, name); if (res) return res; } return iFonts->resources()->findResource(kind, name); } void CairoPainter::execute(const PdfDict *xform, const PdfDict *resources, bool applyMatrix) { // ipeDebug("execute %s", xform->dictRepr().z()); iResourceStack.push_back(resources); std::vector m; if (applyMatrix && xform->getNumberArray("Matrix", nullptr, m) && m.size() == 6) { Matrix mx; for (int i = 0; i < 6; ++i) mx.a[i] = m[i]; cairoTransform(iCairo, mx); } Buffer buffer = xform->inflate(); BufferSource source(buffer); PdfParser parser(source); clearArgs(); // if called recursively... while (!parser.eos()) { PdfToken tok = parser.token(); if (tok.iType != PdfToken::EOp) { const PdfObj *obj = parser.getObject(); if (!obj) break; // no further parsing attempted iArgs.push_back(obj); } else { // its an operator, execute it String op = tok.iString; parser.getToken(); if (op == "cm") opcm(); else if (op == "q") opq(); else if (op == "Q") opQ(); else if (op == "rg") oprg(false); else if (op == "RG") oprg(true); else if (op == "g") opg(false); else if (op == "G") opg(true); else if (op == "k") opk(false); else if (op == "K") opk(true); else if (op == "scn") opscn(false); else if (op == "SCN") opscn(true); else if (op == "w") opw(); else if (op == "d") opd(); else if (op == "Do") opDo(); else if (op == "sh") opsh(); else if (op == "i") opi(); else if (op == "j") opj(); else if (op == "J") opJ(); else if (op == "M") opM(); else if (op == "W") opW(false); else if (op == "W*") opW(true); else if (op == "gs") opgs(); else if (op == "m") opm(); else if (op == "l") opl(); else if (op == "h") oph(); else if (op == "c") opc(); else if (op == "v") opv(); else if (op == "y") opy(); else if (op == "re") opre(); else if (op == "n") opn(); else if (op == "b") opStrokeFill(true, true, true, false); else if (op == "b*") opStrokeFill(true, true, true, true); else if (op == "B") opStrokeFill(false, true, true, false); else if (op == "B*") opStrokeFill(false, true, true, true); else if (op == "f" || op == "F") opStrokeFill(false, true, false, false); else if (op == "f*") opStrokeFill(false, true, false, true); else if (op == "s") opStrokeFill(true, false, true, false); else if (op == "S") opStrokeFill(false, false, true, false); else if (op == "Tc") opTc(&iPdfState.back().iCharacterSpacing); else if (op == "Tw") opTc(&iPdfState.back().iWordSpacing); else if (op == "TL") opTc(&iPdfState.back().iLeading); else if (op == "Ts") opTc(&iPdfState.back().iTextRise); else if (op == "Tz") opTz(); else if (op == "Tf") opTf(); else if (op == "Tm") opTm(); else if (op == "Td") opTd(false); else if (op == "TD") opTd(true); else if (op == "T*") opTstar(); else if (op == "TJ") opTJ(); else if (op == "Tj") opTj(false, false); else if (op == "'") opTj(true, false); else if (op == "\"") opTj(true, true); else if (op == "BT") opBT(); else if (op == "ET") opET(); else if (op == "MP" || op == "DP" || op == "BMC" || op == "BDC" || op == "EMC") { // content markers, ignore } else if (op == "ri") { // set rendering intent, ignore } else { String a; for (const auto & arg : iArgs) a += arg->repr() + " "; ipeDebug("op %s (%s)", op.z(), a.z()); } clearArgs(); } } clearArgs(); iResourceStack.pop_back(); } void CairoPainter::opg(bool stroke) { if (iArgs.size() != 1 || !iArgs[0]->number()) return; double gr = iArgs[0]->number()->value(); auto & ps = iPdfState.back(); if (stroke) ps.iStrokeRgb[0] = ps.iStrokeRgb[1] = ps.iStrokeRgb[2] = gr; else ps.iFillRgb[0] = ps.iFillRgb[1] = ps.iFillRgb[2] = gr; } void CairoPainter::oprg(bool stroke) { if (iArgs.size() != 3 || !iArgs[0]->number() || !iArgs[1]->number() || !iArgs[2]->number()) return; double *col = (stroke ? iPdfState.back().iStrokeRgb : iPdfState.back().iFillRgb); for (int i = 0; i < 3; ++i) col[i] = iArgs[i]->number()->value(); } void CairoPainter::opk(bool stroke) { if (iArgs.size() != 4 || !iArgs[0]->number() || !iArgs[1]->number() || !iArgs[2]->number() || !iArgs[3]->number()) return; ipeDebug("PDF setting CMYK color"); // should use the colorspace of the monitor instead of this crude conversion double v = 1.0 - iArgs[3]->number()->value(); double *col = (stroke ? iPdfState.back().iStrokeRgb : iPdfState.back().iFillRgb); for (int i = 0; i < 3; ++i) col[i] = v * (1.0 - iArgs[i]->number()->value()); } void CairoPainter::opscn(bool stroke) { // uncolored tiling pattern arguments actually depend on colorspace set with cs, // we simply assume here that it's DeviceRGB String pattern; auto & ps = iPdfState.back(); if (iArgs.size() == 1 && iArgs[0]->name()) { // colored tiling pattern pattern = iArgs[0]->name()->value(); } else { if (iArgs.size() != 4 || !iArgs[0]->number() || !iArgs[1]->number() || !iArgs[2]->number() || !iArgs[3]->name()) return; // uncolored tiling pattern pattern = iArgs[3]->name()->value(); double *col = (stroke ? ps.iStrokeRgb : ps.iFillRgb); for (int i = 0; i < 3; ++i) col[i] = iArgs[i]->number()->value(); } if (stroke) ipeDebug("op scn /%s: stroke pattern not implemented.", pattern.z()); else ps.iFillPattern = pattern; } void CairoPainter::opcm() { if (iArgs.size() != 6) return; Matrix m; for (int i = 0; i < 6; ++i) { if (!iArgs[i]->number()) return; m.a[i] = iArgs[i]->number()->value(); } cairoTransform(iCairo, m); } void CairoPainter::opw() { if (iArgs.size() != 1 || !iArgs[0]->number()) return; cairo_set_line_width(iCairo, iArgs[0]->number()->value()); } void CairoPainter::opd() { if (iArgs.size() != 2 || !iArgs[0]->array() || !iArgs[1]->number()) return; std::vector dashes; for (int i = 0; i < iArgs[0]->array()->count(); ++i) { const PdfObj *obj = iArgs[0]->array()->obj(i, nullptr); if (!obj->number()) return; dashes.emplace_back(obj->number()->value()); } double offset = iArgs[1]->number()->value(); cairo_set_dash(iCairo, &dashes[0], dashes.size(), offset); } void CairoPainter::opi() { if (iArgs.size() != 1 || !iArgs[0]->number()) return; // ipeDebug("Set flatness tolerance to %g", iArgs[0]->number()->value()); } void CairoPainter::opj() { if (iArgs.size() != 1 || !iArgs[0]->number()) return; cairo_set_line_join(iCairo, cairo_line_join_t(iArgs[0]->number()->value())); } void CairoPainter::opJ() { if (iArgs.size() != 1 || !iArgs[0]->number()) return; cairo_set_line_cap(iCairo, cairo_line_cap_t(iArgs[0]->number()->value())); } void CairoPainter::opM() { if (iArgs.size() != 1 || !iArgs[0]->number()) return; cairo_set_miter_limit(iCairo, iArgs[0]->number()->value()); } void CairoPainter::opW(bool eofill) { cairo_set_fill_rule(iCairo, eofill ? CAIRO_FILL_RULE_EVEN_ODD : CAIRO_FILL_RULE_WINDING); cairo_clip_preserve(iCairo); } // -------------------------------------------------------------------- void CairoPainter::opgs() { if (iArgs.size() != 1 || !iArgs[0]->name()) return; String name = iArgs[0]->name()->value(); const PdfDict *d = findResource("ExtGState", name); if (!d) { ipeDebug("gs %s cannot find ExtGState dictionary!", name.z()); return; } for (int j = 0; j < d->count(); ++j) { String key = d->key(j); const PdfObj *val = d->value(j); if (key == "ca") { if (val->number()) iPdfState.back().iFillOpacity = val->number()->value(); } else if (key == "CA") { if (val->number()) iPdfState.back().iStrokeOpacity = val->number()->value(); } else if (key == "Type" || key == "SA" || key == "TR" || key == "TR2" || key == "SM" || key == "HT" || key == "OP" || key == "op" || key == "RI" || key == "UCR" || key == "UCR2" || key == "BG" || key == "BG2" || key == "OPM" ) { // ignore } else ipeDebug("gs %s %s", key.z(), val->repr().z()); } } void CairoPainter::opsh() { if (iArgs.size() != 1 || !iArgs[0]->name()) return; String name = iArgs[0]->name()->value(); const PdfDict *d = findResource("Shading", name); if (d) drawShading(iCairo, d, iFonts->resources()); } void CairoPainter::opDo() { if (iArgs.size() != 1 || !iArgs[0]->name()) return; String name = iArgs[0]->name()->value(); // ipeDebug("Do %s at level %d", name.z(), iResourceStack.size()); const PdfDict *xf = findResource("XObject", name); if (!xf) return; const PdfObj *subtypeObj = xf->get("Subtype", nullptr); if (!subtypeObj || !subtypeObj->name()) return; String subtype = subtypeObj->name()->value(); if (subtype == "Form") { cairo_save(iCairo); execute(xf, xf); cairo_restore(iCairo); } else if (subtype == "Image") { drawImage(iCairo, xf, iFonts->resources(), iPdfState.back().iFillOpacity); } else ipeDebug("Do operator with unsupported XObject subtype %s", subtype.z()); } // -------------------------------------------------------------------- void CairoPainter::opq() { if (iArgs.size() != 0) return; cairo_save(iCairo); iPdfState.push_back(iPdfState.back()); } void CairoPainter::opQ() { if (iArgs.size() != 0) return; cairo_restore(iCairo); iPdfState.pop_back(); } // -------------------------------------------------------------------- void CairoPainter::opm() { if (iArgs.size() != 2 || !iArgs[0]->number() || !iArgs[1]->number()) return; Vector t(iArgs[0]->number()->value(), iArgs[1]->number()->value()); cairo_move_to(iCairo, t.x, t.y); } void CairoPainter::opl() { if (iArgs.size() != 2 || !iArgs[0]->number() || !iArgs[1]->number()) return; Vector t(iArgs[0]->number()->value(), iArgs[1]->number()->value()); cairo_line_to(iCairo, t.x, t.y); } void CairoPainter::oph() { if (iArgs.size() != 0) return; cairo_close_path(iCairo); } void CairoPainter::opc() { if (iArgs.size() != 6 || !iArgs[0]->number() || !iArgs[1]->number() || !iArgs[2]->number() || !iArgs[3]->number() || !iArgs[4]->number() || !iArgs[5]->number()) return; Vector p1(iArgs[0]->number()->value(), iArgs[1]->number()->value()); Vector p2(iArgs[2]->number()->value(), iArgs[3]->number()->value()); Vector p3(iArgs[4]->number()->value(), iArgs[5]->number()->value()); cairo_curve_to(iCairo, p1.x, p1.y, p2.x, p2.y, p3.x, p3.y); } void CairoPainter::opv() { if (iArgs.size() != 4 || !iArgs[0]->number() || !iArgs[1]->number() || !iArgs[2]->number() || !iArgs[3]->number()) return; double x1, y1; cairo_get_current_point(iCairo, &x1, &y1); Vector p2(iArgs[0]->number()->value(), iArgs[1]->number()->value()); Vector p3(iArgs[2]->number()->value(), iArgs[3]->number()->value()); cairo_curve_to(iCairo, x1, y1, p2.x, p2.y, p3.x, p3.y); } void CairoPainter::opy() { if (iArgs.size() != 4 || !iArgs[0]->number() || !iArgs[1]->number() || !iArgs[2]->number() || !iArgs[3]->number()) return; Vector p1(iArgs[0]->number()->value(), iArgs[1]->number()->value()); Vector p3(iArgs[2]->number()->value(), iArgs[3]->number()->value()); cairo_curve_to(iCairo, p1.x, p1.y, p3.x, p3.y, p3.x, p3.y); } void CairoPainter::opre() { if (iArgs.size() != 4 || !iArgs[0]->number() || !iArgs[1]->number() || !iArgs[2]->number() || !iArgs[3]->number()) return; Vector t(iArgs[0]->number()->value(), iArgs[1]->number()->value()); Vector wh(iArgs[2]->number()->value(), iArgs[3]->number()->value()); cairo_rectangle(iCairo, t.x, t.y, wh.x, wh.y); } void CairoPainter::opn() { // the sequence "W n" updates the clipping path and then clears the current path cairo_new_path(iCairo); } // TODO: cache patterns instead of recreating them for every object? // caching would need different handling of uncolored tiling patterns. // shading patterns are not implemented here, because Ipe and tikz create // them using the 'sh' operator. void CairoPainter::createPattern() { auto & ps = iPdfState.back(); const PdfDict *pat = findResource("Pattern", ps.iFillPattern); double patternType, paintType, xstep, ystep; if (pat && pat->getNumber("PatternType", patternType, nullptr) && pat->getNumber("PaintType", paintType, nullptr) && pat->getNumber("XStep", xstep, nullptr) && pat->getNumber("YStep", ystep, nullptr)) { ipeDebug("Fill pattern /%s PatternType %g PaintType %g xstep %g ystep %g", ps.iFillPattern.z(), patternType, paintType, xstep, ystep); // handle tiling patterns only if (patternType != 1.0) return; // to get good quality patterns, the pattern surface cannot be too small // except that for Ipe patterns this isn't necessary. double xscale = 1.0; double yscale = 1.0; // Heuristic: if a matrix exists, let's assume small cell is okay if (pat->get("Matrix", nullptr) == nullptr) { while (xscale * xstep < 100) xscale *= 2.0; while (yscale * ystep < 100) yscale *= 2.0; } int width = (int) std::ceil(xscale * xstep); int height = (int) std::ceil(yscale * ystep); ipeDebug("Using pattern surface of size %d x %d", width, height); cairo_surface_t *sf = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, width, height); cairo_t *cc = cairo_create(sf); cairo_paint_with_alpha(cc, 0.0); // clear surface to transparent cairo_translate(cc, 0.0, height); cairo_scale(cc, 1.0, -1.0); auto & ps0 = iPdfState.back(); PdfState ps; ps.iFont = nullptr; for (int i = 0; i < 3; ++i) { ps.iFillRgb[i] = ps0.iFillRgb[i]; ps.iStrokeRgb[i] = ps0.iStrokeRgb[i]; } ps.iStrokeOpacity = ps0.iStrokeOpacity; ps.iFillOpacity = ps0.iFillOpacity; ps.iCharacterSpacing = 0.0; ps.iWordSpacing = 0.0; ps.iHorizontalScaling = 1.0; ps.iLeading = 0.0; ps.iTextRise = 0.0; // drawing the pattern four times is also not necessary for Ipe patterns... // we can avoid this if we consult the BBox for (int dx = 0; dx < 2; ++dx) { for (int dy = 0; dy < 2; ++dy) { cairo_save(cc); cairo_translate(cc, -dx * width, -dy * height); cairo_scale(cc, xscale, yscale); CairoPainter painter(iCascade, iFonts, cc, 1.0, false); painter.iPdfState.push_back(ps); painter.execute(pat, pat, false); cairo_restore(cc); } } cairo_surface_flush(sf); cairo_destroy(cc); cairo_pattern_t *cpat = cairo_pattern_create_for_surface(sf); cairo_pattern_set_extend(cpat, CAIRO_EXTEND_REPEAT); Matrix mx; std::vector m; if (pat->getNumberArray("Matrix", nullptr, m) && m.size() == 6) { for (int i = 0; i < 6; ++i) mx.a[i] = m[i]; // PDF pattern matrix goes from user space to pattern space, // Cairo pattern matrix is the opposite mx = mx.inverse(); } mx = Matrix(xscale, 0.0, 0.0, -yscale, 0.0, height) * mx; cairo_matrix_t cm; cairoMatrix(cm, mx); cairo_pattern_set_matrix(cpat, &cm); cairo_set_source(iCairo, cpat); cairo_pattern_destroy(cpat); } } void CairoPainter::opStrokeFill(bool close, bool fill, bool stroke, bool eofill) { if (close) cairo_close_path(iCairo); PdfState &ps = iPdfState.back(); if (fill) { if (!ps.iFillPattern.empty()) createPattern(); else cairo_set_source_rgba(iCairo, ps.iFillRgb[0], ps.iFillRgb[1], ps.iFillRgb[2], ps.iFillOpacity); cairo_set_fill_rule(iCairo, eofill ? CAIRO_FILL_RULE_EVEN_ODD : CAIRO_FILL_RULE_WINDING); } if (fill && stroke) cairo_fill_preserve(iCairo); else if (fill) cairo_fill(iCairo); if (stroke) { cairo_set_source_rgba(iCairo, ps.iStrokeRgb[0], ps.iStrokeRgb[1], ps.iStrokeRgb[2], ps.iStrokeOpacity); cairo_stroke(iCairo); } } // -------------------------------------------------------------------- void CairoPainter::opBT() { iTextMatrix = iTextLineMatrix = Matrix(); } void CairoPainter::opET() { // nothing } void CairoPainter::opTc(double *p) { if (iArgs.size() != 1 || !iArgs[0]->number()) return; *p = iArgs[0]->number()->value(); } void CairoPainter::opTz() { if (iArgs.size() != 1 || !iArgs[0]->number()) return; iPdfState.back().iHorizontalScaling = iArgs[0]->number()->value() / 100.0; } void CairoPainter::opTm() { if (iArgs.size() != 6) return; Matrix m; for (int i = 0; i < 6; ++i) { if (!iArgs[i]->number()) return; m.a[i] = iArgs[i]->number()->value(); } iTextMatrix = iTextLineMatrix = m; } void CairoPainter::opTf() { if (iArgs.size() != 2 || !iArgs[0]->name() || !iArgs[1]->number()) return; String name = iArgs[0]->name()->value(); iPdfState.back().iFontSize = iArgs[1]->number()->value(); const PdfDict *fd = findResource("Font", name); if (fd) iPdfState.back().iFont = iFonts->getFace(fd); } void CairoPainter::opTd(bool setLeading) { if (iArgs.size() != 2 || !iArgs[0]->number() || !iArgs[1]->number()) return; Vector t(iArgs[0]->number()->value(), iArgs[1]->number()->value()); iTextMatrix = iTextLineMatrix = iTextLineMatrix * Matrix(t); if (setLeading) iPdfState.back().iLeading = t.y; } void CairoPainter::opTstar() { if (iArgs.size() != 0) return; Vector t(0, iPdfState.back().iLeading); iTextMatrix = iTextLineMatrix = iTextLineMatrix * Matrix(t); } void CairoPainter::opTj(bool nextLine, bool setSpacing) { PdfState &ps = iPdfState.back(); if (!setSpacing) { if (iArgs.size() != 1 || !iArgs[0]->string()) return; } else { if (iArgs.size() != 3 || !iArgs[0]->number() || !iArgs[1]->number() || !iArgs[2]->string()) return; } String s = iArgs[iArgs.size() - 1]->string()->decode(); if (setSpacing) { ps.iWordSpacing = iArgs[0]->number()->value(); ps.iCharacterSpacing = iArgs[1]->number()->value(); } if (nextLine) { Vector t(0, ps.iLeading); iTextMatrix = iTextLineMatrix = iTextLineMatrix * Matrix(t); } if (!ps.iFont) return; std::vector glyphs; Vector textPos(0, 0); collectGlyphs(s, glyphs, textPos); drawGlyphs(glyphs); iTextMatrix = iTextMatrix * Matrix(textPos); } void CairoPainter::opTJ() { PdfState &ps = iPdfState.back(); if (!ps.iFont || iArgs.size() != 1 || !iArgs[0]->array()) return; std::vector glyphs; Vector textPos(0, 0); for (int i = 0; i < iArgs[0]->array()->count(); ++i) { const PdfObj *obj = iArgs[0]->array()->obj(i, nullptr); if (obj->number()) textPos.x -= 0.001 * ps.iFontSize * obj->number()->value() * ps.iHorizontalScaling; else if (obj->string()) collectGlyphs(obj->string()->decode(), glyphs, textPos); } drawGlyphs(glyphs); iTextMatrix = iTextMatrix * Matrix(textPos); } void CairoPainter::collectGlyphs(String s, std::vector &glyphs, Vector &textPos) { PdfState &ps = iPdfState.back(); bool ucs = (ps.iFont->type() == FontType::CIDType0 || ps.iFont->type() == FontType::CIDType2); int j = 0; while (j < s.size()) { int ch = uint8_t(s[j++]); if (ucs && j < s.size()) ch = (ch << 8) | uint8_t(s[j++]); cairo_glyph_t g; g.index = ps.iFont->glyphIndex(ch); Vector p = iTextMatrix.linear() * textPos; g.x = p.x; g.y = p.y; glyphs.push_back(g); textPos.x += (0.001 * ps.iFontSize * ps.iFont->width(ch) + ps.iCharacterSpacing) * ps.iHorizontalScaling; if (ch == ' ') textPos.x += ps.iWordSpacing * ps.iHorizontalScaling; } } // -------------------------------------------------------------------- //! Draw a glyph. /*! Glyph is drawn with hotspot at position pos. */ void CairoPainter::drawGlyphs(std::vector &glyphs) { PdfState &ps = iPdfState.back(); if (!ps.iFont) return; Matrix m = iTextMatrix * Matrix(ps.iFontSize * ps.iHorizontalScaling, 0, 0, ps.iFontSize, 0, ps.iTextRise) * Linear(1, 0, 0, -1); cairo_matrix_t matrix; cairoMatrix(matrix, m); cairo_save(iCairo); cairo_set_font_face(iCairo, ps.iFont->cairoFont()); cairo_set_font_matrix(iCairo, &matrix); cairo_set_source_rgba(iCairo, ps.iFillRgb[0], ps.iFillRgb[1], ps.iFillRgb[2], ps.iFillOpacity); cairo_show_glyphs(iCairo, &glyphs[0], glyphs.size()); cairo_restore(iCairo); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecairo/ipethumbs.cpp0000644000175000017500000001544413561570220017332 0ustar otfriedotfried// -------------------------------------------------------------------- // Making thumbnails of Ipe pages and PDF pages // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipethumbs.h" #include "ipecairopainter.h" #include #ifdef CAIRO_HAS_SVG_SURFACE #include #endif #ifdef CAIRO_HAS_PDF_SURFACE #include #endif #ifdef CAIRO_HAS_PS_SURFACE #include #endif #include using namespace ipe; // -------------------------------------------------------------------- Thumbnail::Thumbnail(const Document *doc, int width) { iDoc = doc; iWidth = width; iLayout = iDoc->cascade()->findLayout(); Rect paper = iLayout->paper(); iHeight = int(iWidth * paper.height() / paper.width()); iZoom = iWidth / paper.width(); iFonts = std::make_unique(doc->resources()); } Buffer Thumbnail::render(const Page *page, int view) { Buffer buffer(iWidth * iHeight * 4); memset(buffer.data(), 0xff, iWidth * iHeight * 4); cairo_surface_t* surface = cairo_image_surface_create_for_data((uint8_t *) buffer.data(), CAIRO_FORMAT_ARGB32, iWidth, iHeight, iWidth * 4); cairo_t *cc = cairo_create(surface); cairo_scale(cc, iZoom, -iZoom); Vector offset = iLayout->iOrigin - iLayout->paper().topLeft(); cairo_translate(cc, offset.x, offset.y); CairoPainter painter(iDoc->cascade(), iFonts.get(), cc, iZoom, true); painter.pushMatrix(); for (int i = 0; i < page->count(); ++i) { if (page->objectVisible(view, i)) page->object(i)->draw(painter); } painter.popMatrix(); cairo_surface_flush(surface); cairo_show_page(cc); cairo_destroy(cc); cairo_surface_destroy(surface); return buffer; } static cairo_status_t stream_writer(void *closure, const unsigned char *data, unsigned int length) { if (::fwrite(data, 1, length, (std::FILE *) closure) != length) return CAIRO_STATUS_WRITE_ERROR; return CAIRO_STATUS_SUCCESS; } bool Thumbnail::saveRender(TargetFormat fm, const char *dst, const Page *page, int view, double zoom, bool transparent, bool nocrop) { Rect bbox; int wid, ht; if (nocrop) { bbox = iLayout->paper(); wid = int(bbox.width() * zoom); ht = int(bbox.height() * zoom); } else { bbox = page->pageBBox(iDoc->cascade()); wid = int(bbox.width() * zoom + 1); ht = int(bbox.height() * zoom + 1); } Buffer data; cairo_surface_t* surface = nullptr; std::FILE *file = Platform::fopen(dst, "wb"); if (!file) return false; if (fm == EPNG) { if (wid * ht > 20000000) return false; data = Buffer(wid * ht * 4); if (transparent) memset(data.data(), 0x00, wid * ht * 4); else memset(data.data(), 0xff, wid * ht * 4); surface = cairo_image_surface_create_for_data((uint8_t *) data.data(), CAIRO_FORMAT_ARGB32, wid, ht, wid * 4); #ifdef CAIRO_HAS_SVG_SURFACE } else if (fm == ESVG) { surface = cairo_svg_surface_create_for_stream(&stream_writer, (void *) file, wid, ht); #endif #ifdef CAIRO_HAS_PS_SURFACE } else if (fm == EPS) { surface = cairo_ps_surface_create_for_stream(&stream_writer, (void *) file, wid, ht); cairo_ps_surface_set_eps(surface, true); #endif #ifdef CAIRO_HAS_PDF_SURFACE } else if (fm == EPDF) { surface = cairo_pdf_surface_create_for_stream(&stream_writer, (void *) file, wid, ht); #endif } cairo_t *cc = cairo_create(surface); cairo_scale(cc, zoom, -zoom); cairo_translate(cc, -bbox.topLeft().x, -bbox.topLeft().y); CairoPainter painter(iDoc->cascade(), iFonts.get(), cc, zoom, true); // painter.Transform(IpeLinear(zoom, 0, 0, -zoom)); // painter.Translate(-bbox.TopLeft()); painter.pushMatrix(); if (nocrop) { const Symbol *background = iDoc->cascade()->findSymbol(Attribute::BACKGROUND()); if (background && page->findLayer("BACKGROUND") < 0) painter.drawSymbol(Attribute::BACKGROUND()); } for (int i = 0; i < page->count(); ++i) { if (page->objectVisible(view, i)) page->object(i)->draw(painter); } painter.popMatrix(); cairo_surface_flush(surface); cairo_show_page(cc); if (fm == EPNG) cairo_surface_write_to_png_stream(surface, &stream_writer, (void *) file); cairo_destroy(cc); cairo_surface_destroy(surface); ::fclose(file); return true; } // -------------------------------------------------------------------- PdfThumbnail::PdfThumbnail(const PdfFile *pdf, int width) { iPdf = pdf; iCascade = std::make_unique(); iCascade->insert(0, StyleSheet::standard()); iResources = std::make_unique(iPdf); iFonts = std::make_unique(iResources.get()); iWidth = width; iHeight = 0; for (int i = 0; i < iPdf->countPages(); ++i) { Rect paper = iPdf->mediaBox(iPdf->page(i)); iHeight = std::max(iHeight, (int) (paper.height() * iWidth / paper.width())); } } Buffer PdfThumbnail::render(const PdfDict *page) { Rect paper = iPdf->mediaBox(page); double zoom = iWidth / paper.width(); const PdfObj *stream0 = page->get("Contents", iPdf); const PdfDict *stream = stream0 ? stream0->dict() : nullptr; Buffer buffer(iWidth * iHeight * 4); cairo_surface_t* surface = cairo_image_surface_create_for_data((uint8_t *) buffer.data(), CAIRO_FORMAT_ARGB32, iWidth, iHeight, iWidth * 4); cairo_t *cc = cairo_create(surface); cairo_set_source_rgb(cc, 1.0, 1.0, 1.0); cairo_paint(cc); cairo_translate(cc, 0.0, iHeight); cairo_scale(cc, zoom, -zoom); if (stream) { CairoPainter painter(iCascade.get(), iFonts.get(), cc, 1.0, false); painter.executeStream(stream, page); } cairo_surface_flush(surface); cairo_destroy(cc); cairo_surface_destroy(surface); return buffer; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecairo/ipefonts.cpp0000644000175000017500000003332113561570220017153 0ustar otfriedotfried// -------------------------------------------------------------------- // Rendering fonts onto the canvas // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipefonts.h" #include "ipepdfparser.h" #include "ipexml.h" #include #include #include FT_FREETYPE_H #include #include using namespace ipe; // -------------------------------------------------------------------- struct Engine { public: Engine(); ~Engine(); cairo_font_face_t *screenFont(); private: bool iScreenFontLoaded; cairo_font_face_t *iScreenFont; public: bool iOk; FT_Library iLib; int iFacesLoaded; int iFacesUnloaded; int iFacesDiscarded; }; // Auto-constructed and destructed Freetype engine. static Engine engine; // -------------------------------------------------------------------- Engine::Engine() { iOk = false; iScreenFont = nullptr; iScreenFontLoaded = false; iFacesLoaded = 0; iFacesUnloaded = 0; iFacesDiscarded = 0; if (FT_Init_FreeType(&iLib)) return; iOk = true; } Engine::~Engine() { ipeDebug("Freetype engine: %d faces loaded, %d faces unloaded, " "%d faces discarded", iFacesLoaded, iFacesUnloaded, iFacesDiscarded); if (iScreenFont) cairo_font_face_destroy(iScreenFont); if (iOk) FT_Done_FreeType(iLib); // causes an assert in cairo to fail: // cairo_debug_reset_static_data(); ipeDebug("Freetype engine done: %d faces discarded", iFacesDiscarded); } // -------------------------------------------------------------------- cairo_font_face_t *Engine::screenFont() { if (!iScreenFontLoaded) { iScreenFontLoaded = true; iScreenFont = cairo_toy_font_face_create("Sans", CAIRO_FONT_SLANT_NORMAL, CAIRO_FONT_WEIGHT_BOLD); } return iScreenFont; } // -------------------------------------------------------------------- /*! \class ipe::Fonts \ingroup cairo \brief Provides the fonts used to render text. */ Fonts::Fonts(const PdfResourceBase *resources) : iResources(resources) { // nothing } String Fonts::freetypeVersion() { int major, minor, patch; FT_Library_Version(engine.iLib, &major, &minor, &patch); char buf[128]; sprintf(buf, "Freetype %d.%d.%d / %d.%d.%d", FREETYPE_MAJOR, FREETYPE_MINOR, FREETYPE_PATCH, major, minor, patch); return String(buf); } //! Return a Cairo font to render to the screen w/o Latex font. cairo_font_face_t *Fonts::screenFont() { return engine.iOk ? engine.screenFont() : nullptr; } //! Get a typeface. /*! Corresponds to a Freetype "face", or a PDF font resource. A Face can be loaded at various sizes (transformations), resulting in individual FaceSize's. */ Face *Fonts::getFace(const PdfDict *d) { if (!engine.iOk) return nullptr; auto it = std::find_if(iFaces.begin(), iFaces.end(), [d](std::unique_ptr &f) { return f->matches(d); } ); if (it != iFaces.end()) return it->get(); iFaces.emplace_back(std::make_unique(d, iResources)); return iFaces.back().get(); } // -------------------------------------------------------------------- struct FaceData { Buffer iData; FT_Face iFace; }; static void face_data_destroy(FaceData *face_data) { ++engine.iFacesDiscarded; FT_Done_Face(face_data->iFace); // discard Freetype face delete face_data; // discard memory buffer } static const cairo_user_data_key_t datakey = { 0 }; /*! \class ipe::Face \ingroup cairo \brief A typeface (aka font), actually loaded (from a font file or PDF file). */ Face::Face(const PdfDict *d, const PdfResourceBase *resources) noexcept : iFontDict(d), iResources(resources) { /* d: /Type /Font /Subtype /Type1 /Encoding 24 0 R /FirstChar 6 /LastChar 49 /Widths 25 0 R /BaseFont /YEHLEP+CMR10 /FontDescriptor 7 0 R */ const PdfObj *type = d->get("Type", nullptr); if (!type || !type->name() || type->name()->value() != "Font") return; type = d->get("Subtype", nullptr); if (!type || !type->name()) return; String t = type->name()->value(); const PdfDict *d0 = d; if (t == "Type0") { const PdfObj *desc = getPdf(d, "DescendantFonts"); if (!desc || !desc->array()) return; desc = desc->array()->obj(0, nullptr); if (!desc) return; if (desc->ref()) desc = iResources->object(desc->ref()->value()); if (!desc || !desc->dict()) return; d = desc->dict(); type = d->get("Subtype", nullptr); if (!type || !type->name()) return; t = type->name()->value(); } const PdfObj *name = getPdf(d, "BaseFont"); if (!name || !name->name()) return; iName = name->name()->value(); // ipeDebug("Font '%s' of type '%s'", iName.z(), t.z()); if (t == "Type1") iType = FontType::Type1; else if (t == "TrueType") iType = FontType::Truetype; else if (t == "CIDFontType0") iType = FontType::CIDType0; else if (t == "CIDFontType2") iType = FontType::CIDType2; else { iType = FontType::Unsupported; return; } Buffer data; if (!getFontFile(d, data)) { ipeDebug("Failed to get font file for %s", iName.z()); return; } if (FT_New_Memory_Face(engine.iLib, (const uint8_t *) data.data(), data.size(), 0, &iFace)) return; FaceData *face_data = new FaceData; face_data->iData = data; face_data->iFace = iFace; // see cairo_ft_font_face_create_for_ft_face docs, // it explains why the user_data is necessary iCairoFont = cairo_ft_font_face_create_for_ft_face(iFace, 0); cairo_status_t status = cairo_font_face_set_user_data(iCairoFont, &datakey, face_data, (cairo_destroy_func_t) face_data_destroy); if (status) { ipeDebug("Failed to set user data for Cairo font"); cairo_font_face_destroy(iCairoFont); FT_Done_Face(iFace); delete face_data; iCairoFont = nullptr; iFace = nullptr; return; } ++engine.iFacesLoaded; if (iType == FontType::CIDType0 || iType == FontType::CIDType2) { getCIDWidth(d); const PdfObj *enc = getPdf(d0, "Encoding"); if (!enc || !enc->name()) return; String encoding = enc->name()->value(); if (encoding != "Identity-H") ipeDebug("Unsupported encoding: %s", encoding.z()); // ipeDebug("FT Face has %d charmaps, is cid-keyed: %d", // iFace->num_charmaps, FT_IS_CID_KEYED(iFace)); } else { getSimpleWidth(d); if (iType == FontType::Type1) getType1Encoding(d); else setupTruetypeEncoding(); } } Face::~Face() noexcept { if (iCairoFont) { ipeDebug("Done with Cairo face %s (%d references left)", iName.z(), cairo_font_face_get_reference_count(iCairoFont)); ++engine.iFacesUnloaded; cairo_font_face_destroy(iCairoFont); } } const PdfObj *Face::getPdf(const PdfDict *d, String key) const noexcept { return iResources->getDeep(d, key); } // -------------------------------------------------------------------- int Face::width(int ch) const noexcept { int i = 0; while (i < size(iWidth)) { if (iWidth[i] <= ch && ch <= iWidth[i+1]) { // found interval if (iWidth[i+2] < 0) return -iWidth[i+1] - 1; return iWidth[i + 2 + (ch - iWidth[i])]; } else { if (iWidth[i+2] < 0) i += 3; else i += 3 + (iWidth[i+1] - iWidth[i]); } } return iDefaultWidth; } int Face::glyphIndex(int ch) noexcept { if (!iCairoFont) return 0; switch (iType) { case FontType::Type1: return iEncoding[ch]; case FontType::Truetype: return FT_Get_Char_Index(iFace, (FT_ULong) ch); case FontType::CIDType0: case FontType::CIDType2: return ch; // for cid-keyed font, this is a cid default: return 0; } } // -------------------------------------------------------------------- void Face::getCIDWidth(const PdfDict *d) noexcept { const PdfObj *dw = getPdf(d, "DW"); const PdfObj *w = getPdf(d, "W"); if (!dw || !dw->number()) return; iDefaultWidth = int(dw->number()->value()); if (!w || !w->array()) return; int i = 0; while (i + 1 < w->array()->count()) { const PdfObj *obj = w->array()->obj(i, nullptr); if (!obj->number()) return; int beg = int(obj->number()->value()); obj = w->array()->obj(i+1, nullptr); if (obj->number()) { int fin = int(obj->number()->value()); if (i+2 == w->array()->count()) return; obj = w->array()->obj(i+2, nullptr); if (!obj || !obj->number()) return; iWidth.push_back(beg); iWidth.push_back(fin); iWidth.push_back(-int(obj->number()->value()) - 1); i += 3; } else if (obj->array()) { int fin = beg + obj->array()->count() - 1; iWidth.push_back(beg); iWidth.push_back(fin); for (int j = 0; j < obj->array()->count(); ++j) { const PdfObj *val = obj->array()->obj(j, nullptr); iWidth.push_back(val->number() ? int(val->number()->value()) : 1000); } i += 2; } else return; } } void Face::getSimpleWidth(const PdfDict *d) noexcept { const PdfObj *fc = getPdf(d, "FirstChar"); const PdfObj *wid = getPdf(d, "Widths"); if (!fc || !fc->number() || !wid || !wid->array()) return; int firstChar = int(fc->number()->value()); iWidth.push_back(firstChar); iWidth.push_back(firstChar + wid->array()->count() - 1); for (int i = 0; i < wid->array()->count(); ++i) { const PdfObj *obj = wid->array()->obj(i, nullptr); iWidth.push_back(obj->number() ? int(obj->number()->value()) : 0); } // ipeDebug("Got %d widths entries", iWidth.size()); } // -------------------------------------------------------------------- void Face::getType1Encoding(const PdfDict *d) noexcept { const PdfObj *enc = getPdf(d, "Encoding"); const PdfArray *darr = nullptr; if (enc && enc->dict()) { const PdfObj *diff = getPdf(enc->dict(), "Differences"); if (diff && diff->array()) darr = diff->array(); } if (darr) { // have an encoding as expected String name[0x100]; for (int i = 0; i < 0x100; ++i) name[i] = ".notdef"; int idx = 0; for (int i = 0; i < darr->count(); ++i) { const PdfObj *obj = darr->obj(i, nullptr); if (obj->number()) idx = int(obj->number()->value()); else if (obj->name() && idx < 0x100) name[idx++] = obj->name()->value(); } for (int i = 0; i < 0x100; ++i) { int glyph = FT_Get_Name_Index(iFace, const_cast(name[i].z())); iEncoding.push_back(glyph); } } else { // font descriptor has no encoding, use information in Postscript font if (FT_Has_PS_Glyph_Names(iFace)) { T1_EncodingType type; FT_Get_PS_Font_Value(iFace, PS_DICT_ENCODING_TYPE, 0, (void *) &type, sizeof(type)); if (type == T1_ENCODING_TYPE_ARRAY) { for (int i = 0; i < 0x100; ++i) iEncoding.push_back(FT_Get_Char_Index(iFace, i)); char name[100]; for (int i = 0; i < 0x100; ++i) { FT_Get_PS_Font_Value(iFace, PS_DICT_ENCODING_ENTRY, i, (void *) name, 100); iEncoding[i] = FT_Get_Name_Index(iFace, name); } return; } } // no Postscript glyph names or no Postscript encoding array, fall back for (int k = 0; k < iFace->num_charmaps; ++k) { if (iFace->charmaps[k]->encoding == FT_ENCODING_ADOBE_CUSTOM) { FT_Set_Charmap(iFace, iFace->charmaps[k]); break; } } for (int i = 0; i < 0x100; ++i) iEncoding.push_back(FT_Get_Char_Index(iFace, i)); } } void Face::setupTruetypeEncoding() noexcept { FT_Set_Charmap(iFace, iFace->charmaps[0]); if (iFace->charmaps[0]->platform_id != 1 || iFace->charmaps[0]->encoding_id != 0) { ipeDebug("TrueType face %s has strange first charmap (of %d)", iName.z(), iFace->num_charmaps); for (int i = 0; i < iFace->num_charmaps; ++i) { ipeDebug("Map %d has platform %d, encoding %d", i, iFace->charmaps[i]->platform_id, iFace->charmaps[i]->encoding_id); } } } bool Face::getFontFile(const PdfDict *d, Buffer &data) noexcept { const PdfObj *fontDescriptor = getPdf(d, "FontDescriptor"); if (!fontDescriptor || !fontDescriptor->dict()) return false; const PdfDict *fd = fontDescriptor->dict(); const PdfObj *fontFile = getPdf(fd, "FontFile"); if (!fontFile) fontFile = getPdf(fd, "FontFile2"); if (!fontFile) fontFile = getPdf(fd, "FontFile3"); if (!fontFile || !fontFile->dict() || fontFile->dict()->stream().size() == 0) return false; data = fontFile->dict()->inflate(); // Fix strange header in some pdftex fonts that will cause EPS // export to break. size_t m = data.size() > 1024 ? 1024 : data.size(); std::string s { (const char *) data.data(), m }; size_t i = s.find("FontDirectory"); if (i != std::string::npos) { size_t j = s.find("{save true}{false}ifelse}{false}ifelse", i); if (j != std::string::npos) memset(data.data() + i, ' ', j - i + 38); } return true; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecairo/ipefonts.h0000644000175000017500000000625413561570220016625 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // CanvasFonts maintains the Freetype fonts for the canvas // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEFONTS_H #define IPEFONTS_H #include "ipebase.h" #include "ipegeo.h" #include "iperesources.h" #include #include //------------------------------------------------------------------------ struct FT_FaceRec_; namespace ipe { class PdfResourceBase; class PdfDict; enum class FontType { Type1, Truetype, CIDType0, CIDType2, Unsupported }; class Face { public: Face(const PdfDict *d, const PdfResourceBase *resources) noexcept; ~Face() noexcept; inline bool matches(const PdfDict *d) const noexcept { return d == iFontDict; } inline FontType type() const noexcept { return iType; } int width(int ch) const noexcept; int glyphIndex(int ch) noexcept; inline cairo_font_face_t *cairoFont() noexcept { return iCairoFont; } private: const PdfObj *getPdf(const PdfDict *d, String key) const noexcept; bool getFontFile(const PdfDict *d, Buffer &data) noexcept; void getSimpleWidth(const PdfDict *d) noexcept; void getType1Encoding(const PdfDict *d) noexcept; void setupTruetypeEncoding() noexcept; void getCIDWidth(const PdfDict *d) noexcept; private: const PdfDict *iFontDict; const PdfResourceBase *iResources; FontType iType; String iName; cairo_font_face_t *iCairoFont { nullptr }; FT_FaceRec_ *iFace { nullptr }; std::vector iEncoding; std::vector iWidth; int iDefaultWidth { 1000 }; }; class Fonts { public: Fonts(const PdfResourceBase *resources); Face *getFace(const PdfDict *d); static cairo_font_face_t *screenFont(); static String freetypeVersion(); const PdfResourceBase *resources() const noexcept { return iResources; } private: const PdfResourceBase *iResources; std::list> iFaces; }; } // namespace //------------------------------------------------------------------------ #endif ipe-7.2.13/src/ipecairo/ipethumbs.h0000644000175000017500000000476113561570220016777 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::Thumbnail // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPETHUMBS_H #define IPETHUMBS_H #include "ipedoc.h" #include "ipefonts.h" // -------------------------------------------------------------------- namespace ipe { class Thumbnail { public: enum TargetFormat { ESVG, EPNG, EPS, EPDF }; Thumbnail(const Document *doc, int width); int width() const { return iWidth; } int height() const { return iHeight; } Buffer render(const Page *page, int view); bool saveRender(TargetFormat fm, const char *dst, const Page *page, int view, double zoom, bool transparent, bool nocrop); private: const Document *iDoc; int iWidth; int iHeight; double iZoom; const Layout *iLayout; std::unique_ptr iFonts; }; class PdfThumbnail { public: PdfThumbnail(const PdfFile *pdf, int width); int width() const { return iWidth; } int height() const { return iHeight; } Buffer render(const PdfDict *page); private: const PdfFile *iPdf; int iWidth; int iHeight; std::unique_ptr iCascade; // dummy stylesheet std::unique_ptr iResources; std::unique_ptr iFonts; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecairo/Makefile0000644000175000017500000000211113561570220016251 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for Ipecairo # -------------------------------------------------------------------- OBJDIR = $(BUILDDIR)/obj/ipecairo include ../common.mak TARGET = $(call dll_target,ipecairo) MAKE_SYMLINKS = $(call dll_symlinks,ipecairo) SONAME = $(call soname,ipecairo) INSTALL_SYMLINKS = $(call install_symlinks,ipecairo) CPPFLAGS += -I../include $(CAIRO_CFLAGS) $(FREETYPE_CFLAGS) LIBS += -L$(buildlib) -lipe $(CAIRO_LIBS) $(FREETYPE_LIBS) ifdef WIN32 LIBS += -lgdiplus endif CXXFLAGS += $(DLL_CFLAGS) all: $(TARGET) sources = \ ipecairopainter.cpp \ ipefonts.cpp \ ipethumbs.cpp $(TARGET): $(objects) $(MAKE_LIBDIR) $(CXX) $(LDFLAGS) $(DLL_LDFLAGS) $(SONAME) -o $@ $^ $(LIBS) $(MAKE_SYMLINKS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_SYMLINKS) # -------------------------------------------------------------------- ipe-7.2.13/src/ipecairo/ipecairopainter.h0000644000175000017500000001037213561570220020150 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::CairoPainter // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPECAIROPAINTER_H #define IPECAIROPAINTER_H #include "ipeattributes.h" #include "ipepainter.h" #include "ipefonts.h" #include // -------------------------------------------------------------------- namespace ipe { class Cascade; class PdfObj; class CairoPainter : public Painter { public: CairoPainter(const Cascade *sheet, Fonts *fonts, cairo_t *cc, double zoom, bool pretty); virtual ~CairoPainter() { } void setDimmed(bool dim) { iDimmed = dim; } void executeStream(const PdfDict *stream, const PdfDict *resources); protected: virtual void doPush(); virtual void doPop(); virtual void doMoveTo(const Vector &v); virtual void doLineTo(const Vector &v); virtual void doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3); virtual void doClosePath(); virtual void doDrawArc(const Arc &arc); virtual void doAddClipPath(); virtual void doDrawPath(TPathMode mode); virtual void doDrawBitmap(Bitmap bitmap); virtual void doDrawText(const Text *text); private: const PdfDict *findResource(String kind, String name); void drawGlyphs(std::vector &glyphs); void collectGlyphs(String s, std::vector &glyphs, Vector &textPos); void execute(const PdfDict *stream, const PdfDict *resources, bool applyMatrix = true); void clearArgs(); void opcm(); void opBT(); void opET(); void opTf(); void opTm(); void opTd(bool setLeading); void opTstar(); void opTc(double *p); void opTz(); void opTJ(); void opTj(bool nextLine, bool setSpacing); void opk(bool stroke); void opg(bool stroke); void oprg(bool stroke); void opscn(bool stroke); void opw(); void opd(); void opDo(); void opi(); void opj(); void opJ(); void opM(); void opW(bool eofill); void opgs(); void opm(); void opl(); void opc(); void opy(); void opv(); void oph(); void opq(); void opQ(); void opre(); void opn(); void opStrokeFill(bool close, bool fill, bool stroke, bool eofill); void opsh(); void createPattern(); private: Fonts *iFonts; cairo_t *iCairo; double iZoom; bool iPretty; bool iDimmed; bool iAfterMoveTo; // PDF operator drawing std::vector iArgs; std::vector iResourceStack; struct PdfState { double iStrokeRgb[3]; double iFillRgb[3]; double iStrokeOpacity; double iFillOpacity; Face *iFont; // not owned double iFontSize; double iTextRise; double iCharacterSpacing; double iWordSpacing; double iHorizontalScaling; double iLeading; String iFillPattern; }; std::vector iPdfState; // text matrix is only valid inside BT-ET pairs Matrix iTextMatrix; Matrix iTextLineMatrix; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipelets/0000755000175000017500000000000013561570220014470 5ustar otfriedotfriedipe-7.2.13/src/ipelets/kgon/0000755000175000017500000000000013561570220015426 5ustar otfriedotfriedipe-7.2.13/src/ipelets/kgon/Makefile0000644000175000017500000000165213561570220017072 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for kgon ipelet (an example of a C++ ipelet) # -------------------------------------------------------------------- IPESRCDIR = ../.. OBJDIR = $(BUILDDIR)/obj/ipelets DEPEND = $(OBJDIR)/kgon.depend include ../../common.mak TARGET = $(call ipelet_target,kgon) LUASCRIPT = kgon.lua CPPFLAGS += -I../../include LIBS += -L$(buildlib) -lipe CXXFLAGS += $(DLL_CFLAGS) all: $(TARGET) sources = kgon.cpp $(TARGET): $(objects) $(MAKE_IPELETDIR) $(CXX) $(LDFLAGS) $(PLUGIN_LDFLAGS) -o $@ $^ $(LIBS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPELETDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPELETDIR) $(INSTALL_FILES) $(LUASCRIPT) $(INSTALL_ROOT)$(IPELETDIR) # -------------------------------------------------------------------- ipe-7.2.13/src/ipelets/kgon/kgon.lua0000644000175000017500000000344513561570220017075 0ustar otfriedotfried---------------------------------------------------------------------- -- kgon ipelet description ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] label = "Regular k-gon" about = [[ Constructs a regular k-gon from a circle. This ipelet is part of Ipe. ]] -- this variable will store the C++ ipelet when it has been loaded ipelet = false -- parameters for the C++ code parameters = { n = "7" } function run(model) if not ipelet then ipelet = assert(ipe.Ipelet(dllname)) end model:runIpelet(label, ipelet, 1, parameters) end -- define a shortcut for this function shortcuts.ipelet_1_kgon = "Alt+Ctrl+K" ---------------------------------------------------------------------- ipe-7.2.13/src/ipelets/kgon/kgon.cpp0000644000175000017500000000632113561570220017072 0ustar otfriedotfried// -------------------------------------------------------------------- // Ipelet for creating regular k-gons // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipelet.h" #include "ipepath.h" #include "ipepage.h" using namespace ipe; // -------------------------------------------------------------------- class KGonIpelet : public Ipelet { public: virtual int ipelibVersion() const { return IPELIB_VERSION; } virtual bool run(int, IpeletData *data, IpeletHelper *helper); }; // -------------------------------------------------------------------- bool KGonIpelet::run(int, IpeletData *data, IpeletHelper *helper) { Page *page = data->iPage; int sel = page->primarySelection(); if (sel < 0) { helper->message("No selection"); return false; } const Path *p = page->object(sel)->asPath(); if (p == 0 || p->shape().countSubPaths() != 1 || p->shape().subPath(0)->type() != SubPath::EEllipse) { helper->message("Primary selection is not a circle"); return false; } String str = helper->getParameter("n"); // get default value from Lua wrapper if (!helper->getString("Enter k (number of corners)", str)) return false; int k = Lex(str).getInt(); if (k < 3 || k > 1000) return false; const Ellipse *e = p->shape().subPath(0)->asEllipse(); Matrix m = p->matrix() * e->matrix(); Vector center = m.translation(); Vector v = m * Vector(1,0); double radius = (v - center).len(); Curve *sp = new Curve; double alpha = 2.0 * IpePi / k; Vector v0 = center + radius * Vector(1,0); for (int i = 1; i < k; ++i) { Vector v1 = center + radius * Vector(Angle(i * alpha)); sp->appendSegment(v0, v1); v0 = v1; } sp->setClosed(true); Shape shape; shape.appendSubPath(sp); Path *obj = new Path(data->iAttributes, shape); page->append(ESecondarySelected, data->iLayer, obj); helper->message("Created regular k-gon"); return true; } // -------------------------------------------------------------------- IPELET_DECLARE Ipelet *newIpelet() { return new KGonIpelet; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelets/qvoronoi/0000755000175000017500000000000013561570220016344 5ustar otfriedotfriedipe-7.2.13/src/ipelets/qvoronoi/qvoronoi.lua0000644000175000017500000000373313561570220020731 0ustar otfriedotfried---------------------------------------------------------------------- -- qvoronoi ipelet description ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] label = "Voronoi diagrams" about = [[ Computes Voronoi diagrams and Delaunay triangulations. Uses the Qhull library by C. Bradford Barber and Hannu Huhdanpaa. ]] -- this variable will store the C++ ipelet when it has been loaded ipelet = false function run(model, num) if not ipelet then ipelet = assert(ipe.Ipelet(dllname)) end model:runIpelet(methods[num].label, ipelet, num) end methods = { { label="Delaunay triangulation" }, { label="Voronoi diagram" }, { label="Order-2 Voronoi diagram" }, { label="Order-3 Voronoi diagram" }, { label="Furthest-point Voronoi diagram" }, { label="Set length of infinite edges" }, } ---------------------------------------------------------------------- ipe-7.2.13/src/ipelets/qvoronoi/Makefile0000644000175000017500000000267313561570220020014 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for qvoronoi ipelet # Needs reentrant qhull library (www.qhull.org) # On Ubuntu/Debian: apt install libqhull-r7 libqhull-dev # -------------------------------------------------------------------- IPESRCDIR = ../.. OBJDIR = $(BUILDDIR)/obj/ipelets DEPEND = $(OBJDIR)/qvoronoi.depend include ../../common.mak ifdef WIN32 QHULL_CFLAGS = -I$(IPEDEPS)/include/libqhull_r QHULL_LIBS = -L$(IPEDEPS)/lib -lqhull_r else ifdef MACOS QHULL_CFLAGS = -I$(IPEDEPS)/include/libqhull_r QHULL_LIBS = -L$(IPEDEPS)/lib -lqhull_r else QHULL_CFLAGS ?= -I/usr/include/libqhull_r QHULL_LIBS ?= -lqhull_r endif TARGET = $(call ipelet_target,qvoronoi) LUASCRIPT = qvoronoi.lua CPPFLAGS += -I../../include $(QHULL_CFLAGS) LIBS += -L$(buildlib) $(QHULL_LIBS) -lipe CXXFLAGS += $(DLL_CFLAGS) all: $(TARGET) sources = qvoronoi.cpp $(TARGET): $(objects) $(MAKE_IPELETDIR) $(CXX) $(LDFLAGS) $(PLUGIN_LDFLAGS) -o $@ $^ $(LIBS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPELETDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPELETDIR) $(INSTALL_FILES) $(LUASCRIPT) $(INSTALL_ROOT)$(IPELETDIR) ifdef IPEAPP app: $(INSTALL_DIR) $(RESOURCEDIR)/ipelets $(INSTALL_FILES) qvoronoi.lua $(RESOURCEDIR)/ipelets endif # -------------------------------------------------------------------- ipe-7.2.13/src/ipelets/qvoronoi/qvoronoi.cpp0000644000175000017500000003021213561570220020722 0ustar otfriedotfried// -------------------------------------------------------------------- // Ipelet for computing various Voronoi diagrams // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include extern "C" { #include "qhull_ra.h" } #include "ipelib.h" using namespace ipe; // -------------------------------------------------------------------- struct DelaunayEdge { public: DelaunayEdge(int x, int y) : a(x), b(y) { /* nothing */ } DelaunayEdge() : a(-1), b(-1) { /* nothing */ } public: int a,b; }; inline bool operator<(const DelaunayEdge& x, const DelaunayEdge& y) { return (x.a > y.a || (x.a == y.a && x.b > y.b)); } inline bool operator!=(const DelaunayEdge& x, const DelaunayEdge& y) { return (x.a != y.a || x.b != y.b); } // -------------------------------------------------------------------- class VoronoiIpelet : public Ipelet { public: VoronoiIpelet(); virtual int ipelibVersion() const { return IPELIB_VERSION; } virtual bool run(int function, IpeletData *data, IpeletHelper *helper); private: void addVoronoiEdge(facetT *facet, facetT *neighbor); void addInfiniteEdge(facetT *facet, facetT *neighbor); void voronoiTreatFacet(qhT *qh, facetT *facet); void addDelaunayEdge(int from, int to); void delaunayTreatFacet(qhT *qh, facetT *facet); private: int iVoronoiSign; std::vector iSites; std::vector iEdges; std::vector iDelaunay; double iInfiniteEdgeLength; }; VoronoiIpelet::VoronoiIpelet() { iInfiniteEdgeLength = 100.0; } // -------------------------------------------------------------------- class CollectVisitor : public Visitor { public: CollectVisitor(std::vector &sites); virtual void visitGroup(const Group *obj); virtual void visitPath(const Path *obj); virtual void visitReference(const Reference *obj); private: std::vector &iSites; std::list iStack; }; CollectVisitor::CollectVisitor(std::vector &sites) : iSites(sites) { iStack.push_back(Matrix()); // id matrix } void CollectVisitor::visitGroup(const Group *obj) { iStack.push_back(iStack.back() * obj->matrix()); for (Group::const_iterator it = obj->begin(); it != obj->end(); ++it) (*it)->accept(*this); iStack.pop_back(); } void CollectVisitor::visitPath(const Path *obj) { Matrix m = iStack.back() * obj->matrix(); Shape shape = obj->shape(); for (int i = 0; i < shape.countSubPaths(); ++i) { const Curve *curve = shape.subPath(i)->asCurve(); if (curve) { iSites.push_back(m * curve->segment(0).cp(0)); for (int j = 0; j < curve->countSegments(); ++j) iSites.push_back(m * curve->segment(j).last()); } } } void CollectVisitor::visitReference(const Reference *obj) { String s = obj->name().string(); if (s.left(5) == "mark/") { iSites.push_back(iStack.back() * obj->matrix() * obj->position()); } } // -------------------------------------------------------------------- // // readpoints put points into structure for qhull // // returns: // number of points, array of point coordinates // static coordT *readpoints(qhT *qh, const std::vector &sites, int mode, int *numpoints) { coordT *points, *coords; if (mode < 2 || mode > 3) *numpoints= sites.size(); else if (mode == 2) *numpoints = sites.size() * (sites.size() - 1) / 2; else if (mode == 3) *numpoints = sites.size() * (sites.size() - 1) * (sites.size() - 2) / 6; qh->normal_size = 3 * sizeof(coordT); /* for tracing with qh_printpoint */ coords = points = new coordT[*numpoints * 3]; if (mode < 2 || mode == 4) { for (const auto & site : sites) { *(coords++)= site.x; *(coords++)= site.y; *(coords++)= site.x * site.x + site.y * site.y; } } else if (mode == 2) { for (int i = 0; i < size(sites) - 1; i++) { for (int j = i + 1; j < size(sites); j++) { *(coords++)= (sites[i].x + sites[j].x) / 2.0; *(coords++)= (sites[i].y + sites[j].y) / 2.0; *(coords++)= (sites[i].x * sites[i].x + sites[i].y * sites[i].y + sites[j].x * sites[j].x + sites[j].y * sites[j].y) / 2.0; } } } else if (mode == 3) { for (int i = 0; i < size(sites) - 2; i++) { for (int j = i + 1; j < size(sites) - 1; j++) { for (int k = j + 1; k < size(sites); k++) { *(coords++)= (sites[i].x + sites[j].x + sites[k].x) / 3.0; *(coords++)= (sites[i].y + sites[j].y + sites[k].y) / 3.0; *(coords++)= (sites[i].x * sites[i].x + sites[i].y * sites[i].y + sites[j].x * sites[j].x + sites[j].y * sites[j].y + sites[k].x * sites[k].x + sites[k].y * sites[k].y) / 3.0; } } } } else if (mode == 5) { #if 0 // for medial axis int j = size(sites) - 1; pl_unitvec d; for (int i = 0; i < size(sites); i++) { d = normalized(sites[i] - sites[j]).normal(); // facet has equation (d.x, d.y, 1) * (x,y,z) = c = dot(d, sites[i]); // dualize it to point (-d.x/2, -d.y/2, -c) *(coords++)= -d.x / 2.0; *(coords++)= -d.y / 2.0; *(coords++)= -dot(d, sites[i]); j = i; } #endif } return points; } // -------------------------------------------------------------------- // returns Voronoi vertex dual to facet inline Vector voronoi_vertex(facetT *facet) { return Vector(-0.5 * facet->normal[0]/facet->normal[2], -0.5 * facet->normal[1]/facet->normal[2]); } void VoronoiIpelet::addVoronoiEdge(facetT *facet, facetT *neighbor) { if (facet->id < neighbor->id) { iEdges.push_back(Segment(voronoi_vertex(facet), voronoi_vertex(neighbor))); } } void VoronoiIpelet::addInfiniteEdge(facetT *facet, facetT *neighbor) { Vector dir; Vector v = voronoi_vertex(facet); if (neighbor->normal[2] == 0.0) { // neighboring facet is vertical dir = Vector(neighbor->normal[0], neighbor->normal[2]); } else { dir = v - voronoi_vertex(neighbor); } dir = dir.normalized(); iEdges.push_back(Segment(v, v + iInfiniteEdgeLength * dir)); } void VoronoiIpelet::voronoiTreatFacet(qhT *qh, facetT *facet) { facetT *neighbor, **neighborp; if (!facet) return; if (qh_skipfacet(qh, facet)) return; if (facet == qh_MERGEridge) return; if (facet == qh_DUPLICATEridge) return; if (iVoronoiSign * facet->normal[2] >= 0.0) return; FOREACHneighbor_(facet) { if (neighbor != qh_MERGEridge && neighbor != qh_DUPLICATEridge) { if (iVoronoiSign * neighbor->normal[2] < 0.0) { // make Voronoi edge between the two facets addVoronoiEdge(facet, neighbor); } else { addInfiniteEdge(facet, neighbor); } } } } // -------------------------------------------------------------------- void VoronoiIpelet::addDelaunayEdge(int from, int to) { if (from < to) iDelaunay.push_back(DelaunayEdge(to, from)); else iDelaunay.push_back(DelaunayEdge(from, to)); } void VoronoiIpelet::delaunayTreatFacet(qhT *qh, facetT *facet) { setT *vertices; vertexT *vertex, **vertexp; if (!facet) return; if (qh_skipfacet(qh, facet)) return; if (facet == qh_MERGEridge) return; if (facet == qh_DUPLICATEridge) return; if (facet->normal[2] >= 0.0) return; vertices= qh_facet3vertex(qh, facet); int id, first_id = -1, last_id = -1; FOREACHvertex_(vertices) { id = qh_pointid(qh, vertex->point); if (last_id >= 0) { addDelaunayEdge(last_id, id); last_id = id; } else { last_id = first_id = id; } } addDelaunayEdge(last_id, first_id); qh_settempfree(qh, &vertices); } // -------------------------------------------------------------------- #if 0 // for medial axis: single convex polygon only for (Object *ob = ium_input; ob; ob = ob->next) { if (ob->type == IPE_LINE) { if (size(sites) > 0 || !ob->w.line->closed) { ium_message = "can handle single convex polygon only"; ium_end(); } // check whether the polygon is really convex pl_polygon pgn(ob->w.line->v); if (!pgn.is_convex()) { ium_message = "can handle single convex polygon only"; ium_end(); } if (pgn.is_clockwise()) pgn.invert_orientation(); sites = pgn.all_vertices(); } else if (ob->type != IPE_TEXT) { ium_message = "can handle single convex polygon only"; ium_end(); } } #endif bool VoronoiIpelet::run(int function, IpeletData *data, IpeletHelper *helper) { ipeDebug("VoronoiIpelet::run(%d)", function); if (function == 5) { char buf[32]; std::sprintf(buf, "%g", iInfiniteEdgeLength); String el(buf); if (helper->getString("Length of infinite edges (in points):", el)) iInfiniteEdgeLength = std::strtod(el.z(), nullptr); return false; } iVoronoiSign = (function == 4) ? -1 : 1; iSites.clear(); CollectVisitor vis(iSites); for (int it = 0; it < data->iPage->count(); ++it) { if (data->iPage->select(it)) data->iPage->object(it)->accept(vis); } if (iSites.size() < 4) { helper->messageBox("You need to select at least four sites", nullptr, 0); return false; } qhT qh_qh; // Qhull's data structure. qhT *qh= &qh_qh; QHULL_LIB_CHECK // Check for compatible library ipeDebug("qh_meminit"); qh_meminit(qh, stderr); qh_initqhull_start(qh, stdin, stdout, stderr); int numpoints = 0; coordT *points = nullptr; if (!setjmp(qh->errexit)) { points = readpoints(qh, iSites, function, &numpoints); qh_initqhull_globals(qh, points, numpoints, 3, False); ipeDebug("qh_initqhull_mem()"); qh_initqhull_mem(qh); /* mem.c and set.c are initialized */ qh_initqhull_buffers(qh); qh_initthresholds(qh, qh->qhull_command); if (qh->SCALEinput) qh_scaleinput(qh); if (qh->ROTATErandom >= 0) { qh_randommatrix(qh, qh->gm_matrix, qh->hull_dim, qh->gm_row); qh_gram_schmidt(qh, qh->hull_dim, qh->gm_row); qh_rotateinput(qh, qh->gm_row); } qh_qhull(qh); qh_check_output(qh); #ifndef WIN32 // this crashes on Windows. Why? ipeDebug("qh_produce_output()"); qh_produce_output(qh); #endif if (qh->VERIFYoutput && !qh->FORCEoutput && !qh->STOPpoint && !qh->STOPcone) qh_check_points(qh); // now create segments for Ipe facetT *facet, *facetlist = qh->facet_list; FORALLfacet_(facetlist) { if (!function) delaunayTreatFacet(qh, facet); else voronoiTreatFacet(qh, facet); } Group *group = new Group; if (!function) { std::sort(iDelaunay.begin(), iDelaunay.end()); for (int j = 0; j < size(iDelaunay); j++) { if (!j || iDelaunay[j] != iDelaunay[j-1]) { Vector a(points[3*iDelaunay[j].a], points[3*iDelaunay[j].a + 1]); Vector b(points[3*iDelaunay[j].b], points[3*iDelaunay[j].b + 1]); group->push_back(new Path(data->iAttributes, Shape(Segment(a, b)))); } } } else { for (const auto & edge : iEdges) group->push_back(new Path(data->iAttributes, Shape(edge))); } data->iPage->append(ESecondarySelected, data->iLayer, group); } ipeDebug("qh_freehull(True)"); qh_freeqhull(qh, True); delete [] points; iEdges.clear(); iSites.clear(); iDelaunay.clear(); return true; } // -------------------------------------------------------------------- IPELET_DECLARE Ipelet *newIpelet() { return new VoronoiIpelet; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipelets/lua/0000755000175000017500000000000013561570220015251 5ustar otfriedotfriedipe-7.2.13/src/ipelets/lua/symbols.lua0000644000175000017500000001525513561570220017454 0ustar otfriedotfried---------------------------------------------------------------------- -- symbols ipelet ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] label = "Symbols" revertOriginal = _G.revertOriginal about = [[ Functions for creating, using, and editing symbols. This ipelet is part of Ipe. ]] V = ipe.Vector current_symbol = nil current_group = nil current_element = nil ---------------------------------------------------------------------- PASTETOOL = {} PASTETOOL.__index = PASTETOOL function PASTETOOL:new(model, name) local tool = {} _G.setmetatable(tool, PASTETOOL) tool.model = model tool.pos = model.ui:pos() tool.name = name tool.size = 1 if name:match("%(s?f?p?x%)$") then tool.size = model.doc:sheets():find("symbolsize", model.attributes.symbolsize) end local obj = model.doc:sheets():find("symbol", name) model.ui:pasteTool(obj, tool) tool.setColor(1.0, 0, 0) return tool end function PASTETOOL:mouseButton(button, modifiers, press) self.model.ui:finishTool() local obj = ipe.Reference(self.model.attributes, self.name, self.pos) self.model:creation("create symbol", obj) end function PASTETOOL:mouseMove(button, modifiers) self.pos = self.model.ui:pos() self.setMatrix(ipe.Matrix(self.size, 0, 0, self.size, self.pos.x, self.pos.y)) self.model.ui:update(false) -- update tool end function PASTETOOL:key(code, modifiers, text) if text == "\027" then self.model.ui:finishTool() return true else return false end end ---------------------------------------------------------------------- function select_symbol(model) local s = model.doc:sheets():allNames("symbol") local symbolsByGroup = {} for _, sym in ipairs(s) do local i = sym:find("/") local g, n if i then g = sym:sub(1, i-1) n = sym:sub(i+1) else g = "" n = sym end if not symbolsByGroup[g] then symbolsByGroup[g] = {} end local sbg = symbolsByGroup[g] sbg[#sbg+1] = n end local groups = {} for g,sbg in pairs(symbolsByGroup) do groups[#groups+1] = g end table.sort(groups) local d = ipeui.Dialog(model.ui:win(), "Use symbol") groups.action = function (d) local g = d:get("group") if g ~= current_group then current_group = g local syms = symbolsByGroup[groups[g]] d:set("select", syms) end end d:add("label", "label", { label = "Select symbol" }, 1, 1, 1, 3) d:add("group", "combo", groups, 2, 1, 1, 3) if current_group == nil then current_group = 1 end d:set("group", current_group) d:add("select", "combo", symbolsByGroup[groups[current_group]], 3, 1, 1, 3) if current_element then d:set("select", current_element) end d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("column", 1, 1) if not d:execute() then return end current_element = d:get("select") local g = groups[current_group] local sym = symbolsByGroup[g][current_element] if g ~= "" then g = g .. "/" end return g .. sym end function use_symbol(model, num) local name = select_symbol(model) if not name then return end if num == 1 then PASTETOOL:new(model, name) else -- clone symbol local obj = model.doc:sheets():find("symbol", name) model:creation("clone symbol", obj) end end function use_current_symbol(model, num) if not current_symbol then model.ui:explain("current symbol has not been set") else PASTETOOL:new(model, current_symbol) end end function select_current_symbol(model, num) local name = select_symbol(model) if not name then return end current_symbol = name end ---------------------------------------------------------------------- function create_symbol(model, num) local p = model:page() local prim = p:primarySelection() if not prim then model.ui:explain("no selection") return end local str = model:getString("Enter name of new symbol") if not str or str:match("^%s*$") then return end local name = str:match("^%s*%S+%s*$") local old = model.doc:sheets():find("symbol", name) if old then local r = ipeui.messageBox(model.ui:win(), "question", "Symbol '" .. name .. "' already exists", "Do you want to proceed?", "okcancel") if r <= 0 then return end end if num == 3 then -- new stylesheet local sheet = ipe.Sheet() sheet:add("symbol", name, p[prim]) local t = { label = methods[num].label, sheet = sheet, } t.redo = function (t, doc) doc:sheets():insert(1, t.sheet:clone()) end t.undo = function (t, doc) doc:sheets():remove(1) end model:register(t) else -- top stylesheet local sheet = model.doc:sheets():sheet(1) local t = { label = methods[num].label, original = sheet:clone(), final = sheet:clone(), } t.final:add("symbol", name, p[prim]) t.redo = function (t, doc) doc:sheets():remove(1) doc:sheets():insert(1, t.final:clone()) end t.undo = function (t, doc) doc:sheets():remove(1) doc:sheets():insert(1, t.original:clone()) end model:register(t) end end ---------------------------------------------------------------------- methods = { { label = "use symbol", run = use_symbol }, { label = "use current symbol", run = use_current_symbol }, { label = "create symbol (in new style sheet)", run = create_symbol }, { label = "create symbol (in top style sheet)", run = create_symbol }, { label = "clone symbol", run = use_symbol }, { label = "select current symbol", run = select_current_symbol } } ---------------------------------------------------------------------- ipe-7.2.13/src/ipelets/lua/align.lua0000644000175000017500000003052313561570220017051 0ustar otfriedotfried---------------------------------------------------------------------- -- align ipelet ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] label = "Align && distribute" revertOriginal = _G.revertOriginal about = [[ Several alignment functions. This ipelet is part of Ipe. ]] V = ipe.Vector skip = 0.0 ---------------------------------------------------------------------- function set_skip(model) local str = model:getString("Enter skip in points") if not str or str:match("^%s*$") then return end local s = tonumber(str) if not s then model:warning("Enter distance between consecutive objects in points") return end skip = s model.ui:explain("set skip distance to " .. skip .. " points") end ---------------------------------------------------------------------- function simple_align(model, num) local p = model:page() if not p:hasSelection() then model.ui:explain("no selection") return end local pin = {} local selection = {} for i, obj, sel, lay in p:objects() do if sel == 2 then pin[obj:get("pinned")] = true selection[#selection + 1] = i end end if #selection == 0 then model.ui:explain("nothing to align") return end if (pin.fixed or pin.horizontal and methods[num].need_h or pin.vertical and methods[num].need_v) then model:warning("Cannot align objects", "Some object is pinned and cannot be moved") return end local prim = p:primarySelection() local pbox = p:bbox(prim) local pref = pbox:bottomLeft() local pobj = p[prim] if pobj:type() == "text" then pref = pobj:matrix() * pobj:position() end local t = { label = "align " .. methods[num].label, pno = model.pno, vno = model.vno, selection = selection, original = p:clone(), undo = revertOriginal, pbox = pbox, pref = pref, fn = num, } t.redo = function (t, doc) local p = doc[t.pno] for _,i in ipairs(t.selection) do local box = p:bbox(i) local ref = box:bottomLeft() if (p[i]:type() == "text") then ref = p[i]:matrix() * p[i]:position() end local vx, vy = 0, 0 if (t.fn == 1) then -- top vy = t.pbox:top() - box:top() elseif (t.fn == 2) then -- bottom vy = t.pbox:bottom() - box:bottom() elseif (t.fn == 3) then -- left vx = t.pbox:left() - box:left() elseif (t.fn == 4) then -- right vx = t.pbox:right() - box:right() elseif (t.fn == 5) then -- center vx = 0.5 * ((t.pbox:left() + t.pbox:right()) - (box:left() + box:right())) vy = 0.5 * ((t.pbox:bottom() + t.pbox:top()) - (box:bottom() + box:top())) elseif (t.fn == 6) then -- h center vx = 0.5 * ((t.pbox:left() + t.pbox:right()) - (box:left() + box:right())) elseif (t.fn == 7) then -- v center vy = 0.5 * ((t.pbox:bottom() + t.pbox:top()) - (box:bottom() + box:top())) elseif (t.fn == 8) then -- baseline vy = t.pref.y - ref.y end p:transform(i, ipe.Translation(V(vx, vy))) end end model:register(t) end ---------------------------------------------------------------------- function sequence_align_setup(model, num, movement) local p = model:page() if not p:hasSelection() then model.ui:explain("no selection") return end local pin = {} for i, obj, sel, lay in p:objects() do if sel then pin[obj:get("pinned")] = true end end if pin.fixed or pin[movement] then model:warning("Cannot align objects", "Some object is pinned and cannot be moved") return false end return true end ---------------------------------------------------------------------- function ltr_skip(p, selection) local dx = { 0 } local xtarget = p:bbox(selection[1]):right() + skip for i = 2,#selection do local j = selection[i] dx[i] = xtarget - p:bbox(j):left() xtarget = xtarget + p:bbox(j):width() + skip end return dx end function ltr_equal_gaps(p, selection) local dx = { 0 } local total = 0.0 for _,i in ipairs(selection) do total = total + p:bbox(i):width() end local skip = (p:bbox(selection[#selection]):right() - p:bbox(selection[1]):left() - total) / (#selection - 1) local xtarget = p:bbox(selection[1]):right() + skip for i = 2,#selection-1 do local j = selection[i] dx[i] = xtarget - p:bbox(j):left() xtarget = xtarget + p:bbox(j):width() + skip end dx[#selection] = 0 return dx end function ltr_centers(p, selection) local dx = { 0 } local front = p:bbox(selection[1]) local rear = p:bbox(selection[#selection]) local fcenter = (front:left() + front:right()) / 2 local rcenter = (rear:left() + rear:right()) / 2 local step = (rcenter - fcenter) / (#selection - 1) for i = 2,#selection-1 do local box = p:bbox(selection[i]) local center = (box:left() + box:right()) / 2 dx[i] = (fcenter + (i-1) * step) - center end dx[#selection] = 0 return dx end function ltr_left(p, selection) local dx = { 0 } local front = p:bbox(selection[1]) local rear = p:bbox(selection[#selection]) local fleft = front:left() local step = (rear:left() - fleft) / (#selection - 1) for i = 2,#selection-1 do local box = p:bbox(selection[i]) dx[i] = (fleft + (i-1) * step) - box:left() end dx[#selection] = 0 return dx end function ltr_right(p, selection) local dx = { 0 } local front = p:bbox(selection[1]) local rear = p:bbox(selection[#selection]) local fright = front:right() local step = (rear:right() - fright) / (#selection - 1) for i = 2,#selection-1 do local box = p:bbox(selection[i]) dx[i] = (fright + (i-1) * step) - box:right() end dx[#selection] = 0 return dx end function ltr(model, num) if not sequence_align_setup(model, num, "horizontal") then return end local p = model:page() local selection = model:selection() table.sort(selection, function (a,b) return (p:bbox(a):left() < p:bbox(b):left()) end) if #selection == 1 or #selection == 2 and methods[num].compute ~= ltr_skip then model.ui:explain("nothing to distribute") return end local dx = methods[num].compute(p, selection) local t = { label = methods[num].label, pno = model.pno, vno = model.vno, selection = selection, original = p:clone(), undo = revertOriginal, dx = dx, } t.redo = function (t, doc) local p = doc[t.pno] for i = 1,#t.selection do local j = t.selection[i] local dx = t.dx[i] if dx ~= 0 then p:transform(j, ipe.Translation(V(dx, 0.0))) end end end model:register(t) end ---------------------------------------------------------------------- function ttb_skip(p, selection) local dy = { 0 } local ytarget = p:bbox(selection[1]):bottom() - skip for i = 2,#selection do local j = selection[i] dy[i] = ytarget - p:bbox(j):top() ytarget = ytarget - p:bbox(j):height() - skip end return dy end function ttb_equal_gaps(p, selection) local dy = { 0 } local total = 0.0 for _,i in ipairs(selection) do total = total + p:bbox(i):height() end local skip = (p:bbox(selection[1]):top() - p:bbox(selection[#selection]):bottom() - total) / (#selection - 1) local ytarget = p:bbox(selection[1]):bottom() - skip for i = 2,#selection-1 do local j = selection[i] dy[i] = ytarget - p:bbox(j):top() ytarget = ytarget - p:bbox(j):height() - skip end dy[#selection] = 0 return dy end function ttb_centers(p, selection) local dy = { 0 } local front = p:bbox(selection[1]) local rear = p:bbox(selection[#selection]) local fcenter = (front:top() + front:bottom()) / 2 local rcenter = (rear:top() + rear:bottom()) / 2 local step = (fcenter - rcenter) / (#selection - 1) for i = 2,#selection-1 do local box = p:bbox(selection[i]) local center = (box:top() + box:bottom()) / 2 dy[i] = (fcenter - (i-1) * step) - center end dy[#selection] = 0 return dy end function ttb_top(p, selection) local dy = { 0 } local front = p:bbox(selection[1]) local rear = p:bbox(selection[#selection]) local ftop = front:top() local step = (ftop - rear:top()) / (#selection - 1) for i = 2,#selection-1 do local box = p:bbox(selection[i]) dy[i] = (ftop - (i-1) * step) - box:top() end dy[#selection] = 0 return dy end function ttb_bottom(p, selection) local dy = { 0 } local front = p:bbox(selection[1]) local rear = p:bbox(selection[#selection]) local fbottom = front:bottom() local step = (fbottom - rear:bottom()) / (#selection - 1) for i = 2,#selection-1 do local box = p:bbox(selection[i]) dy[i] = (fbottom - (i-1) * step) - box:bottom() end dy[#selection] = 0 return dy end function ttb(model, num) if not sequence_align_setup(model, num, "vertical") then return end local p = model:page() local selection = model:selection() table.sort(selection, function (a,b) return (p:bbox(a):top() > p:bbox(b):top()) end) if #selection == 1 or #selection == 2 and methods[num].compute ~= ttb_skip then model.ui:explain("nothing to distribute") return end local dy = methods[num].compute(p, selection) local t = { label = methods[num].label, pno = model.pno, vno = model.vno, selection = selection, original = p:clone(), undo = revertOriginal, dy = dy, } t.redo = function (t, doc) local p = doc[t.pno] for i = 1,#t.selection do local j = t.selection[i] local dy = t.dy[i] if dy ~= 0 then p:transform(j, ipe.Translation(V(0.0, dy))) end end end model:register(t) end ---------------------------------------------------------------------- methods = { { label = "align top", run = simple_align, need_v = true }, { label = "align bottom", run = simple_align, need_v = true }, { label = "align left", run = simple_align, need_h = true }, { label = "align right", run = simple_align, need_h = true }, { label = "align center", run = simple_align, need_v = true, need_h = true }, { label = "align H center", run = simple_align, need_h = true }, { label = "align V center", run = simple_align, need_v = true }, { label = "align baseline", run = simple_align, need_v = true }, { label = "distribute left to right", run=ltr, compute = ltr_skip }, { label = "distribute horizontally", run=ltr, compute = ltr_equal_gaps }, { label = "distribute H centers evenly", run=ltr, compute = ltr_centers }, { label = "distribute left sides evenly", run=ltr, compute = ltr_left }, { label = "distribute right sides evenly", run=ltr, compute = ltr_right }, { label = "distribute top to bottom", run=ttb, compute = ttb_skip }, { label = "distribute vertically", run=ttb, compute = ttb_equal_gaps }, { label = "distribute V centers evenly", run=ttb, compute = ttb_centers }, { label = "distribute top sides evenly", run=ttb, compute = ttb_top }, { label = "distribute bottom sides evenly", run=ttb, compute = ttb_bottom }, { label = "set skip...", run = set_skip }, } shortcuts.ipelet_1_align = "Shift+T" shortcuts.ipelet_2_align = "Shift+B" shortcuts.ipelet_3_align = "Shift+L" shortcuts.ipelet_4_align = "Shift+R" shortcuts.ipelet_5_align = "Shift+C" shortcuts.ipelet_6_align = "Shift+H" shortcuts.ipelet_7_align = "Shift+V" shortcuts.ipelet_15_align = "Alt+Shift+V" ---------------------------------------------------------------------- ipe-7.2.13/src/ipelets/lua/selectby.lua0000644000175000017500000001035613561570220017573 0ustar otfriedotfried---------------------------------------------------------------------- -- selectby ipelet ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] label = "Select by type/attribute" about = [[ Select objects based on their type or attribute value. This ipelet is part of Ipe. ]] function run(model) local s = "Please indicate the attributes on which to base object selection.\n" .. "Ipe will select all objects on the current page where the indicated attributes match the current setting in the UI." local d = ipeui.Dialog(model.ui:win(), "Select by type/attribute") d:add("label1", "label", {label=s}, 1, 1, 2, 2) local objtypes = { "All types", "path", "text", "reference", "image", "group" } d:add("objtype", "combo", objtypes, 3, 1) d:add("stroke", "checkbox", {label="Stroke color"}, 3, 2) d:add("pinned", "checkbox", {label="Pinning"}, 4, 1) d:add("opacity", "checkbox", {label="Opacity"}, 4, 2) d:add("label2", "label", {label=""}, 5, 1, 2, 1) d:add("pathlabel", "label", {label="Path objects"}, 6, 1) d:add("fill", "checkbox", {label="Fill color"}, 7, 1) d:add("pen", "checkbox", {label="Line width"}, 8, 1) d:add("dashstyle", "checkbox", {label="Dash style"}, 9, 1) d:add("pathmode", "checkbox", {label="Stroke && fill style"}, 10, 1) d:add("gradient", "checkbox", {label="Gradient pattern"}, 11, 1) d:add("tiling", "checkbox", {label="Tiling pattern"}, 12, 1) d:add("textlabel", "label", {label="Text objects"}, 6, 2) d:add("textsize", "checkbox", {label="Text size"}, 7, 2) d:add("textstyle", "checkbox", {label="Minipage style"}, 8, 2) d:add("labelstyle", "checkbox", {label="Label style"}, 9, 2) d:add("horizontalalignment", "checkbox", {label="Horizontal alignment"}, 10, 2) d:add("verticalalignment", "checkbox", {label="Vertical alignment"}, 11, 2) d:add("label3", "label", {label=""}, 13, 1, 2, 1) d:add("markshape", "checkbox", {label="Mark type"}, 14, 1) d:add("symbolsize", "checkbox", {label="Symbol size"}, 14, 2) d:add("transformations", "checkbox", {label="Allowed transformations"}, 15, 1) d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") if not d:execute() then return end local keys = { "stroke", "pinned", "opacity", "fill", "pen", "dashstyle", "pathmode", "gradient", "tiling", "textsize", "textstyle", "labelstyle", "horizontalalignment", "verticalalignment", "markshape", "symbolsize", "transformations" } local needed = { } local needType = nil if d:get("objtype") ~= 1 then needType = objtypes[d:get("objtype")] end for _, k in ipairs(keys) do needed[k] = d:get(k) end print("---") _G.printTable(needed) -- perform selection local p = model:page() local a = model.attributes print("---") _G.printTable(a) print("---") for i,obj,sel,layer in p:objects(p) do local soundsGood = 2 if needType and obj:type() ~= needType then soundsGood = nil end for _,k in ipairs(keys) do if needed[k] and obj:get(k) ~= a[k] then soundsGood = nil end end p:setSelect(i, soundsGood) end p:ensurePrimarySelection() end ---------------------------------------------------------------------- ipe-7.2.13/src/ipelets/lua/goodies.lua0000644000175000017500000002671113561570220017414 0ustar otfriedotfried---------------------------------------------------------------------- -- goodies ipelet ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] label = "Goodies" revertOriginal = _G.revertOriginal about = [[ Several small functions, like precise scale and rotate, precise boxes, marking circle centers, regular k-gons. This ipelet is part of Ipe. ]] V = ipe.Vector local function bounding_box(p) local box = ipe.Rect() for i,obj,sel,layer in p:objects() do if sel then box:add(p:bbox(i)) end end return box end local function boxshape(v1, v2) return { type="curve", closed=true; { type="segment"; v1, V(v1.x, v2.y) }, { type="segment"; V(v1.x, v2.y), v2 }, { type="segment"; v2, V(v2.x, v1.y) } } end function preciseTransform(model, num) local p = model:page() if not p:hasSelection() then model.ui:explain("no selection") return end if num==3 and not model.snap.with_axes then model:warning("Cannot mirror at x-axis", "The coordinate system has not been set") return end -- check pinned for i, obj, sel, layer in p:objects() do if sel and obj:get("pinned") ~= "none" then model:warning("Cannot transform objects", "At least one of the objects is pinned") return end end local matrix local label = methods[num].label if num == 1 then -- mirror horizontal matrix = ipe.Matrix(-1, 0, 0, 1, 0, 0) elseif num == 2 then -- Mirror vertical matrix = ipe.Matrix(1, 0, 0, -1, 0, 0) elseif num == 3 then -- Mirror at x-axis matrix = (ipe.Rotation(model.snap.orientation) * ipe.Matrix(1, 0, 0, -1, 0, 0) * ipe.Rotation(-model.snap.orientation)) elseif num == 4 then -- turn 90 degrees matrix = ipe.Matrix(0, 1, -1, 0, 0, 0) elseif num == 5 then -- turn 180 degrees matrix = ipe.Matrix(-1, 0, 0, -1, 0, 0) elseif num == 6 then -- turn 270 degrees matrix = ipe.Matrix(0, -1, 1, 0, 0, 0) elseif num == 7 then -- rotate by angle local str = model:getString("Enter angle in degrees") if not str or str:match("^%s*$") then return end local degrees = tonumber(str) if not degrees then model:warning("Please enter angle in degrees") return end matrix = ipe.Rotation(math.pi * degrees / 180.0) label = "rotation by " .. degrees .. " degrees" elseif num == 8 then -- stretch or scale local str = model:getString("Enter stretch factors") if not str or str:match("^%s*$") then return end if str:match("^[%+%-%d%.]+$") then local sx = tonumber(str) if sx == 0 then model:warning("Illegal scale factor", "You cannot use a zero scale factor") return end label = "scale by " .. sx matrix = ipe.Matrix(sx, 0, 0, sx, 0, 0) else local ssx, ssy = str:match("^([%+%-%d%.]+)%s+([%+%-%d%.]+)$") if not ssx then model:warning("Please enter numeric stretch factors", "You can either enter a single number to scale the object" .. " or two numbers to stretch in x and y directions.") return end local sx, sy = tonumber(ssx), tonumber(ssy) if sx == 0 or sy == 0 then model:warning("Illegal stretch factor", "You cannot use a zero stretch factor") return end label = "stretch by " .. sx .. ", " .. sy matrix = ipe.Matrix(sx, 0, 0, sy, 0, 0) end end local origin if model.snap.with_axes then origin = model.snap.origin else local box = bounding_box(p) origin = 0.5 * (box:bottomLeft() + box:topRight()) end matrix = ipe.Translation(origin) * matrix * ipe.Translation(-origin) local t = { label = label, pno = model.pno, vno = model.vno, selection = model:selection(), original = model:page():clone(), matrix = matrix, undo = revertOriginal, } t.redo = function (t, doc) local p = doc[t.pno] for _,i in ipairs(t.selection) do p:transform(i, t.matrix) end end model:register(t) end function rotateAxis(model, num) if not model.snap.with_axes then model:warning("Cannot rotate coordinate system", "The coordinate system has not been set") return end local str = model:getString("Enter angle in degrees") if not str or str:match("^%s*$") then return end local degrees = tonumber(str) if not degrees then model:warning("Please enter angle in degrees") return end local rad = math.pi * degrees / 180.0 model.snap.orientation = model.snap.orientation + rad if model.snap.orientation >= 2 * math.pi then model.snap.orientation = model.snap.orientation - 2 * math.pi elseif model.snap.orientation < 0 then model.snap.orientation = model.snap.orientation + 2 * math.pi end model:setSnap() end function preciseBox(model) local dpmm = 72.0 / 25.4 local str = model:getString("Enter width and height in mm") if not str or str:match("^%s*$") then return end local ssx, ssy = str:match("^([%+%-%d%.]+)%s+([%+%-%d%.]+)$") if not ssx then model:warning("Please enter selfwidth and height in mm", "Separate the two numbers by a space.") return end local sx, sy = tonumber(ssx), tonumber(ssy) local shape = { boxshape(V(0,0), V(sx * dpmm, sy * dpmm)) } local obj = ipe.Path(model.attributes, shape) model:creation("create precise box", obj) end function boundingBox(model) local box = bounding_box(model:page()) local shape = { boxshape(box:bottomLeft(), box:topRight()) } local obj = ipe.Path(model.attributes, shape) model:creation("create bounding box", obj) end function mediaBox(model) local layout = model.doc:sheets():find("layout") local shape = { boxshape(-layout.origin, -layout.origin + layout.papersize) } local obj = ipe.Path(model.attributes, shape) model:creation("create mediabox", obj) end function checkPrimaryIsCircle(model, arc_ok) local p = model:page() local prim = p:primarySelection() if not prim then model.ui:explain("no selection") return end local obj = p[prim] if obj:type() == "path" then local shape = obj:shape() if #shape == 1 then local s = shape[1] if s.type == "ellipse" then return prim, obj, s[1]:translation(), shape end if arc_ok and s.type == "curve" and #s == 1 and s[1].type == "arc" then return prim, obj, s[1].arc:matrix():translation(), shape end end end if arc_ok then model:warning("Primary selection is not an arc, a circle, or an ellipse") else model:warning("Primary selection is not a circle or an ellipse") end end function markCircleCenter(model) local prim, obj, pos, shape = checkPrimaryIsCircle(model, true) if not prim then return end local obj = ipe.Reference(model.attributes, model.attributes.markshape, obj:matrix() * pos) model:creation("mark circle center", obj) end local function incorrect_input(model) model:warning("Cannot create parabolas", "Primary selection is not a segment, or " .. "other selected objects are not marks") end function parabola(model) local p = model:page() local prim = p:primarySelection() if not prim then model.ui:explain("no selection") return end local seg = p[prim] if seg:type() ~= "path" then incorrect_input(model) return end local shape = seg:shape() if #shape ~= 1 or shape[1].type ~= "curve" or #shape[1] ~= 1 or shape[1][1].type ~= "segment" then incorrect_input(model) return end local marks = {} for i,obj,sel,layer in p:objects() do if sel == 2 then if obj:type() ~= "reference" or obj:symbol():sub(1,5) ~= "mark/" then incorrect_input(model) return end marks[#marks + 1] = obj:matrix() * obj:position() end end if #marks == 0 then incorrect_input(model) return end local p0 = seg:matrix() * shape[1][1][1] local p1 = seg:matrix() * shape[1][1][2] local tfm = ipe.Translation(p0) * ipe.Rotation((p1 - p0):angle()) local inv = tfm:inverse() -- treat x-interval from 0 to xmax local xmax = (p1 - p0):len() local parabolas = { } for i,pos in ipairs(marks) do local mrk = inv * pos local a = -mrk.x local b = xmax - mrk.x -- the following are the three control points for the unit -- parabola between x = a and x = b local q0 = V(a, a*a) local q1 = V(0.5*(a + b), a*b) local q2 = V(b, b*b) local curve = { type="curve", closed=false; { type="spline", q0, q1, q2 } } local obj = ipe.Path(model.attributes, { curve } ) local stretch = 2.0 * mrk.y; local offs = V(mrk.x, mrk.y / 2.0) local m = (tfm * ipe.Translation(offs) * ipe.Matrix(1, 0, 0, 1.0/stretch, 0, 0)) obj:setMatrix(m); parabolas[#parabolas + 1] = obj end if #parabolas > 1 then local obj = ipe.Group(parabolas) model:creation("create parabolas", obj) else model:creation("create parabola", parabolas[1]) end end function regularKGon(model) local prim, obj, pos, shape = checkPrimaryIsCircle(model, false) if not prim then return end local str = model:getString("Enter number of corners") if not str or str:match("^%s*$)") then return end local k = tonumber(str) if not k then model:warning("Enter a number between 3 and 1000!") return end local m = shape[1][1] local center = m:translation() local v = m * V(1,0) local radius = (v - center):len() local curve = { type="curve", closed=true } local alpha = 2 * math.pi / k local v0 = center + radius * V(1,0) for i = 1,k-1 do local v1 = center + radius * ipe.Direction(i * alpha) curve[#curve + 1] = { type="segment", v0, v1 } v0 = v1 end local kgon = ipe.Path(model.attributes, { curve } ) kgon:setMatrix(obj:matrix()) model:creation("create regular k-gon", kgon) end methods = { { label = "Mirror horizontal", run=preciseTransform }, { label = "Mirror vertical", run=preciseTransform }, { label = "Mirror at x-axis", run=preciseTransform }, { label = "Turn 90 degrees", run=preciseTransform }, { label = "Turn 180 degrees", run=preciseTransform }, { label = "Turn 270 degrees", run=preciseTransform }, { label = "Precise rotate", run=preciseTransform }, { label = "Precise stretch", run=preciseTransform }, { label = "Rotate coordinate system", run=rotateAxis }, { label = "Insert precise box", run=preciseBox }, { label = "Insert bounding box", run=boundingBox }, { label = "Insert media box", run=mediaBox }, { label = "Mark circle center", run=markCircleCenter }, { label = "Make parabolas", run=parabola }, { label = "Regular k-gon", run=regularKGon }, } ---------------------------------------------------------------------- ipe-7.2.13/src/ipelets/lua/search-replace.lua0000644000175000017500000000545013561570220020636 0ustar otfriedotfried---------------------------------------------------------------------- -- search-replace ipelet ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] label = "Search && replace" about = [[ Search and replace text in selected text objects. This ipelet is part of Ipe. ]] function run(model) local s = [[Enter pattern and replacement text. The pattern will be substituted by the replacement text in all selected text objects. The substitution does not occur inside groups.]] local d = ipeui.Dialog(model.ui:win(), "Search & replace") d:add("label1", "label", {label=s}, 1, 1, 1, 4) d:add("label2", "label", {label="Pattern"}, 2, 1) d:add("pattern", "input", {}, 2, 2, 1, 3) d:add("label3", "label", {label="Replace by"}, 3, 1) d:add("replace", "input", {}, 3, 2, 1, 3) d:add("regex", "checkbox", {label="Use Lua patterns"}, 4, 1, 1, 4) d:addButton("ok", "&Ok", "accept") d:addButton("cancel", "&Cancel", "reject") d:setStretch("column", 2, 1) if not d:execute() then return end local s1 = d:get("pattern") local s2 = d:get("replace") if not d:get("regex") then -- make strings non-magic s1 = string.gsub(s1, "(%W)", "%%%1") s2 = string.gsub(s2, "%%", "%%%%") end local t = { label = label, pno = model.pno, vno = model.vno, original = model:page():clone(), final = model:page():clone(), undo = _G.revertOriginal, redo = _G.revertFinal, } for i,obj,sel,layer in t.final:objects() do if sel and obj:type() == "text" then local text = obj:text() text = text:gsub(s1, s2) obj:setText(text) end end model:register(t) end ---------------------------------------------------------------------- ipe-7.2.13/src/ipelets/lua/Makefile0000644000175000017500000000121213561570220016705 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for Lua ipelets (only for install) # -------------------------------------------------------------------- IPESRCDIR = ../.. include ../../common.mak LUASCRIPTS = move.lua goodies.lua align.lua euclid.lua \ symbols.lua search-replace.lua selectby.lua all: install: $(INSTALL_DIR) $(INSTALL_ROOT)$(IPELETDIR) $(INSTALL_FILES) $(LUASCRIPTS) $(INSTALL_ROOT)$(IPELETDIR) ifdef IPEAPP app: $(INSTALL_DIR) $(RESOURCEDIR)/ipelets $(INSTALL_FILES) $(LUASCRIPTS) $(RESOURCEDIR)/ipelets endif # -------------------------------------------------------------------- ipe-7.2.13/src/ipelets/lua/move.lua0000644000175000017500000001052113561570220016721 0ustar otfriedotfried---------------------------------------------------------------------- -- move ipelet ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] label = "Move" revertOriginal = _G.revertOriginal about = [[ Moving objects in small steps, best used with shortcuts. Original Ipe 6 version by Gunter Schenck, this ipelet is now part of Ipe. ]] methods = { { label = "right 1pt", dx=1 }, { label = "left 1pt", dx=-1 }, { label = "up 1pt", dy=1 }, { label = "down 1pt", dy=-1 }, { label = "right-up 1pt", dx=1, dy=1 }, { label = "left-up 1pt", dx=-1, dy=1}, { label = "right-down 1pt", dx=1, dy=-1 }, { label = "left-down 1pt", dx=-1, dy=-1 }, { label = "right 0.1pt", dx=0.1 }, { label = "left 0.1pt", dx=-0.1 }, { label = "up 0.1pt", dy=0.1 }, { label = "down 0.1pt", dy=-0.1 }, { label = "right-up 0.1pt", dx=0.1, dy=0.1 }, { label = "left-up 0.1pt", dx=-0.1, dy=0.1 }, { label = "right-down 0.1pt", dx=0.1, dy=-0.1 }, { label = "left-down 0.1pt", dx=-0.1, dy=-0.1 }, { label = "right 10pt", dx=10 }, { label = "left 10pt", dx=-10 }, { label = "up 10pt", dy=10 }, { label = "down 10pt", dy=-10 }, { label = "right-up 10pt", dx=10, dy=10 }, { label = "left-up 10pt", dx=-10, dy=10 }, { label = "right-down 10pt", dx=10, dy=-10 }, { label = "left-down 10pt", dx=-10, dy=-10 }, } shortcuts.ipelet_1_move = "Ctrl+6" shortcuts.ipelet_2_move = "Ctrl+4" shortcuts.ipelet_3_move = "Ctrl+8" shortcuts.ipelet_4_move = "Ctrl+2" shortcuts.ipelet_5_move = "Ctrl+9" shortcuts.ipelet_6_move = "Ctrl+7" shortcuts.ipelet_7_move = "Ctrl+3" shortcuts.ipelet_8_move = "Ctrl+1" shortcuts.ipelet_9_move = "Alt+6" shortcuts.ipelet_10_move = "Alt+4" shortcuts.ipelet_11_move = "Alt+8" shortcuts.ipelet_12_move = "Alt+2" shortcuts.ipelet_13_move = "Alt+9" shortcuts.ipelet_14_move = "Alt+7" shortcuts.ipelet_15_move = "Alt+3" shortcuts.ipelet_16_move = "Alt+1" shortcuts.ipelet_17_move = "Ctrl+Alt+6" shortcuts.ipelet_18_move = "Ctrl+Alt+4" shortcuts.ipelet_19_move = "Ctrl+Alt+8" shortcuts.ipelet_20_move = "Ctrl+Alt+2" shortcuts.ipelet_21_move = "Ctrl+Alt+9" shortcuts.ipelet_22_move = "Ctrl+Alt+7" shortcuts.ipelet_23_move = "Ctrl+Alt+3" shortcuts.ipelet_24_move = "Ctrl+Alt+1" -- TODO: check if objects are pinned function run(model, num) local p = model:page() if not p:hasSelection() then model.ui:explain("no selection") return end local dx = methods[num].dx if not dx then dx = 0 end local dy = methods[num].dy if not dy then dy = 0 end local pin = {} for i, obj, sel, lay in p:objects() do if sel then pin[obj:get("pinned")] = true end end if pin.fixed or pin.horizontal and dx ~= 0 or pin.vertical and dy ~= 0 then model:warning("Cannot move objects", "Some object is pinned and cannot be moved") return end local t = { label = "move by (" .. dx .. ", " .. dy .. ")", pno = model.pno, vno = model.vno, selection = model:selection(), original = model:page():clone(), matrix = ipe.Matrix(1, 0, 0, 1, dx, dy), undo = revertOriginal, } t.redo = function (t, doc) local p = doc[t.pno] for _,i in ipairs(t.selection) do p:transform(i, t.matrix) end end model:register(t) end ---------------------------------------------------------------------- ipe-7.2.13/src/ipelets/lua/euclid.lua0000644000175000017500000001024513561570220017223 0ustar otfriedotfried---------------------------------------------------------------------- -- Euclid ipelet ---------------------------------------------------------------------- --[[ This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. --]] label = "Euclidean Geometry" about = [[ Create the incircle or the three excircles of a triangle. Original Ipe 6 version by Jari Lappalainen, this ipelet is now part of Ipe. ]] function incorrect(model) model:warning("Primary selection is not a triangle") end function collect_vertices(model) local p = model:page() local prim = p:primarySelection() if not prim then model.ui:explain("no selection") return end local obj = p[prim] if obj:type() ~= "path" then incorrect(model) return end local shape = obj:shape() if (#shape ~= 1 or shape[1].type ~= "curve" or #shape[1] ~= 2 or shape[1][1].type ~= "segment" or shape[1][2].type ~= "segment") then incorrect(model) return end local m = obj:matrix() local a = m * shape[1][1][1] local b = m * shape[1][1][2] local c = m * shape[1][2][2] return a, b, c end function angle_bisector(origin, dir1, dir2) assert(dir1:sqLen() > 0) assert(dir2:sqLen() > 0) local bisector = dir1:normalized() + dir2:normalized() if bisector:sqLen() == 0 then bisector = dir1:orthogonal() end return ipe.LineThrough(origin, origin + bisector) end function create_circle(model, center, radius) local shape = { type="ellipse"; ipe.Matrix(radius, 0, 0, radius, center.x, center.y) } return ipe.Path(model.attributes, { shape } ) end function incircle(model, a, b, c) local b1 = angle_bisector(a, b - a, c - a) local b2 = angle_bisector(b, c - b, a - b) local center = b1:intersects(b2) if (center) then local AB = ipe.LineThrough(a, b) local radius = AB:distance(center) return create_circle(model, center, radius) end end function excircle(model, a, b, c) local b1 = angle_bisector(a, b - a, c - a) local b2 = angle_bisector(b, c - b, a - b) local n1 = b1:normal() local n2 = b2:normal() local nl1 = ipe.LineThrough(a, a + n1) local nl2 = ipe.LineThrough(b, b + n2) local center = nl1:intersects(nl2) if center then local AB = ipe.LineThrough(a, b) local radius = AB:distance(center) return create_circle(model, center, radius) end end function create_incircle(model) local a, b, c = collect_vertices(model) if not a then return end local obj = incircle(model, a, b, c) if obj then model:creation("create incircle of triangle", obj) end end function create_excircles(model) local a, b, c = collect_vertices(model) if not a then return end local circles = {} local obj = excircle(model, a, b, c) if obj then circles[#circles + 1] = obj end obj = excircle(model, b, c, a) if obj then circles[#circles + 1] = obj end obj = excircle(model, c, a, b) if obj then circles[#circles + 1] = obj end local group = ipe.Group(circles) model:creation("create excircles of triangles", group) end methods = { { label="Incircle of triangle", run = create_incircle }, { label="Excircles of triangle", run = create_excircles }, } ---------------------------------------------------------------------- ipe-7.2.13/src/include/0000755000175000017500000000000013561570220014446 5ustar otfriedotfriedipe-7.2.13/src/include/ipeimage.h0000644000175000017500000000634013561570220016402 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // The image object // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEIMAGE_H #define IPEIMAGE_H #include "ipebitmap.h" #include "ipeobject.h" // -------------------------------------------------------------------- namespace ipe { class Image : public Object { public: explicit Image(const Rect &rect, Bitmap bitmap); explicit Image(const XmlAttributes &attr, String data); explicit Image(const XmlAttributes &attr, Bitmap bitmap); virtual Object *clone() const override; virtual Image *asImage() override; virtual Type type() const override; virtual void saveAsXml(Stream &stream, String layer) const override; virtual void draw(Painter &painter) const override; virtual void drawSimple(Painter &painter) const override; virtual void accept(Visitor &visitor) const override; virtual double distance(const Vector &v, const Matrix &m, double bound) const override; virtual void addToBBox(Rect &box, const Matrix &m, bool) const override; virtual void snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const override; inline Rect rect() const; inline Bitmap bitmap() const; virtual bool setAttribute(Property prop, Attribute value) override; virtual Attribute getAttribute(Property prop) const noexcept override; void setOpacity(Attribute opaq); //! Return opacity of the opject. inline Attribute opacity() const { return iOpacity; } private: void init(const XmlAttributes &attr); private: Rect iRect; Bitmap iBitmap; Attribute iOpacity; }; // -------------------------------------------------------------------- //! Return the rectangle occupied by the image on the paper. /*! The transformation matrix is applied to this, of course. */ inline Rect Image::rect() const { return iRect; } //! Return Bitmap of the image. inline Bitmap Image::bitmap() const { return iBitmap; } } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipexml.h0000644000175000017500000000604013561570220016115 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // XML parsing // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEXML_H #define IPEXML_H #include "ipebase.h" #include // -------------------------------------------------------------------- namespace ipe { class XmlAttributes { private: using Map = std::map; public: //! Iterator for (key, value) pairs. typedef Map::const_iterator const_iterator; //! Return const iterator for first attribute. const_iterator begin() const { return iMap.begin(); } //! Return const iterator for end of attributes. const_iterator end() const { return iMap.end(); } XmlAttributes(); void clear(); String operator[](String str) const; bool has(String str) const; bool has(String str, String &val) const; void add(String key, String val); //! Set that the tag contains the final /. inline void setSlash() { iSlash = true; } //! Return whether tag contains the final /. inline bool slash() const { return iSlash; } private: Map iMap; bool iSlash; }; class XmlParser { public: XmlParser(DataSource &source); virtual ~XmlParser(); int parsePosition() const { return iPos; } String parseToTag(); bool parseAttributes(XmlAttributes &attr, bool qm = false); bool parsePCDATA(String tag, String &pcdata); inline bool isTagChar(int ch) { return ('a' <= ch && ch <= 'z') || ('A' <= ch && ch <= 'Z') || ch == '-'; } inline void getChar() { iCh = iSource.getChar(); ++iPos; } inline bool eos() { return (iCh == EOF); } void skipWhitespace(); protected: String parseToTagX(); protected: DataSource &iSource; String iTopElement; int iCh; // current character int iPos; // position in input stream }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipegeo.h0000644000175000017500000004414513561570220016077 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Geometric primitives // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEGEO_H #define IPEGEO_H #include "ipebase.h" #include // -------------------------------------------------------------------- #define IpePi 3.1415926535897932385 #define IpeTwoPi 6.2831853071795862 #define IpeHalfPi 1.5707963267948966 namespace ipe { /*! \ingroup geo Maximum of two values. */ template inline T max(const T &lhs, const T &rhs) { return (lhs > rhs) ? lhs : rhs; } /*! \ingroup geo Minimum of two values. */ template inline T min(const T &lhs, const T &rhs) { return (lhs < rhs) ? lhs : rhs; } /*! \ingroup geo Absolute value. */ inline double abs(double val) { return (val > 0) ? val : -val; } // -------------------------------------------------------------------- class Angle { public: //! Construct uninitialized angle. inline explicit Angle() { /* nothing */ } //! Construct an angle (in radians). inline Angle(double alpha) : iAlpha(alpha) { } //! Construct an angle in degrees. inline static Angle Degrees(double alpha) { return Angle(alpha * IpePi / 180.0); } //! Return value (in radians). inline operator double() const { return iAlpha; } double degrees() const; Angle normalize(double lowlimit); bool liesBetween(Angle small, Angle large) const; private: double iAlpha; }; // -------------------------------------------------------------------- class Vector { public: //! Uninitialized vector. Vector() { /* no initialization */ } explicit Vector(Angle alpha); //! Construct a vector. explicit Vector(double x0, double y0) : x(x0), y(y0) { } //! Return square of Euclidean length inline double sqLen() const; double len() const; Angle angle() const; Vector normalized() const; Vector orthogonal() const; double factorize(Vector &unit) const; bool snap(const Vector &mouse, Vector &pos, double &bound) const; inline bool operator==(const Vector &rhs) const; inline bool operator!=(const Vector &rhs) const; inline void operator+=(const Vector &rhs); inline void operator-=(const Vector &rhs); inline void operator*=(double rhs); inline Vector operator+(const Vector &rhs) const; inline Vector operator-(const Vector &rhs) const; inline Vector operator*(double rhs) const; inline Vector operator-() const; static Vector ZERO; public: double x; //!< Coordinates are public. double y; //!< Coordinates are public. }; /*! \relates Vector */ Stream &operator<<(Stream &stream, const Vector &rhs); // -------------------------------------------------------------------- class Rect { public: //! Create empty rectangle. explicit Rect() : iMin(1,0), iMax(-1,0) { } //! Create rectangle containing just the point \a c. explicit Rect(const Vector &c) : iMin(c), iMax(c) { } explicit Rect(const Vector &c1, const Vector &c2); //! Make rectangle empty. void clear() { iMin.x = 1.0; iMax.x = -1.0; iMin.y = iMax.y = 0; } //! True if rectangle is empty. int isEmpty() const { return iMin.x > iMax.x; } //! Return left side. inline double left() const { return iMin.x; } //! Return right side. inline double right() const { return iMax.x; } //! Return bottom side. inline double bottom() const { return iMin.y; } //! Return top side. inline double top() const { return iMax.y; } //! Return top right corner. inline Vector topRight() const { return iMax; } //! Return bottom left corner. inline Vector bottomLeft() const { return iMin; } //! Return top left corner. inline Vector topLeft() const { return Vector(iMin.x, iMax.y); } //! Return bottom right corner. inline Vector bottomRight() const { return Vector(iMax.x, iMin.y); } //! Return center of rectangle. inline Vector center() const { return (iMin + iMax) * 0.5; } //! Return width. double width() const { return iMax.x - iMin.x; } //! Return height. double height() const { return iMax.y - iMin.y; } void addPoint(const Vector &rhs); void addRect(const Rect &rhs); void clipTo(const Rect &rhs); bool contains(const Vector &rhs) const; bool contains(const Rect &rhs) const; bool certainClearance(const Vector &v, double bound) const; bool intersects(const Rect &rhs) const; private: Vector iMin; //!< Lower-left corner. Vector iMax; //!< Top-right corner. }; /*! \relates Rect */ Stream &operator<<(Stream &stream, const Rect &rhs); // -------------------------------------------------------------------- class Line { public: //! Create default line (x-axis). explicit Line() : iP(0.0, 0.0), iDir(1.0, 0.0) { } explicit Line(const Vector &p, const Vector &dir); static Line through(const Vector &p, const Vector &q); double side(const Vector &p) const; inline Vector normal() const; double distance(const Vector &v) const; bool intersects(const Line &line, Vector &pt); Vector project(const Vector &v) const; inline Vector dir() const; public: //! Point on the line. Vector iP; private: Vector iDir; // unit vector }; // -------------------------------------------------------------------- class Segment { public: //! Create uninitialized segment Segment() { /* nothing */ } explicit Segment(const Vector &p, const Vector &q) : iP(p), iQ(q) { } inline Line line() const; double distance(const Vector &v, double bound) const; double distance(const Vector &v) const; bool project(const Vector &v, Vector &projection) const; bool intersects(const Segment &seg, Vector &pt) const; bool intersects(const Line &l, Vector &pt) const; bool snap(const Vector &mouse, Vector &pos, double &bound) const; public: //! First endpoint. Vector iP; //! Second endpoint. Vector iQ; }; // -------------------------------------------------------------------- class Bezier { public: //! Default constructor, uninitialized curve. inline Bezier() { /* nothing */ } inline Bezier(const Vector &p0, const Vector &p1, const Vector &p2, const Vector &p3); Vector point(double t) const; Vector tangent(double t) const; double distance(const Vector &v, double bound); bool straight(double precision) const; void subdivide(Bezier &l, Bezier &r) const; void approximate(double precision, std::vector &result) const; Rect bbox() const; bool snap(const Vector &v, double &t, Vector &pos, double &bound) const; static Bezier quadBezier(const Vector &p0, const Vector &p1, const Vector &p2); static void oldSpline(int n, const Vector *v, std::vector &result); static void spline(int n, const Vector *v, std::vector &result); static void closedSpline(int n, const Vector *v, std::vector &result); void intersect(const Line &l, std::vector &result) const; void intersect(const Segment &l, std::vector &result) const; void intersect(const Bezier &b, std::vector &result) const; public: Vector iV[4]; }; // -------------------------------------------------------------------- class Linear { public: Linear(); explicit Linear(Angle angle); inline explicit Linear(double m11, double m21, double m12, double m22); explicit Linear(String str); Linear inverse() const; inline bool isIdentity() const; inline Vector operator*(const Vector &rhs) const; inline bool operator==(const Linear &rhs) const; inline double determinant() const; public: double a[4]; }; /*! \relates Linear */ Stream &operator<<(Stream &stream, const Linear &rhs); // -------------------------------------------------------------------- class Matrix { public: Matrix(); inline Matrix(const Linear &linear); inline explicit Matrix(const Linear &linear, const Vector &t); inline explicit Matrix(double m11, double m21, double m12, double m22, double t1, double t2); inline explicit Matrix(const Vector &v); explicit Matrix(String str); Matrix inverse() const; inline Vector operator*(const Vector &rhs) const; inline Bezier operator*(const Bezier &rhs) const; inline Vector translation() const; inline Linear linear() const; inline double determinant() const; inline bool isIdentity() const; inline bool operator==(const Matrix &rhs) const; public: double a[6]; }; /*! \relates Matrix */ Stream &operator<<(Stream &stream, const Matrix &rhs); // -------------------------------------------------------------------- class Arc { public: inline Arc(); inline Arc(const Matrix &m, Angle alpha, Angle beta); inline Arc(const Matrix &m); Arc(const Matrix &m0, const Vector &begp, const Vector &endp); inline bool isEllipse() const; double distance(const Vector &v, double bound) const; double distance(const Vector &v, double bound, Vector &pos, Angle &angle) const; Rect bbox() const; inline Vector beginp() const; inline Vector endp() const; void intersect(const Line &l, std::vector &result) const; void intersect(const Segment &s, std::vector &result) const; void intersect(const Arc &a, std::vector &result) const; void intersect(const Bezier &b, std::vector &result) const; private: void subdivide(Arc &l, Arc &r) const; bool straight(const double precision) const; public: Matrix iM; Angle iAlpha; Angle iBeta; }; // -------------------------------------------------------------------- //! Return square of vector's length. inline double Vector::sqLen() const { return (x * x + y * y); } //! Equality. inline bool Vector::operator==(const Vector &rhs) const { return x == rhs.x && y == rhs.y; } //! Inequality. inline bool Vector::operator!=(const Vector &rhs) const { return x != rhs.x || y != rhs.y; } //! Vector-addition. inline void Vector::operator+=(const Vector &rhs) { x += rhs.x; y += rhs.y; } //! Vector-subtraction. inline void Vector::operator-=(const Vector &rhs) { x -= rhs.x; y -= rhs.y; } //! Multiply vector by scalar. inline void Vector::operator*=(double rhs) { x *= rhs; y *= rhs; } //! Vector-addition. inline Vector Vector::operator+(const Vector &rhs) const { Vector result = *this; result += rhs; return result; } //! Vector-subtraction. inline Vector Vector::operator-(const Vector &rhs) const { Vector result = *this; result -= rhs; return result; } //! Vector * scalar. inline Vector Vector::operator*(double rhs) const { Vector result = *this; result *= rhs; return result; } //! Scalar * vector. \relates Vector inline Vector operator*(double lhs, const Vector &rhs) { return Vector(lhs * rhs.x, lhs * rhs.y); } //! Dotproduct of two vectors. \relates Vector inline double dot(const Vector &lhs, const Vector &rhs) { return lhs.x * rhs.x + lhs.y * rhs.y; } //! Return a normal vector pointing to the left of the directed line. inline Vector Line::normal() const { return Vector(-iDir.y, iDir.x); } //! Return direction of line. inline Vector Line::dir() const { return iDir; } //! Return directed line supporting the segment. inline Line Segment::line() const { return Line(iP, (iQ - iP).normalized()); } //! Unary minus for Vector. inline Vector Vector::operator-() const { return -1 * *this; } //! Constructor with four control points. inline Bezier::Bezier(const Vector &p0, const Vector &p1, const Vector &p2, const Vector &p3) { iV[0] = p0; iV[1] = p1; iV[2] = p2; iV[3] = p3; } //! Transform Bezier spline. \relates Matrix inline Bezier Matrix::operator*(const Bezier &rhs) const { return Bezier(*this * rhs.iV[0], *this * rhs.iV[1], *this * rhs.iV[2], *this * rhs.iV[3]); }; // -------------------------------------------------------------------- //! Construct unit circle. inline Arc::Arc() : iAlpha(0.0), iBeta(IpeTwoPi) { // nothing } //! Construct with given parameters. inline Arc::Arc(const Matrix &m, Angle alpha, Angle beta) : iM(m), iAlpha(alpha), iBeta(beta) { // nothing } //! Construct an ellipse inline Arc::Arc(const Matrix &m) : iM(m), iAlpha(0.0), iBeta(IpeTwoPi) { // nothing } //! Is this an entire ellipse? inline bool Arc::isEllipse() const { return iAlpha == 0.0 && iBeta == IpeTwoPi; } //! Return begin point of arc. inline Vector Arc::beginp() const { return iM * Vector(Angle(iAlpha)); } //! Return end point of arc. inline Vector Arc::endp() const { return iM * Vector(Angle(iBeta)); } // -------------------------------------------------------------------- //! Create identity matrix. inline Linear::Linear() { a[0] = a[3] = 1.0; a[1] = a[2] = 0.0; } //! Create linear matrix with given coefficients. inline Linear::Linear(double m11, double m21, double m12, double m22) { a[0] = m11; a[1] = m21; a[2] = m12; a[3] = m22; } //! Linear matrix times vector. \relates Linear inline Vector Linear::operator*(const Vector &rhs) const { return Vector(a[0] * rhs.x + a[2] * rhs.y, a[1] * rhs.x + a[3] * rhs.y); }; //! Is this the identity matrix? inline bool Linear::isIdentity() const { return (a[0] == 1.0 && a[1] == 0.0 && a[2] == 0.0 && a[3] == 1.0); } //! Linear matrix multiplication. \relates Linear inline Linear operator*(const Linear &lhs, const Linear &rhs) { Linear m; m.a[0] = lhs.a[0] * rhs.a[0] + lhs.a[2] * rhs.a[1]; m.a[1] = lhs.a[1] * rhs.a[0] + lhs.a[3] * rhs.a[1]; m.a[2] = lhs.a[0] * rhs.a[2] + lhs.a[2] * rhs.a[3]; m.a[3] = lhs.a[1] * rhs.a[2] + lhs.a[3] * rhs.a[3]; return m; } //! Check for equality of two linear matrices. inline bool Linear::operator==(const Linear &rhs) const { return (a[0] == rhs.a[0] && a[1] == rhs.a[1] && a[2] == rhs.a[2] && a[3] == rhs.a[3]); } //! Return determinant of a linear matrix. inline double Linear::determinant() const { return (a[0] * a[3] - a[1] * a[2]); } // -------------------------------------------------------------------- //! Create matrix with given coefficients. inline Matrix::Matrix(double m11, double m21, double m12, double m22, double t1, double t2) { a[0] = m11; a[1] = m21; a[2] = m12; a[3] = m22; a[4] = t1; a[5] = t2; } //! Create linear matrix. inline Matrix::Matrix(const Linear &linear) { a[0] = linear.a[0]; a[1] = linear.a[1]; a[2] = linear.a[2]; a[3] = linear.a[3]; a[4] = a[5] = 0.0; } inline Matrix::Matrix(const Linear &linear, const Vector &t) { a[0] = linear.a[0]; a[1] = linear.a[1]; a[2] = linear.a[2]; a[3] = linear.a[3]; a[4] = t.x; a[5] = t.y; } //! Matrix times vector. \relates Matrix inline Vector Matrix::operator*(const Vector &rhs) const { return Vector(a[0] * rhs.x + a[2] * rhs.y + a[4], a[1] * rhs.x + a[3] * rhs.y + a[5]); }; //! Is this the identity matrix? inline bool Matrix::isIdentity() const { return (a[0] == 1.0 && a[1] == 0.0 && a[2] == 0.0 && a[3] == 1.0 && a[4] == 0.0 && a[5] == 0.0); } //! Create identity matrix. inline Matrix::Matrix() { a[0] = a[3] = 1.0; a[1] = a[2] = a[4] = a[5] = 0.0; } //! Matrix multiplication. \relates Matrix inline Matrix operator*(const Matrix &lhs, const Matrix &rhs) { Matrix m; m.a[0] = lhs.a[0] * rhs.a[0] + lhs.a[2] * rhs.a[1]; m.a[1] = lhs.a[1] * rhs.a[0] + lhs.a[3] * rhs.a[1]; m.a[2] = lhs.a[0] * rhs.a[2] + lhs.a[2] * rhs.a[3]; m.a[3] = lhs.a[1] * rhs.a[2] + lhs.a[3] * rhs.a[3]; m.a[4] = lhs.a[0] * rhs.a[4] + lhs.a[2] * rhs.a[5] + lhs.a[4]; m.a[5] = lhs.a[1] * rhs.a[4] + lhs.a[3] * rhs.a[5] + lhs.a[5]; return m; } //! Create translation matrix. inline Matrix::Matrix(const Vector &v) { a[0] = a[3] = 1.0; a[1] = a[2] = 0.0; a[4] = v.x; a[5] = v.y; } //! Return translation component. inline Vector Matrix::translation() const { return Vector(a[4], a[5]); } //! Return determinant of the matrix. inline double Matrix::determinant() const { return a[0]*a[3]-a[1]*a[2]; } //! Check for equality of two matrices. inline bool Matrix::operator==(const Matrix &rhs) const { return (a[0] == rhs.a[0] && a[1] == rhs.a[1] && a[2] == rhs.a[2] && a[3] == rhs.a[3] && a[4] == rhs.a[4] && a[5] == rhs.a[5]); } //! Return linear transformation component of this affine transformation. inline Linear Matrix::linear() const { return Linear(a[0], a[1], a[2], a[3]); } //! Transform arc. \relates Matrix // must be here because it uses Matrix multiplication above inline Arc operator*(const Matrix &lhs, const Arc &rhs) { return Arc(lhs * rhs.iM, rhs.iAlpha, rhs.iBeta); } } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipeiml.h0000644000175000017500000000426113561570220016101 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Parse an Ipe XML file // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEIML_H #define IPEIML_H #include "ipegroup.h" #include "ipepage.h" #include "ipedoc.h" #include "ipebitmap.h" // -------------------------------------------------------------------- namespace ipe { class ImlParser : public XmlParser { public: enum Errors { ESuccess = 0, EVersionTooOld, EVersionTooRecent, ESyntaxError }; explicit ImlParser(DataSource &source); int parseDocument(Document &doc); bool parsePage(Page &page); Object *parseObject(String tag, Page *page = nullptr, int *currentLayer = nullptr); StyleSheet *parseStyleSheet(); bool parseStyle(StyleSheet &sheet); // bool parseSelection(PageObjectSeq &seq); Page *parsePageSelection(); virtual Buffer pdfStream(int objNum); bool parseBitmap(); private: std::vector iBitmaps; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipepainter.h0000644000175000017500000001412113561570220016756 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Painter abstraction // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPAINTER_H #define IPEPAINTER_H #include #include "ipeattributes.h" #include "ipestyle.h" #include "ipebitmap.h" // -------------------------------------------------------------------- namespace ipe { class Painter { public: struct State { Color iStroke; Color iFill; Fixed iPen; String iDashStyle; TLineCap iLineCap; TLineJoin iLineJoin; TFillRule iFillRule; Color iSymStroke; Color iSymFill; Fixed iSymPen; Fixed iOpacity; Fixed iStrokeOpacity; Attribute iTiling; Attribute iGradient; }; public: Painter(const Cascade *style); virtual ~Painter(); void transform(const Matrix &m); void untransform(TTransformations trans); void translate(const Vector &v); void push(); void pop(); void pushMatrix(); void popMatrix(); void newPath(); void moveTo(const Vector &v); void lineTo(const Vector &v); void curveTo(const Vector &v1, const Vector &v2, const Vector &v3); inline void curveTo(const Bezier &bezier); void rect(const Rect &re); void drawEllipse(); void drawArc(const Arc &arc); void closePath(); void drawPath(TPathMode mode); void drawBitmap(Bitmap bitmap); void drawText(const Text *text); void drawSymbol(Attribute symbol); void addClipPath(); void setStroke(Attribute color); void setFill(Attribute color); void setPen(Attribute pen); void setDashStyle(Attribute dash); void setLineCap(TLineCap cap); void setLineJoin(TLineJoin join); void setFillRule(TFillRule rule); void setSymStroke(Attribute color); void setSymFill(Attribute color); void setSymPen(Attribute wid); void setOpacity(Attribute opaq); void setStrokeOpacity(Attribute opaq); void setTiling(Attribute til); void setGradient(Attribute grad); //! Return style sheet cascade. inline const Cascade *cascade() const { return iCascade; } //! Return current stroke color. inline Color stroke() const { return iState.back().iStroke; } //! Return current fill color. inline Color fill() const { return iState.back().iFill; } //! Return current transformation matrix. inline const Matrix &matrix() const { return iMatrix.back(); } //! Return current pen. inline Fixed pen() const {return iState.back().iPen; } //! Return current dash style (always absolute attribute). inline String dashStyle() const {return iState.back().iDashStyle; } void dashStyle(std::vector &dashes, double &offset) const; //! Return current line cap. inline TLineCap lineCap() const {return iState.back().iLineCap; } //! Return current line join. inline TLineJoin lineJoin() const {return iState.back().iLineJoin; } //! Return current fill rule. inline TFillRule fillRule() const {return iState.back().iFillRule; } //! Return current symbol stroke color. inline Color symStroke() const { return iState.back().iSymStroke; } //! Return current symbol fill color. inline Color symFill() const { return iState.back().iSymFill; } //! Return current symbol pen. inline Fixed symPen() const { return iState.back().iSymPen; } //! Return current opacity. inline Fixed opacity() const { return iState.back().iOpacity; } //! Return current stroke opacity. inline Fixed strokeOpacity() const { return iState.back().iStrokeOpacity; } //! Return current tiling. inline Attribute tiling() const { return iState.back().iTiling; } //! Return current gradient fill. inline Attribute gradient() const { return iState.back().iGradient; } //! Return full current graphics state. inline const State & state() const { return iState.back(); } void setState(const State &state); protected: virtual void doPush(); virtual void doPop(); virtual void doNewPath(); virtual void doMoveTo(const Vector &v); virtual void doLineTo(const Vector &v); virtual void doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3); virtual void doDrawArc(const Arc &arc); virtual void doClosePath(); virtual void doDrawPath(TPathMode mode); virtual void doDrawBitmap(Bitmap bitmap); virtual void doDrawText(const Text *text); virtual void doDrawSymbol(Attribute symbol); virtual void doAddClipPath(); void drawArcAsBezier(double alpha); protected: std::list iState; std::list iMatrix; const Cascade *iCascade; int iInPath; }; // -------------------------------------------------------------------- //! Overloaded function. /*! Assumes current position is \c bezier.iV[0] */ inline void Painter::curveTo(const Bezier &bezier) { curveTo(bezier.iV[1], bezier.iV[2], bezier.iV[3]); } } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipelatex.h0000644000175000017500000000531313561570220016434 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Latex source to PDF converter // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef PDFLATEX_P_H #define PDFLATEX_P_H #include #include "ipepage.h" #include "ipetext.h" #include "ipepdfparser.h" #include "iperesources.h" // -------------------------------------------------------------------- namespace ipe { class Cascade; class TextCollectingVisitor; class Latex { public: Latex(const Cascade *sheet, LatexType latexType); ~Latex(); int scanObject(const Object *obj); int scanPage(Page *page); void addPageNumber(int pno, int vno, int npages, int nviews); int createLatexSource(Stream &stream, String preamble); bool readPdf(DataSource &source); bool updateTextObjects(); PdfResources *takeResources(); private: bool getXForm(String key, const PdfDict *ipeInfo); void warn(String msg); private: struct SText { const Text *iText; Attribute iSize; }; typedef std::list TextList; typedef std::list XFormList; const Cascade *iCascade; bool iXetex; LatexType iLatexType; PdfFile iPdf; //! List of text objects scanned. Objects not owned. TextList iTextObjects; //! List of XForm objects read from PDF file. Objects owned! XFormList iXForms; //! The resources from the generated PDF file. PdfResources *iResources; friend class ipe::TextCollectingVisitor; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipefactory.h0000644000175000017500000000340413561570220016765 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // The Ipe object factory. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEFACTORY_H #define IPEFACTORY_H #include "ipebitmap.h" #include "ipeobject.h" // -------------------------------------------------------------------- namespace ipe { class ObjectFactory { public: static Object *createObject(String name, const XmlAttributes &attr, String data); static Object *createImage(String name, const XmlAttributes &attr, Bitmap bitmap); }; } // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipeshape.h0000644000175000017500000002033113561570220016414 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Drawable shapes // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPESHAPE_H #define IPESHAPE_H #include "ipegeo.h" // -------------------------------------------------------------------- namespace ipe { class Painter; class Ellipse; class ClosedSpline; class Curve; class CurveSegment { public: enum Type { EArc, ESegment, ESpline, EOldSpline }; //! Type of segment. inline Type type() const { return iType; } //! Number of control points. inline int countCP() const { return iNumCP; } //! Return control point. inline Vector cp(int i) const { return iCP[i]; } //! Return last control point. inline Vector last() const { return iCP[iNumCP - 1]; } //! Matrix (if Type() == EArc). inline Matrix matrix() const { return *iM; } Arc arc() const; void beziers(std::vector &bez) const; void draw(Painter &painter) const; void addToBBox(Rect &box, const Matrix &m, bool cp) const; double distance(const Vector &v, const Matrix &m, double bound) const; void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) const; void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; private: CurveSegment(Type type, int num, const Vector *cp, const Matrix *m = nullptr); private: Type iType; const Vector *iCP; int iNumCP; const Matrix *iM; friend class Curve; }; class SubPath { public: //! The subpath types. enum Type { ECurve, EEllipse, EClosedSpline }; virtual ~SubPath() = 0; //! Return type of this subpath. virtual Type type() const = 0; virtual bool closed() const; virtual const Ellipse *asEllipse() const; // virtual Ellipse *asEllipse(); virtual const ClosedSpline *asClosedSpline() const; // virtual ClosedSpline *asClosedSpline(); virtual const Curve *asCurve() const; // virtual Curve *asCurve(); //! Save subpath to XML stream. virtual void save(Stream &stream) const = 0; //! Draw subpath (does not call drawPath()). virtual void draw(Painter &painter) const = 0; //! Add subpath to box. virtual void addToBBox(Rect &box, const Matrix &m, bool cp) const = 0; //! Return distance from \a v to subpath transformed by \a m. virtual double distance(const Vector &v, const Matrix &m, double bound) const = 0; //! Snap to vertex. virtual void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) const = 0; //! Snap to boundary of subpath. virtual void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const = 0; }; class Ellipse : public SubPath { public: Ellipse(const Matrix &m); virtual Type type() const; virtual const Ellipse *asEllipse() const; //! Return matrix that transforms unit circle to the ellipse. inline Matrix matrix() const { return iM; } virtual void save(Stream &stream) const; virtual void draw(Painter &painter) const; virtual void addToBBox(Rect &box, const Matrix &m, bool cp) const; virtual double distance(const Vector &v, const Matrix &m, double bound) const; virtual void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) const; virtual void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; private: Matrix iM; }; class ClosedSpline : public SubPath { public: ClosedSpline(const std::vector &v); virtual Type type() const; virtual const ClosedSpline *asClosedSpline() const; void beziers(std::vector &bez) const; virtual void save(Stream &stream) const; virtual void draw(Painter &painter) const; virtual void addToBBox(Rect &box, const Matrix &m, bool cp) const; virtual double distance(const Vector &v, const Matrix &m, double bound) const; virtual void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) const; virtual void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; public: std::vector iCP; // control points }; class Curve : public SubPath { public: Curve(); virtual Type type() const; inline virtual bool closed() const { return iClosed; } virtual const Curve *asCurve() const; virtual void save(Stream &stream) const; virtual void draw(Painter &painter) const; virtual void addToBBox(Rect &box, const Matrix &m, bool cp) const; virtual double distance(const Vector &v, const Matrix &m, double bound) const; virtual void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) const; virtual void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; /*! \brief Return number of segments. This does not include the closing segment for a closed path. */ int countSegments() const { return iSeg.size(); } CurveSegment segment(int i) const; CurveSegment closingSegment(Vector u[2]) const; void appendSegment(const Vector &v0, const Vector &v1); void appendArc(const Matrix &m, const Vector &v0, const Vector &v1); void appendSpline(const std::vector &v) { appendSpline(v, CurveSegment::ESpline); } void appendOldSpline(const std::vector &v) { appendSpline(v, CurveSegment::EOldSpline); } void setClosed(bool closed); private: void appendSpline(const std::vector &v, CurveSegment::Type type); private: struct Seg { CurveSegment::Type iType; int iLastCP; int iMatrix; }; bool iClosed; std::vector iSeg; std::vector iCP; // control points std::vector iM; // for arcs }; class Shape { public: Shape(); explicit Shape(const Rect &rect); explicit Shape(const Segment &seg); explicit Shape(const Vector ¢er, double radius); explicit Shape(const Vector ¢er, double radius, double alpha0, double alpha1); ~Shape(); Shape(const Shape &rhs); Shape &operator=(const Shape &rhs); bool load(String data); void save(Stream &stream) const; void addToBBox(Rect &box, const Matrix &m, bool cp) const; double distance(const Vector &v, const Matrix &m, double bound) const; void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) const; void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; //! Return number of subpaths. inline int countSubPaths() const { return iImp->iSubPaths.size(); } //! Return subpath. inline const SubPath *subPath(int i) const { return iImp->iSubPaths[i]; } bool isSegment() const; void appendSubPath(SubPath *sp); void draw(Painter &painter) const; private: typedef std::vector SubPathSeq; struct Imp { ~Imp(); int iRefCount; SubPathSeq iSubPaths; }; Imp *iImp; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipelib.h0000644000175000017500000000335113561570220016065 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Includes everything to handle Ipe objects, pages, and documents // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPELIB_H #define IPELIB_H // -------------------------------------------------------------------- #include "ipebase.h" #include "ipegeo.h" #include "ipepath.h" #include "ipetext.h" #include "ipeimage.h" #include "ipereference.h" #include "ipegroup.h" #include "ipepage.h" #include "ipedoc.h" #include "ipelet.h" #include "ipesnap.h" // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipetext.h0000644000175000017500000001422513561570220016305 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // The text object. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPETEXT_H #define IPETEXT_H #include "ipeobject.h" // -------------------------------------------------------------------- namespace ipe { class Text : public Object { public: enum TextType { ELabel, EMinipage }; explicit Text(); explicit Text(const AllAttributes &attr, String data, const Vector &pos, TextType type, double width = 10.0); Text(const Text &rhs); ~Text(); explicit Text(const XmlAttributes &attr, String data); virtual Object *clone() const; virtual Text *asText(); virtual Type type() const; virtual void saveAsXml(Stream &stream, String layer) const; virtual void draw(Painter &painter) const; virtual void drawSimple(Painter &painter) const; virtual void accept(Visitor &visitor) const; virtual void addToBBox(Rect &box, const Matrix &m, bool) const; virtual double distance(const Vector &v, const Matrix &m, double bound) const; virtual void snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void checkStyle(const Cascade *sheet, AttributeSeq &seq) const; virtual bool setAttribute(Property prop, Attribute value); virtual Attribute getAttribute(Property prop) const noexcept; private: void quadrilateral(const Matrix &m, Vector v[4]) const; public: Vector align() const; TextType textType() const; inline Vector position() const; inline String text() const; void setStroke(Attribute stroke); void setOpacity(Attribute opaq); inline Attribute stroke() const; inline Attribute size() const; inline Attribute style() const; //! Return opacity of the opject. inline Attribute opacity() const { return iOpacity; } inline bool isMinipage() const; void setTextType(TextType type); inline THorizontalAlignment horizontalAlignment() const; inline TVerticalAlignment verticalAlignment() const; void setHorizontalAlignment(THorizontalAlignment align); void setVerticalAlignment(TVerticalAlignment align); static TVerticalAlignment makeVAlign(String str, TVerticalAlignment def); static THorizontalAlignment makeHAlign(String str, THorizontalAlignment def); static void saveAlignment(Stream &stream, THorizontalAlignment h, TVerticalAlignment v); inline double width() const; inline double height() const; inline double depth() const; inline double totalHeight() const; void setSize(Attribute size); void setStyle(Attribute style); void setWidth(double width); void setText(String text); struct XForm { int iRefCount; Rect iBBox; int iDepth; float iStretch; String iName; Vector iTranslation; }; void setXForm(XForm *xform) const; inline const XForm *getXForm() const; private: Vector iPos; String iText; Attribute iStroke; Attribute iSize; Attribute iStyle; Attribute iOpacity; mutable double iWidth; mutable double iHeight; mutable double iDepth; TextType iType; THorizontalAlignment iHorizontalAlignment; TVerticalAlignment iVerticalAlignment; mutable XForm *iXForm; // reference counted }; // -------------------------------------------------------------------- //! Return text position. inline Vector Text::position() const { return iPos; } //! Return text source. inline String Text::text() const { return iText; } //! Return stroke color. inline Attribute Text::stroke() const { return iStroke; } //! Return font size. inline Attribute Text::size() const { return iSize; } //! Return Latex style of text object. inline Attribute Text::style() const { return iStyle; } //! Return width of text object. inline double Text::width() const { return iWidth; } //! Return height of text object (from baseline to top). inline double Text::height() const { return iHeight; } //! Return depth of text object. inline double Text::depth() const { return iDepth; } //! Return height + depth of text object. inline double Text::totalHeight() const { return iHeight + iDepth; } //! Return true if text object is formatted as a minipage. /*! Equivalent to type being EMinipage. */ inline bool Text::isMinipage() const { return (iType == EMinipage); } //! Return horizontal alignment of text object. inline THorizontalAlignment Text::horizontalAlignment() const { return iHorizontalAlignment; } //! Return vertical alignment of text object. inline TVerticalAlignment Text::verticalAlignment() const { return iVerticalAlignment; } //! Return the PDF representation of this text object. /*! If Pdflatex has not been run yet, returns 0. */ inline const Text::XForm *Text::getXForm() const { return iXForm; } } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipebitmap.h0000644000175000017500000001307713561570220016601 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Bitmaps // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEBITMAP_H #define IPEBITMAP_H #include "ipebase.h" #include "ipegeo.h" #include "ipexml.h" // -------------------------------------------------------------------- namespace ipe { class Bitmap { public: enum Flags { ERGB = 0x01, // not grayscale EAlpha = 0x02, // has alpha channel EDCT = 0x04, // DCT encoded jpg image EInflate = 0x08, // data needs to be inflated ENative = 0x10, // data is already in native-endian ARGB32 }; Bitmap(); Bitmap(int width, int height, uint32_t flags, Buffer data); Bitmap(const XmlAttributes &attr, String data); Bitmap(const XmlAttributes &attr, Buffer data, Buffer smask); Bitmap(const Bitmap &rhs); ~Bitmap(); Bitmap &operator=(const Bitmap &rhs); void saveAsXml(Stream &stream, int id, int pdfObjNum = -1) const; inline bool isNull() const; bool equal(Bitmap rhs) const; inline int width() const; inline int height() const; inline bool isJpeg() const; inline bool isGray() const; inline bool hasAlpha() const; inline int colorKey() const; Buffer pixelData(); inline int objNum() const; inline void setObjNum(int objNum) const; std::pair embed() const; inline bool operator==(const Bitmap &rhs) const; inline bool operator!=(const Bitmap &rhs) const; inline bool operator<(const Bitmap &rhs) const; static const char *readJpegInfo(FILE *file, int &width, int &height, Vector &dotsPerInch, uint32_t &flags); static Bitmap readJpeg(const char *fname, Vector &dotsPerInch, const char * &errmsg); static Bitmap readPNG(const char *fname, Vector &dotsPerInch, const char * &errmsg); void savePixels(const char *fname); private: std::pair init(const XmlAttributes &attr); void computeChecksum(); void unpack(Buffer alphaChannel); void analyze(); private: struct Imp { int iRefCount; uint32_t iFlags; int iWidth; int iHeight; int iColorKey; Buffer iData; // native-endian ARGB32 or DCT encoded Buffer iPixelData; // native-endian ARGB32 pre-multiplied for Cairo bool iPixelsComputed; int iChecksum; mutable int iObjNum; // Object number (e.g. in PDF file) }; Imp *iImp; }; // -------------------------------------------------------------------- //! Is this a null bitmap? inline bool Bitmap::isNull() const { return (iImp == nullptr); } //! Return width of pixel array. inline int Bitmap::width() const { return iImp->iWidth; } //! Return height of pixel array. inline int Bitmap::height() const { return iImp->iHeight; } //! Is this bitmap a JPEG photo? inline bool Bitmap::isJpeg() const { return (iImp->iFlags & EDCT) != 0; } //! Is the bitmap grayscale? inline bool Bitmap::isGray() const { return (iImp->iFlags & ERGB) == 0; } //! Does the bitmap have transparency? /*! Bitmaps with color key will return false here. */ inline bool Bitmap::hasAlpha() const { return (iImp->iFlags & EAlpha) != 0; } //! Return the color key or -1 if none. inline int Bitmap::colorKey() const { return iImp->iColorKey; } //! Return object number of the bitmap. inline int Bitmap::objNum() const { return iImp->iObjNum; } //! Set object number of the bitmap. inline void Bitmap::setObjNum(int objNum) const { iImp->iObjNum = objNum; } //! Two bitmaps are equal if they share the same data. inline bool Bitmap::operator==(const Bitmap &rhs) const { return iImp == rhs.iImp; } //! Two bitmaps are equal if they share the same data. inline bool Bitmap::operator!=(const Bitmap &rhs) const { return iImp != rhs.iImp; } //! Less operator, to be able to sort bitmaps. /*! The checksum is used, when it is equal, the shared address. This guarantees that bitmaps that are == (share their implementation) are next to each other, and blocks of them are next to blocks that are identical in contents. */ inline bool Bitmap::operator<(const Bitmap &rhs) const { return (iImp->iChecksum < rhs.iImp->iChecksum || (iImp->iChecksum == rhs.iImp->iChecksum && iImp < rhs.iImp)); } } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipepswriter.h0000644000175000017500000000501513561570220017175 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Creating Postscript output // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPSWRITER_H #define IPEPSWRITER_H #include "ipebase.h" #include "ipepage.h" #include "ipedoc.h" #include "ipeimage.h" #include "ipepdfwriter.h" // -------------------------------------------------------------------- namespace ipe { struct Font; class PsPainter : public PdfPainter { public: PsPainter(const Cascade *style, Stream &stream); ~PsPainter(); protected: virtual void doNewPath(); virtual void doDrawPath(TPathMode mode); virtual void doDrawBitmap(Bitmap bitmap); virtual void doAddClipPath(); private: void strokePath(); void fillPath(bool eoFill, bool preservePath); private: int iImageNumber; }; // -------------------------------------------------------------------- class PsWriter { public: PsWriter(TellStream &stream, const Document *doc, bool noColor); ~PsWriter(); bool createHeader(int pno = 0, int vno = 0); void createPageView(int pno = 0, int vno = 0); void createXml(int compressLevel); void createTrailer(); private: void embedFont(const Font &font); private: TellStream &iStream; const Document *iDoc; bool iNoColor; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipepdfparser.h0000644000175000017500000001752713561570220017317 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // PDF file parser // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPDFPARSER_H #define IPEPDFPARSER_H #include "ipebase.h" #include "ipegeo.h" #include // -------------------------------------------------------------------- namespace ipe { using PdfRenumber = std::unordered_map; class PdfNull; class PdfBool; class PdfNumber; class PdfString; class PdfName; class PdfRef; class PdfArray; class PdfDict; class PdfFile; class PdfObj { public: virtual ~PdfObj() = 0; virtual const PdfNull *null() const noexcept; virtual const PdfBool *boolean() const noexcept; virtual const PdfNumber *number() const noexcept; virtual const PdfString *string() const noexcept; virtual const PdfName *name() const noexcept; virtual const PdfRef *ref() const noexcept; virtual const PdfArray *array() const noexcept; virtual const PdfDict *dict() const noexcept; virtual void write(Stream &stream, const PdfRenumber *renumber = nullptr, bool inflate = false) const noexcept = 0; String repr() const noexcept; }; class PdfNull : public PdfObj { public: explicit PdfNull() { /* nothing */ } virtual const PdfNull *null() const noexcept; virtual void write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept; }; class PdfBool : public PdfObj { public: explicit PdfBool(bool val) : iValue(val) { /* nothing */ } virtual const PdfBool *boolean() const noexcept; inline bool value() const noexcept { return iValue; } virtual void write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept; private: bool iValue; }; class PdfNumber : public PdfObj { public: explicit PdfNumber(double val) : iValue(val) { /* nothing */ } virtual const PdfNumber *number() const noexcept; virtual void write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept; inline double value() const noexcept { return iValue; } private: double iValue; }; class PdfString : public PdfObj { public: explicit PdfString(const String &val, bool binary=false) : iBinary(binary), iValue(val) { /* nothing */ } virtual const PdfString *string() const noexcept; virtual void write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept; inline String value() const noexcept { return iValue; } String decode() const noexcept; private: bool iBinary; String iValue; }; class PdfName : public PdfObj { public: explicit PdfName(const String &val) : iValue(val) { /* nothing */ } virtual const PdfName *name() const noexcept; virtual void write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept; inline String value() const noexcept { return iValue; } private: String iValue; }; class PdfRef : public PdfObj { public: explicit PdfRef(int val) : iValue(val) { /* nothing */ } virtual const PdfRef *ref() const noexcept; virtual void write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept; inline int value() const noexcept { return iValue; } private: int iValue; }; class PdfArray : public PdfObj { public: explicit PdfArray() { /* nothing */ } ~PdfArray(); virtual const PdfArray *array() const noexcept; virtual void write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept; void append(const PdfObj *); inline int count() const noexcept { return iObjects.size(); } const PdfObj *obj(int index, const PdfFile *file) const noexcept; private: std::vector iObjects; }; class PdfDict : public PdfObj { public: explicit PdfDict() { /* nothing */ } ~PdfDict(); virtual const PdfDict *dict() const noexcept; String dictRepr() const noexcept; void dictWrite(Stream &stream, const PdfRenumber *renumber, bool inflate, int length) const noexcept; virtual void write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept; void setStream(const Buffer &stream); void add(String key, const PdfObj *obj); const PdfObj *get(String key, const PdfFile *file) const noexcept; bool getNumber(String key, double &val, const PdfFile *file) const noexcept; bool getNumberArray(String key, const PdfFile *file, std::vector &vals) const noexcept; inline int count() const noexcept { return iItems.size(); } inline String key(int index) const noexcept { return iItems[index].iKey; } inline const PdfObj *value(int index) const noexcept { return iItems[index].iVal; } inline Buffer stream() const noexcept { return iStream; } bool deflated() const noexcept; Buffer inflate() const noexcept; private: struct Item { String iKey; const PdfObj *iVal; }; std::vector iItems; Buffer iStream; }; // -------------------------------------------------------------------- //! A PDF lexical token. struct PdfToken { //! The various types of tokens. enum TToken { EErr, EOp, EName, ENumber, EString, EStringBinary, ETrue, EFalse, ENull, EArrayBg, EArrayEnd, EDictBg, EDictEnd }; //! The type of this token. TToken iType; //! The string representing this token. String iString; }; class PdfParser { public: PdfParser(DataSource &source); inline void getChar() { iCh = iSource.getChar(); ++iPos; } inline bool eos() const noexcept { return (iCh == EOF); } inline PdfToken token() const noexcept { return iTok; } void getToken(); PdfObj *getObject(); PdfObj *getObjectDef(); PdfDict *getTrailer(); void skipXRef(); private: void skipWhiteSpace(); PdfArray *makeArray(); PdfDict *makeDict(); private: DataSource &iSource; int iPos; int iCh; PdfToken iTok; }; class PdfFile { public: bool parse(DataSource &source); bool parseObjectStream(const PdfDict *d); const PdfObj *object(int num) const noexcept; const PdfDict *catalog() const noexcept; const PdfDict *page(int pno = 0) const noexcept; std::unique_ptr take(int num); //! Return number of pages. int countPages() const { return static_cast(iPages.size()); } Rect mediaBox(const PdfDict *page) const; private: bool readPageTree(const PdfObj *ptn = nullptr); private: std::unordered_map> iObjects; std::unique_ptr iTrailer; std::vector iPages; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipepage.h0000644000175000017500000001657113561570220016243 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // A page of a document. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPAGE_H #define IPEPAGE_H #include "ipetext.h" // -------------------------------------------------------------------- namespace ipe { class StyleSheet; // -------------------------------------------------------------------- class Page { public: explicit Page(); static Page *basic(); void saveAsXml(Stream &stream) const; void saveAsIpePage(Stream &stream) const; void saveSelection(Stream &stream) const; //! Return number of layers. inline int countLayers() const noexcept { return iLayers.size(); } //! Return name of layer \a index. inline String layer(int index) const noexcept { return iLayers[index].iName; } //! Is layer \a i locked? inline bool isLocked(int i) const noexcept { return !!(iLayers[i].iFlags & ELocked); } //! Does layer \a i have active snapping? inline bool hasSnapping(int i) const noexcept { return !(iLayers[i].iFlags & ENoSnapping); } bool objSnapsInView(int objNo, int view) const noexcept; void setLocked(int i, bool flag); void setSnapping(int i, bool flag); void moveLayer(int index, int newIndex); int findLayer(String name) const; void addLayer(String name); void addLayer(); void removeLayer(String name); void renameLayer(String oldName, String newName); //! Return number of views. inline int countViews() const { return iViews.size(); } int countMarkedViews() const; //! Return effect of view. inline Attribute effect(int index) const { return iViews[index].iEffect; } void setEffect(int index, Attribute sym); //! Return active layer of view. inline String active(int index) const { return iViews[index].iActive; } //! Set active layer of view. void setActive(int index, String name); //! Return name of view. String viewName(int index) const noexcept { return iViews[index].iName; } //! Set name of view. void setViewName(int index, String name) noexcept { iViews[index].iName = name; } //! Return if view is marked. bool markedView(int index) const { return iViews[index].iMarked; } //! Set if view is marked. void setMarkedView(int index, bool marked); void insertView(int i, String active); void removeView(int i); void clearViews(); int findView(String viewNumberOrName) const; //! Is \a layer visible in \a view? inline bool visible(int view, int layer) const { return iLayers[layer].iVisible[view]; } //! Is object at index \a objno visible in \a view? inline bool objectVisible(int view, int objno) const { return iLayers[layerOf(objno)].iVisible[view]; } void setVisible(int view, String layer, bool vis); //! Return title of this page. String title() const; void setTitle(String title); String section(int level) const; void setSection(int level, bool useTitle, String name); //! Does this section title reflect the page title? bool sectionUsesTitle(int level) const { return iUseTitle[level]; } const Text *titleText() const; void applyTitleStyle(const Cascade *sheet); //! Return if page is marked for printing. bool marked() const { return iMarked; } void setMarked(bool marked); //! Return notes for this page. String notes() const { return iNotes; } void setNotes(String notes); //! Return number of objects on the page. inline int count() const { return iObjects.size(); } void objectsPerLayer(std::vector &objcounts) const; //! Return object at index \a i. inline Object *object(int i) { return iObjects[i].iObject; } //! Return object at index \a i (const version). inline const Object *object(int i) const { return iObjects[i].iObject; } //! Return selection status of object at index \a i. inline TSelect select(int i) const { return iObjects[i].iSelect; } //! Return layer of object at index \a i. inline int layerOf(int i) const { return iObjects[i].iLayer; } //! Set selection status of object at index \a i. inline void setSelect(int i, TSelect sel) { iObjects[i].iSelect = sel; } //! Set layer of object at index \a i. inline void setLayerOf(int i, int layer) { iObjects[i].iLayer = layer; } Rect pageBBox(const Cascade *sheet) const; Rect viewBBox(const Cascade *sheet, int view) const; Rect bbox(int i) const; void transform(int i, const Matrix &m); double distance(int i, const Vector &v, double bound) const; void snapVtx(int i, const Vector &mouse, Vector &pos, double &bound) const; void snapCtl(int i, const Vector &mouse, Vector &pos, double &bound) const; void snapBnd(int i, const Vector &mouse, Vector &pos, double &bound) const; void invalidateBBox(int i) const; void insert(int i, TSelect sel, int layer, Object *obj); void append(TSelect sel, int layer, Object *obj); void remove(int i); void replace(int i, Object *obj); bool setAttribute(int i, Property prop, Attribute value); int primarySelection() const; bool hasSelection() const; void deselectAll(); void ensurePrimarySelection(); private: enum { ELocked = 0x01, ENoSnapping = 0x02 }; struct SLayer { public: SLayer(String name); public: String iName; int iFlags; // Invariant: iVisible.size() == iViews.size() std::vector iVisible; }; typedef std::vector LayerSeq; struct SView { public: SView() { iEffect = Attribute::NORMAL(); } public: Attribute iEffect; String iActive; bool iMarked; String iName; }; typedef std::vector ViewSeq; struct SObject { SObject(); SObject(const SObject &rhs); ~SObject(); SObject &operator=(const SObject &rhs); TSelect iSelect; int iLayer; mutable Rect iBBox; Object *iObject; }; typedef std::vector ObjSeq; LayerSeq iLayers; ViewSeq iViews; String iTitle; Text iTitleObject; bool iUseTitle[2]; String iSection[2]; ObjSeq iObjects; String iNotes; bool iMarked; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipeobject.h0000644000175000017500000001222313561570220016563 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // The Ipe object type. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEOBJ_H #define IPEOBJ_H #include "ipeattributes.h" #include "ipexml.h" // -------------------------------------------------------------------- namespace ipe { class Visitor; class Painter; class Group; class Text; class Path; class Image; class Reference; class StyleSheet; class Cascade; // -------------------------------------------------------------------- class Object { public: enum Type { EGroup, EPath, EText, EImage, EReference }; virtual ~Object() = 0; //! Calls visitXXX method of the visitor. virtual void accept(Visitor &visitor) const = 0; //! Make a copy of this object (constant-time). virtual Object *clone() const = 0; virtual Group *asGroup(); virtual const Group *asGroup() const; virtual Text *asText(); virtual Path *asPath(); virtual Image *asImage(); virtual Reference *asReference(); virtual Type type() const = 0; virtual TPinned pinned() const; void setPinned(TPinned pin); //! Return allowed transformations of the object. inline TTransformations transformations() const { return iTransformations; } void setTransformations(TTransformations trans); void setMatrix(const Matrix &matrix); //! Return transformation matrix. inline const Matrix &matrix() const { return iMatrix; } virtual bool setAttribute(Property prop, Attribute value); virtual Attribute getAttribute(Property prop) const noexcept; //! Save the object in XML format. virtual void saveAsXml(Stream &stream, String layer) const = 0; //! Draw the object. virtual void draw(Painter &painter) const = 0; //! Draw simple version for selecting and transforming. virtual void drawSimple(Painter &painter) const = 0; /*! Return distance of transformed object to point \a v. If larger than \a bound, can just return \a bound. */ virtual double distance(const Vector &v, const Matrix &m, double bound) const = 0; //! Extend \a box to include the object transformed by \a m. /*! For objects in a page, don't call this directly. The Page caches the bounding box of each object, so it is far more efficient to call Page::bbox. Control points that lie outside the visual object are included if \a cp is true. If called with an empty box and \a cp == \c false, the result of this function is a tight bounding box for the object, with a little leeway in case the boundary is determined by a spline (it has to be approximated to perform this operation). */ virtual void addToBBox(Rect &box, const Matrix &m, bool cp) const = 0; virtual void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void checkStyle(const Cascade *sheet, AttributeSeq &seq) const; protected: explicit Object(); explicit Object(const AllAttributes &attr); Object(const Object &rhs); explicit Object(const XmlAttributes &attr); void saveAttributesAsXml(Stream &stream, String layer) const; static void checkSymbol(Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq); protected: Matrix iMatrix; TPinned iPinned : 8; TTransformations iTransformations : 8; }; // -------------------------------------------------------------------- class Visitor { public: virtual ~Visitor(); virtual void visitGroup(const Group *obj); virtual void visitPath(const Path *obj); virtual void visitText(const Text *obj); virtual void visitImage(const Image *obj); virtual void visitReference(const Reference *obj); }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipepdfwriter.h0000644000175000017500000001207313561570220017326 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Creating PDF output // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPDFWRITER_H #define IPEPDFWRITER_H #include "ipebase.h" #include "ipepage.h" #include "ipedoc.h" #include "ipeimage.h" #include #include #include // -------------------------------------------------------------------- namespace ipe { class PdfResources; class PdfDict; class PdfPainter : public Painter { public: PdfPainter(const Cascade *style, Stream &stream); virtual ~PdfPainter() { } static void drawColor(Stream &stream, Color color, const char *gray, const char *rgb); protected: virtual void doPush(); virtual void doPop(); virtual void doNewPath(); virtual void doMoveTo(const Vector &v); virtual void doLineTo(const Vector &v); virtual void doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3); virtual void doClosePath(); virtual void doDrawPath(TPathMode mode); virtual void doDrawBitmap(Bitmap bitmap); virtual void doDrawText(const Text *text); virtual void doAddClipPath(); virtual void doDrawSymbol(Attribute symbol); protected: void drawAttributes(); void drawOpacity(bool withStroke); protected: Stream &iStream; // iActiveState records the attribute settings that have been // recorded in the PDF output, to avoid repeating them // over and over again. std::list iActiveState; }; // -------------------------------------------------------------------- class PdfWriter { public: PdfWriter(TellStream &stream, const Document *doc, const PdfResources *resources, uint32_t flags, int fromPage, int toPage, int compression); ~PdfWriter(); void createPages(); void createPageView(int page, int view); void createBookmarks(); void createNamedDests(); void createXmlStream(String xmldata, bool preCompressed); void createTrailer(); private: int startObject(int objnum = -1); int pageObjectNumber(int page, int view); void createStream(const char *data, int size, bool preCompressed); void writeString(String text); void embedBitmap(Bitmap bitmap); void paintView(Stream &stream, int pno, int view); void embedBitmaps(const BitmapFinder &bm); void createResources(const BitmapFinder &bm); void embedResources(); void embedResource(String kind); void embedIpeXForm(const PdfDict *d); void embedXFormResource(const PdfDict *d); void embedLatexResource(int num, String kind); bool hasResource(String kind) const noexcept; private: TellStream &iStream; const Document *iDoc; const PdfResources *iResources; //! SaveFlag's uint32_t iSaveFlags; //! Obj id of XML stream. int iXmlStreamNum; //! Obj id of outline dictionary. int iBookmarks; //! Obj id of named destinations. int iDests; //! Compression level (0..9). int iCompressLevel; //! Obj id of GState with opacity definitions. int iExtGState; //! Obj id of dictionary with pattern definitions. int iPatternNum; // Export only those pages int iFromPage; int iToPage; // Map object number in resources to object number in output. std::unordered_map iResourceNumber; std::vector iBitmaps; //! Next unused PDF object number. int iObjNum; //! Object numbers of gradients, indexed by attribute name std::map iGradients; //! Object numbers of symbols, indexed by attribute name std::map iSymbols; struct PON { int page; int view; int objNum; }; //! List of pages, expressed as Pdf object numbers. std::vector iPageObjectNumbers; //! List of file locations, in object number order (starting with 0). std::map iXref; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipebase.h0000644000175000017500000002762113561570220016237 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Base header file --- must be included by all Ipe components. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEBASE_H #define IPEBASE_H #include #include #include #include #ifdef IPESTRICT #include "ipeosx.h" #endif // -------------------------------------------------------------------- #undef assert #define assert(e) ((e) ? (void)0 : ipeAssertionFailed(__FILE__, __LINE__, #e)) extern void ipeAssertionFailed(const char *, int, const char *); extern void ipeDebug(const char *msg, ...) noexcept; // -------------------------------------------------------------------- namespace ipe { template inline int size(const std::vector &v) { return static_cast(v.size()); } constexpr double IPE_PI = 3.14159265358979323846; #ifdef WIN32 constexpr char IPESEP = '\\'; #else constexpr char IPESEP = '/'; #endif //! Ipelib version. /*! \ingroup base */ const int IPELIB_VERSION = 70213; //! Oldest readable file format version. /*! \ingroup base */ const int OLDEST_FILE_FORMAT = 70000; //! Current file format version. /*! \ingroup base */ const int FILE_FORMAT = 70212; enum class LatexType { Default, Pdftex, Xetex, Luatex }; // -------------------------------------------------------------------- class Stream; class String { public: String() noexcept; String(const char *str) noexcept; String(const char *str, int len) noexcept; String(const String &rhs) noexcept; String(const String &rhs, int index, int len) noexcept; String &operator=(const String &rhs) noexcept; #ifdef WIN32 String(const wchar_t *data); std::wstring w() const noexcept; #endif ~String() noexcept; static String withData(char *data, int len = 0) noexcept; //! Return character at index i. inline char operator[](int i) const noexcept { return iImp->iData[i]; } //! Is the string empty? inline bool empty() const noexcept { return (size() == 0); } //! Return read-only pointer to the data. const char *data() const noexcept { return iImp->iData; } //! Return number of bytes in the string. inline int size() const noexcept { return iImp->iSize; } //! Operator syntax for append. inline void operator+=(const String &rhs) noexcept { append(rhs); } //! Operator syntax for append. inline void operator+=(const char *rhs) noexcept { append(rhs); } //! Operator syntax for append. void operator+=(char ch) noexcept { append(ch); } //! Create substring. inline String substr(int i, int len = -1) const noexcept { return String(*this, i, len); } //! Create substring at the left. inline String left(int i) const noexcept { return String(*this, 0, i); } String right(int i) const noexcept; //! Operator !=. inline bool operator!=(const String &rhs) const noexcept { return !(*this == rhs); } //! Operator !=. inline bool operator!=(const char *rhs) const noexcept { return !(*this == rhs); } int find(char ch) const noexcept; int rfind(char ch) const noexcept; int find(const char *rhs) const noexcept; void erase() noexcept; void append(const String &rhs) noexcept; void append(const char *rhs) noexcept; void append(char ch) noexcept; bool hasPrefix(const char *rhs) const noexcept; bool operator==(const String &rhs) const noexcept; bool operator==(const char *rhs) const noexcept; bool operator<(const String &rhs) const noexcept; String operator+(const String &rhs) const noexcept; int unicode(int &index) const noexcept; String getLine(int &index) const noexcept; const char *z() const noexcept; private: void detach(int n) noexcept; private: struct Imp { int iRefCount; int iSize; int iCapacity; char *iData; }; static Imp *theEmptyString; static Imp *emptyString() noexcept; Imp *iImp; }; // -------------------------------------------------------------------- class Fixed { public: explicit Fixed(int val) : iValue(val * 1000) { /* nothing */ } explicit Fixed() { /* nothing */ } inline static Fixed fromInternal(int32_t val); static Fixed fromDouble(double val); inline int toInt() const { return iValue / 1000; } inline double toDouble() const { return iValue / 1000.0; } inline int internal() const { return iValue; } Fixed mult(int a, int b) const; inline bool operator==(const Fixed &rhs) const; inline bool operator!=(const Fixed &rhs) const; inline bool operator<(const Fixed &rhs) const; inline bool isInteger() const; private: int32_t iValue; friend Stream &operator<<(Stream &stream, const Fixed &f); }; // -------------------------------------------------------------------- class Lex { public: explicit Lex(String str); String token(); String nextToken(); int getInt(); int getHexByte(); Fixed getFixed(); unsigned long int getHexNumber(); double getDouble(); //! Extract next character (not skipping anything). inline char getChar() { return iString[iPos++]; } void skipWhitespace(); //! Operator syntax for getInt(). inline Lex &operator>>(int &i) { i = getInt(); return *this; } //! Operator syntax for getDouble(). inline Lex &operator>>(double &d) { d = getDouble(); return *this; } //! Operator syntax for getFixed(). inline Lex &operator>>(Fixed &d) { d = getFixed(); return *this; } //! Mark the current position. inline void mark() { iMark = iPos; } //! Reset reader to the marked position. inline void fromMark() { iPos = iMark; } //! Return true if at end of string (not even whitespace left). inline bool eos() const { return (iPos == iString.size()); } private: String iString; int iPos; int iMark; }; // -------------------------------------------------------------------- class Buffer { public: explicit Buffer() = default; explicit Buffer(int size); explicit Buffer(const char *data, int size); //! Character access. inline char &operator[](int index) noexcept { return (*iData)[index]; } //! Character access (const version). inline const char &operator[](int index) const noexcept { return (*iData)[index]; } //! Return size of buffer; inline int size() const noexcept { return iData ? static_cast((*iData).size()) : 0; } //! Return pointer to buffer data. inline char *data() noexcept { return iData ? iData->data() : nullptr; } //! Return pointer to buffer data (const version). inline const char *data() const noexcept { return iData ? iData->data() : nullptr; } private: std::shared_ptr> iData; }; // -------------------------------------------------------------------- class Stream { public: //! Virtual destructor. virtual ~Stream(); //! Output character. virtual void putChar(char ch) = 0; //! Close the stream. No more writing allowed! virtual void close(); //! Output string. virtual void putString(String s); //! Output C string. virtual void putCString(const char *s); //! Output raw character data. virtual void putRaw(const char *data, int size); //! Output character. inline Stream &operator<<(char ch) { putChar(ch); return *this; } //! Output string. inline Stream &operator<<(const String &s) { putString(s); return *this; } //! Output C string. inline Stream &operator<<(const char *s) { putCString(s); return *this; } Stream &operator<<(int i); Stream &operator<<(double d); void putHexByte(char b); void putXmlString(String s); }; /*! \class ipe::TellStream \ingroup base \brief Adds position feedback to IpeStream. */ class TellStream : public Stream { public: virtual long tell() const = 0; }; class StringStream : public TellStream { public: StringStream(String &string); virtual void putChar(char ch); virtual void putString(String s); virtual void putCString(const char *s); virtual void putRaw(const char *data, int size); virtual long tell() const; private: String &iString; }; class FileStream : public TellStream { public: FileStream(std::FILE *file); virtual void putChar(char ch); virtual void putString(String s); virtual void putCString(const char *s); virtual void putRaw(const char *data, int size); virtual long tell() const; private: std::FILE *iFile; }; // -------------------------------------------------------------------- class DataSource { public: virtual ~DataSource() = 0; //! Get one more character, or EOF. virtual int getChar() = 0; }; class FileSource : public DataSource { public: FileSource(std::FILE *file); virtual int getChar(); private: std::FILE *iFile; }; class BufferSource : public DataSource { public: BufferSource(const Buffer &buffer); virtual int getChar(); void setPosition(int pos); private: const Buffer &iBuffer; int iPos; }; // -------------------------------------------------------------------- class Platform { public: using DebugHandler = void (*)(const char *); #ifdef IPEBUNDLE static String ipeDir(const char *suffix, const char *fname = nullptr); #endif #ifdef WIN32 static FILE *fopen(const char *fname, const char *mode); static int mkdir(const char *dname); #else inline static FILE *fopen(const char *fname, const char *mode) { return ::fopen(fname, mode); } #endif static String ipeDrive(); static int libVersion(); static void initLib(int version); static void setDebug(bool debug); static String currentDirectory(); static String latexDirectory(); static String latexPath(); static bool fileExists(String fname); static bool listDirectory(String path, std::vector &files); static String realPath(String fname); static String readFile(String fname); static int runLatex(String dir, LatexType engine, String docname) noexcept; static double toDouble(String s); static int toNumber(String s, int &iValue, double &dValue); }; // -------------------------------------------------------------------- inline bool Fixed::operator==(const Fixed &rhs) const { return iValue == rhs.iValue; } inline bool Fixed::operator!=(const Fixed &rhs) const { return iValue != rhs.iValue; } inline bool Fixed::operator<(const Fixed &rhs) const { return iValue < rhs.iValue; } inline bool Fixed::isInteger() const { return (iValue % 1000) == 0; } inline Fixed Fixed::fromInternal(int val) { Fixed f; f.iValue = val; return f; } } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipestyle.h0000644000175000017500000001533413561570220016463 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Ipe style sheet // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPESTYLE_H #define IPESTYLE_H #include "ipeattributes.h" #include "ipetext.h" // -------------------------------------------------------------------- namespace ipe { struct Symbol { Symbol(); Symbol(Object *object); Symbol(const Symbol &rhs); Symbol &operator=(const Symbol &rhs); ~Symbol(); bool iXForm; TTransformations iTransformations; Object *iObject; std::vector iSnap; }; class StyleSheet { public: //! Style of the title on a page. struct TitleStyle { //! Has a TitleStyle been defined in the style sheet? bool iDefined; //! Position on the page (in Ipe coordinate system) Vector iPos; //! Text size. Attribute iSize; //! Text color. Attribute iColor; //! Horizontal alignment. THorizontalAlignment iHorizontalAlignment; //! Vertical alignment. TVerticalAlignment iVerticalAlignment; }; //! How to show page numbers on the paper. struct PageNumberStyle { //! Has a PageNumberStyle been defined in the style sheet? bool iDefined; //! Position on the page Vector iPos; //! Text size. Attribute iSize; //! Text color. Attribute iColor; //! Text alignment, horizontal. THorizontalAlignment iHorizontalAlignment; //! Text alignment, vertical. TVerticalAlignment iVerticalAlignment; //! Template text. String iText; }; StyleSheet(); static StyleSheet *standard(); void addSymbol(Attribute name, const Symbol &symbol); const Symbol *findSymbol(Attribute sym) const; void addGradient(Attribute name, const Gradient &s); const Gradient *findGradient(Attribute sym) const; void addTiling(Attribute name, const Tiling &s); const Tiling *findTiling(Attribute sym) const; void addEffect(Attribute name, const Effect &e); const Effect *findEffect(Attribute sym) const; void add(Kind kind, Attribute name, Attribute value); bool has(Kind kind, Attribute sym) const; Attribute find(Kind, Attribute sym) const; void remove(Kind kind, Attribute sym); void saveAsXml(Stream &stream, bool saveBitmaps = false) const; void allNames(Kind kind, AttributeSeq &seq) const; //! Return whether this is the standard style sheet built into Ipe. inline bool isStandard() const { return iStandard; } //! Return Latex preamble. inline String preamble() const { return iPreamble; } //! Set LaTeX preamble. inline void setPreamble(const String &str) { iPreamble = str; } const Layout *layout() const; void setLayout(const Layout &margins); const TextPadding *textPadding() const; void setTextPadding(const TextPadding &pad); const TitleStyle *titleStyle() const; void setTitleStyle(const TitleStyle &ts); const PageNumberStyle *pageNumberStyle() const; void setPageNumberStyle(const PageNumberStyle &pns); void setLineCap(TLineCap s); void setLineJoin(TLineJoin s); void setFillRule(TFillRule s); //! Return line cap. TLineCap lineCap() const { return iLineCap; } //! Return line join. TLineJoin lineJoin() const { return iLineJoin; } //! Return path fill rule. TFillRule fillRule() const { return iFillRule; } //! Return name of style sheet. inline String name() const { return iName; } //! Set name of style sheet. inline void setName(const String &name) { iName = name; } private: typedef std::map SymbolMap; typedef std::map GradientMap; typedef std::map TilingMap; typedef std::map EffectMap; typedef std::map Map; bool iStandard; String iName; SymbolMap iSymbols; GradientMap iGradients; TilingMap iTilings; EffectMap iEffects; Map iMap; String iPreamble; Layout iLayout; TextPadding iTextPadding; TitleStyle iTitleStyle; PageNumberStyle iPageNumberStyle; TLineJoin iLineJoin; TLineCap iLineCap; TFillRule iFillRule; }; class Cascade { public: Cascade(); Cascade(const Cascade &rhs); Cascade &operator=(const Cascade &rhs); ~Cascade(); //! Return number of style sheets. inline int count() const { return iSheets.size(); } //! Return StyleSheet at \a index. inline StyleSheet *sheet(int index) { return iSheets[index]; } //! Return StyleSheet at \a index. inline const StyleSheet *sheet(int index) const { return iSheets[index]; } void insert(int index, StyleSheet *sheet); void remove(int index); void saveAsXml(Stream &stream) const; bool has(Kind kind, Attribute sym) const; Attribute find(Kind, Attribute sym) const; const Symbol *findSymbol(Attribute sym) const; const Gradient *findGradient(Attribute sym) const; const Tiling *findTiling(Attribute sym) const; const Effect *findEffect(Attribute sym) const; const Layout *findLayout() const; const TextPadding *findTextPadding() const; const StyleSheet::TitleStyle *findTitleStyle() const; const StyleSheet::PageNumberStyle *findPageNumberStyle() const; String findPreamble() const; TLineCap lineCap() const; TLineJoin lineJoin() const; TFillRule fillRule() const; void allNames(Kind kind, AttributeSeq &seq) const; int findDefinition(Kind kind, Attribute sym) const; private: std::vector iSheets; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipeattributes.h0000644000175000017500000003672013561570220017513 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Ipe object attributes // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEATTRIBUTES_H #define IPEATTRIBUTES_H #include "ipebase.h" #include "ipegeo.h" // -------------------------------------------------------------------- namespace ipe { /*! \brief The different kinds of attributes. \ingroup attr The same symbolic attribute (say "normal") has a different value in the StyleSheet depending on the Kind of attribute. The main use for Kind is as an argument to StyleSheet::find. ESymbol, EGradient, ETiling, and EEffect have their own lookup methods in the StyleSheet. The values are still useful as an argument to allNames(), has(), and findDefinition(). */ enum Kind { EPen = 0, ESymbolSize, EArrowSize, EColor, EDashStyle, ETextSize, ETextStretch, ETextStyle, ELabelStyle, EGridSize, EAngleSize, EOpacity, ETiling, ESymbol, EGradient, EEffect }; /*! \ingroup attr */ extern const char * const kind_names[]; /*! \brief A Property identifies an attribute that an object can have. \ingroup attr The Property identifies a unique attribute of an object, while different Property values can be of the same ipe::Kind. For instance, both EPropStrokeColor and EPropFillColor identify an Attribute of Kind EColor. */ enum Property { EPropPen = 0, EPropSymbolSize, EPropFArrow, EPropRArrow, EPropFArrowSize, EPropRArrowSize, EPropFArrowShape, EPropRArrowShape, EPropStrokeColor, EPropFillColor, EPropMarkShape, EPropPathMode, EPropDashStyle, EPropTextSize, EPropTextStyle, EPropLabelStyle, EPropOpacity, EPropStrokeOpacity, EPropTiling, EPropGradient, EPropHorizontalAlignment, EPropVerticalAlignment, EPropLineJoin, EPropLineCap, EPropFillRule, EPropPinned, EPropTransformations, EPropTransformableText, EPropMinipage, EPropWidth, EPropDecoration, }; /*! \ingroup attr */ extern const char * const property_names[]; //! Path mode (stroked, filled, or both). /*! \ingroup attr */ enum TPathMode { EStrokedOnly, EStrokedAndFilled, EFilledOnly }; //! Horizontal alignment. /*! \ingroup attr */ enum THorizontalAlignment { EAlignLeft, EAlignRight, EAlignHCenter }; //! Vertical alignment. /*! \ingroup attr */ enum TVerticalAlignment { EAlignBottom, EAlignBaseline, EAlignTop, EAlignVCenter }; //! Line join style. /*! \ingroup attr */ /*! The EDefaultJoin means to use the setting from the style sheet. */ enum TLineJoin { EDefaultJoin, EMiterJoin, ERoundJoin, EBevelJoin }; //! Line cap style. /*! \ingroup attr */ /*! The EDefaultCap means to use the setting from the style sheet. */ enum TLineCap { EDefaultCap, EButtCap, ERoundCap, ESquareCap }; //! Fill rule. /*! \ingroup attr */ /*! The EDefaultRule means to use the setting from the style sheet. */ enum TFillRule { EDefaultRule, EWindRule, EEvenOddRule }; //! Pinning status of objects. /*! \ingroup attr */ enum TPinned { ENoPin = 0x00, EHorizontalPin = 0x01, EVerticalPin = 0x02, EFixedPin = 0x03 }; //! Transformations that are permitted for an object. /*! \ingroup attr */ enum TTransformations { ETransformationsTranslations, ETransformationsRigidMotions, ETransformationsAffine }; //! Selection status of an object on the page /*! \ingroup attr */ enum TSelect { ENotSelected = 0, EPrimarySelected, ESecondarySelected }; // -------------------------------------------------------------------- class Color { public: //! Default constructor. Color() { /* nothing */ } explicit Color(String str); explicit Color(int r, int g, int b); void save(Stream &stream) const; void saveRGB(Stream &stream) const; bool isGray() const; bool operator==(const Color &rhs) const; inline bool operator!=(const Color &rhs) const {return !(*this == rhs); } public: Fixed iRed, iGreen, iBlue; }; //! A tiling pattern. /*! \ingroup attr */ struct Tiling { Angle iAngle; double iStep; double iWidth; }; //! A gradient pattern. /*! \ingroup attr */ struct Gradient { //! A color stop. struct Stop { //! Offset between 0.0 and 1.0. double offset; //! The color at this offset. Color color; }; //! There are two types of gradients, along an axis or between two circles. enum TType { EAxial = 2, ERadial = 3 }; //! The type of gradient: axial or radial. TType iType; //! The coordinates of the axis endpoints, or the two circle centers. Vector iV[2]; //! The radii of the two circles (not used for axial gradients). double iRadius[2]; //! Whether to extend the gradient beyond the endpoints. bool iExtend; //! Gradient transformation. Matrix iMatrix; //! The color stops. std::vector iStops; }; //! Layout of a Page. /*! \ingroup attr */ struct Layout { //! Create null layout. Layout() { iPaperSize.x = -1.0; } //! Is this an undefined (null) layout? bool isNull() const { return iPaperSize.x < 0.0; } //! Return rectangle describing the paper. Rect paper() const { return Rect(-iOrigin, iPaperSize - iOrigin); } //! Dimensions of the media. Vector iPaperSize; //! Origin of the Ipe coordinate system relative to the paper. Vector iOrigin; //! Size of the frame (the drawing area). Vector iFrameSize; //! Paragraph skip (between textboxes). double iParagraphSkip; //! Crop paper to drawing. bool iCrop; }; //! Padding for text bounding box. /*! \ingroup attr */ struct TextPadding { public: double iLeft, iRight, iTop, iBottom; }; struct Effect { public: //! The various fancy effects that Acrobat Reader will show. enum TEffect { ENormal, ESplitHI, ESplitHO, ESplitVI, ESplitVO, EBlindsH, EBlindsV, EBoxI, EBoxO, EWipeLR, EWipeBT, EWipeRL, EWipeTB, EDissolve, EGlitterLR, EGlitterTB, EGlitterD }; Effect(); void pageDictionary(Stream &stream) const; public: TEffect iEffect; int iTransitionTime; int iDuration; }; // -------------------------------------------------------------------- class Repository { public: static Repository *get(); static void cleanup(); String toString(int index) const; int toIndex(String str); // int getIndex(String str) const; private: Repository(); static Repository *singleton; std::vector iStrings; }; // -------------------------------------------------------------------- class Attribute { enum { EMiniMask = 0xc0000000, ETypeMask = 0xe0000000, ESymbolic = 0x80000000, EFixed = 0x40000000, EAbsolute = 0xc0000000, EEnum = 0xe0000000, EFixedMask = 0x3fffffff, ENameMask = 0x1fffffff, EWhiteValue = ((1000 << 20) + (1000 << 10) + 1000), EOneValue = EFixed|1000 }; public: //! Default constructor. explicit Attribute() { /* nothing */ } explicit Attribute(bool symbolic, String name); explicit Attribute(Fixed value); explicit Attribute(Color color); static Attribute Boolean(bool flag) { return Attribute(EEnum + flag); } explicit Attribute(THorizontalAlignment align) { iName = EEnum + align +2; } explicit Attribute(TVerticalAlignment align) { iName = EEnum + align + 5; } explicit Attribute(TLineJoin join) { iName = EEnum + join + 9; } explicit Attribute(TLineCap cap) { iName = EEnum + cap + 13; } explicit Attribute(TFillRule rule) { iName = EEnum + rule + 17; } explicit Attribute(TPinned pin) { iName = EEnum + pin + 20; } explicit Attribute(TTransformations trans) { iName = EEnum + trans + 24; } explicit Attribute(TPathMode pm) { iName = EEnum + pm + 27; } //! Is it symbolic? inline bool isSymbolic() const { return ((iName & ETypeMask) == ESymbolic); } //! Is it an absolute string value? inline bool isString() const { return ((iName & ETypeMask) == EAbsolute); } //! Is it a color? inline bool isColor() const { return ((iName & EMiniMask) == 0); } //! Is it a number? inline bool isNumber() const { return ((iName & EMiniMask) == EFixed); } //! Is it an enumeration? inline bool isEnum() const { return ((iName & ETypeMask) == EEnum); } //! Is it a boolean? inline bool isBoolean() const { return (isEnum() && 0 <= index() && index() <= 1); } //! Is it the symbolic name "normal"? inline bool isNormal() const { return (iName == ESymbolic); } //! Return index into Repository. inline int index() const { return iName & ENameMask; } int internal() const { return iName; } String string() const; Fixed number() const; Color color() const; bool boolean() const { return bool(index()); } THorizontalAlignment horizontalAlignment() const { return THorizontalAlignment(index() - 2); } TVerticalAlignment verticalAlignment() const { return TVerticalAlignment(index() - 5); } TLineJoin lineJoin() const {return TLineJoin(index() - 9); } TLineCap lineCap() const { return TLineCap(index() - 13); } TFillRule fillRule() const { return TFillRule(index() - 17); } TPinned pinned() const { return TPinned(index() - 20); } TTransformations transformations() const { return TTransformations(index() - 24); } TPathMode pathMode() const { return TPathMode(index() - 27); } //! Are two values equal (only compares index!) inline bool operator==(const Attribute &rhs) const { return iName == rhs.iName; } //! Are two values different (only compares index!) inline bool operator!=(const Attribute &rhs) const { return iName != rhs.iName; } //! Create absolute black color. inline static Attribute BLACK() { return Attribute(0); } //! Create absolute white color. inline static Attribute WHITE() { return Attribute(EWhiteValue); } //! Create absolute number one. inline static Attribute ONE() { return Attribute(EOneValue); } //! Create symbolic attribute "normal". inline static Attribute NORMAL() { return Attribute(ESymbolic); } //! Create symbolic attribute "undefined" inline static Attribute UNDEFINED() { return Attribute(ESymbolic + 1); } //! Create symbolic attribute "Background" inline static Attribute BACKGROUND() { return Attribute(ESymbolic + 2); } //! Create symbolic attribute "sym-stroke" inline static Attribute SYM_STROKE() { return Attribute(ESymbolic + 3); } //! Create symbolic attribute "sym-fill" inline static Attribute SYM_FILL() { return Attribute(ESymbolic + 4); } //! Create symbolic attribute "sym-pen" inline static Attribute SYM_PEN() { return Attribute(ESymbolic + 5); } //! Create symbolic attribute "arrow/normal(spx)" inline static Attribute ARROW_NORMAL() { return Attribute(ESymbolic + 6); } //! Create symbolic attribute "opaque" inline static Attribute OPAQUE() { return Attribute(ESymbolic + 7); } //! Create symbolic attribute "arrow/arc(spx)" inline static Attribute ARROW_ARC() { return Attribute(ESymbolic + 8); } //! Create symbolic attribute "arrow/farc(spx)" inline static Attribute ARROW_FARC() { return Attribute(ESymbolic + 9); } //! Create symbolic attribute "arrow/ptarc(spx)" inline static Attribute ARROW_PTARC() { return Attribute(ESymbolic + 10); } //! Create symbolic attribute "arrow/fptarc(spx)" inline static Attribute ARROW_FPTARC() { return Attribute(ESymbolic + 11); } //! Is it one of the symbolic attributes "arrow/*arc(spc)"? inline bool isArcArrow() const { return ESymbolic + 8 <= iName && iName <= ESymbolic + 11; } static Attribute makeColor(String str, Attribute deflt); static Attribute makeScalar(String str, Attribute deflt); static Attribute makeDashStyle(String str); static Attribute makeTextSize(String str); static Attribute normal(Kind kind); private: inline Attribute(int index) : iName(index) { /* nothing */ } explicit Attribute(bool symbolic, int index); private: std::uint32_t iName; friend class StyleSheet; }; /*! \var AttributeSeq \ingroup attr \brief A sequence of attribute values. */ typedef std::vector AttributeSeq; // -------------------------------------------------------------------- class AllAttributes { public: AllAttributes(); TPathMode iPathMode; //!< Should we stroke and/or fill? Attribute iStroke; //!< Stroke color. Attribute iFill; //!< Fill color. Attribute iDashStyle; //!< Dash style. Attribute iPen; //!< Pen (that is, line width). bool iFArrow; //!< Arrow forward? bool iRArrow; //!< Reverse arrow? Attribute iFArrowShape; //!< Shape of forward arrows Attribute iRArrowShape; //!< Shape of reverse arrows Attribute iFArrowSize; //!< Forward arrow size. Attribute iRArrowSize; //!< Reverse arrow size. Attribute iSymbolSize; //!< Symbol size. Attribute iTextSize; //!< Text size. //! Horizontal alignment of label objects. THorizontalAlignment iHorizontalAlignment; //! Vertical alignment of label objects. TVerticalAlignment iVerticalAlignment; Attribute iTextStyle; //!< Text style for minipages. Attribute iLabelStyle; //!< Text style for labels. TPinned iPinned; //!< Pinned status. //! Should newly created text be transformable? /*! If this is false, newly created text will only allow translations. Otherwise, the value of iTranslations is used (as for other objects). */ bool iTransformableText; //! Allowed transformations. TTransformations iTransformations; TLineJoin iLineJoin; //!< Line join style. TLineCap iLineCap; //!< Line cap style. TFillRule iFillRule; //!< Shape fill rule. Attribute iOpacity; //!< Opacity. Attribute iStrokeOpacity; //!< Stroke opacity. Attribute iTiling; //!< Tiling pattern. Attribute iGradient; //!< Gradient pattern. Attribute iMarkShape; //!< Shape of Mark to create. }; // -------------------------------------------------------------------- /*! \relates Color */ inline Stream &operator<<(Stream &stream, const Color &attr) { attr.save(stream); return stream; } } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipetoolbase.h0000644000175000017500000000377313561570220017137 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::Tool // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPETOOLBASE_H #define IPETOOLBASE_H #include "ipegeo.h" #include "ipepainter.h" namespace ipe { class CanvasBase; class Tool { public: virtual ~Tool(); public: virtual void draw(Painter &painter) const = 0; // left: 1, right:2, middle: 4, // xbutton1: 8, xbutton2: 0x10 // plus 0x80 for double-click virtual void mouseButton(int button, bool press); virtual void mouseMove(); virtual bool key(String text, int modifiers); virtual void snapVtx(const Vector &mouse, Vector &pos, double &bound, bool cp) const; protected: Tool(CanvasBase *canvas); protected: CanvasBase *iCanvas; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipeosx.h0000644000175000017500000000620313561570220016127 0ustar otfriedotfried// -*- objc -*- // Check OS X API levels /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEOSX_H #define IPEOSX_H // -------------------------------------------------------------------- #ifdef __OBJC__ #import #undef CF_AVAILABLE #define IPE_AVAILABLE(_mac) IPE_AVAILABLE_##_mac #define CF_AVAILABLE(_mac, _ios) IPE_AVAILABLE(_mac) #define IPE_AVAILABLE_10_0 __attribute__((availability(macosx,introduced=10_0))) #define IPE_AVAILABLE_10_1 __attribute__((availability(macosx,introduced=10_1))) #define IPE_AVAILABLE_10_2 __attribute__((availability(macosx,introduced=10_2))) #define IPE_AVAILABLE_10_3 __attribute__((availability(macosx,introduced=10_3))) #define IPE_AVAILABLE_10_4 __attribute__((availability(macosx,introduced=10_4))) #define IPE_AVAILABLE_10_5 __attribute__((availability(macosx,introduced=10_5))) #define IPE_AVAILABLE_10_6 __attribute__((availability(macosx,introduced=10_6))) #define IPE_AVAILABLE_10_7 __attribute__((availability(macosx,introduced=10_7))) #define IPE_AVAILABLE_10_8 __attribute__((availability(macosx,introduced=10_8))) #define IPE_AVAILABLE_10_9 __attribute__((availability(macosx,introduced=10_9))) #define IPE_AVAILABLE_10_10 __attribute__((availability(macosx,introduced=10_10))) #define IPE_AVAILABLE_10_10_3 __attribute__((weak_import,deprecated("API in 10.10.3"))) #define IPE_AVAILABLE_10_11 __attribute__((weak_import,deprecated("API in 10.11"))) #define IPE_AVAILABLE_10_12 __attribute__((weak_import,deprecated("API in 10.12"))) #define IPE_AVAILABLE_10_12_1 __attribute__((weak_import,deprecated("API in 10.12.1"))) #define IPE_AVAILABLE_10_12_2 __attribute__((weak_import,deprecated("API in 10.12.2"))) #define IPE_AVAILABLE_10_13 __attribute__((weak_import,deprecated("API in 10.13"))) #define IPE_AVAILABLE_10_13_4 __attribute__((weak_import,deprecated("API in 10.13.4"))) #define IPE_AVAILABLE_10_14 __attribute__((weak_import,deprecated("API in 10.14"))) #define IPE_AVAILABLE_NA __attribute__((weak_import,deprecated("API not available"))) #endif // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/iperesources.h0000644000175000017500000000670213561570220017334 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // The PDF resources created by Pdflatex/Xelatex // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPERESOURCES_H #define IPERESOURCES_H #include "ipebase.h" #include "ipegeo.h" #include "ipepdfparser.h" #include "ipetext.h" // -------------------------------------------------------------------- namespace ipe { class PdfResourceBase { public: PdfResourceBase(); virtual ~PdfResourceBase(); virtual const PdfObj *object(int num) const noexcept = 0; const PdfObj *getDeep(const PdfDict *d, String key) const noexcept; const PdfDict *getDict(const PdfDict *d, String key) const noexcept; const PdfDict *resourcesOfKind(String kind) const noexcept; const PdfDict *findResource(String kind, String name) const noexcept; const PdfDict *findResource(const PdfDict *xf, String kind, String name) const noexcept; protected: std::unique_ptr iPageResources; }; class PdfFileResources : public PdfResourceBase { public: PdfFileResources(const PdfFile *file); ~PdfFileResources() = default; virtual const PdfObj *object(int num) const noexcept; private: const PdfFile *iPdf; }; class PdfResources : public PdfResourceBase { public: struct SPageNumber { int page; int view; std::unique_ptr text; }; public: PdfResources(); virtual ~PdfResources() = default; bool collect(const PdfDict *resources, PdfFile *file); virtual const PdfObj *object(int num) const noexcept; virtual const PdfDict *baseResources() const noexcept; void addPageNumber(SPageNumber &pn) noexcept; const Text *pageNumber(int page, int view) const noexcept; inline const std::vector &embedSequence() const noexcept { return iEmbedSequence; } void show() const noexcept; private: void add(int num, PdfFile *file); void addIndirect(const PdfObj *q, PdfFile *file); bool addToResource(PdfDict *d, String key, const PdfObj *el, PdfFile *file); private: std::unordered_map> iObjects; std::vector iEmbedSequence; //! Page number objects. std::vector iPageNumbers; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipereference.h0000644000175000017500000000731413561570220017260 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // The reference object // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEREF_H #define IPEREF_H #include "ipeobject.h" // -------------------------------------------------------------------- namespace ipe { class Cascade; class Reference : public Object { public: enum { EHasStroke = 0x001, EHasFill = 0x002, EHasPen = 0x004, EHasSize = 0x008, EIsMark = 0x010, EIsArrow = 0x020 }; explicit Reference(const AllAttributes &attr, Attribute name, Vector pos); explicit Reference(const XmlAttributes &attr, String data); virtual Object *clone() const; virtual Reference *asReference(); virtual Type type() const; virtual void accept(Visitor &visitor) const; virtual void saveAsXml(Stream &stream, String layer) const; virtual void draw(Painter &painter) const; virtual void drawSimple(Painter &painter) const; virtual void addToBBox(Rect &box, const Matrix &m, bool cp) const; virtual double distance(const Vector &v, const Matrix &m, double bound) const; virtual void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void checkStyle(const Cascade *sheet, AttributeSeq &seq) const; void setName(Attribute name); //! Return symbolic name. inline Attribute name() const { return iName; } void setStroke(Attribute color); //! Return stroke color. inline Attribute stroke() const { return iStroke; } void setFill(Attribute color); //! Return fill color. inline Attribute fill() const { return iFill; } //! Return pen. inline Attribute pen() const { return iPen; } void setPen(Attribute pen); void setSize(Attribute size); //! Return symbol size. inline Attribute size() const { return iSize; } //! Return position of symbol on page. inline Vector position() const { return iPos; } virtual bool setAttribute(Property prop, Attribute value); virtual Attribute getAttribute(Property prop) const noexcept; inline uint32_t flags() const { return iFlags; } static uint32_t flagsFromName(String name); private: Attribute iName; Vector iPos; Attribute iSize; Attribute iStroke; Attribute iFill; Attribute iPen; uint32_t iFlags; mutable std::vector iSnap; // caching info from the symbol itself }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipepath.h0000644000175000017500000001534313561570220016257 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // The path object. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPATH_H #define IPEPATH_H #include "ipeobject.h" #include "ipeshape.h" // -------------------------------------------------------------------- namespace ipe { class Path : public Object { public: explicit Path(const AllAttributes &attr, const Shape &shape, bool withArrows = false); static Path *create(const XmlAttributes &attr, String data); virtual Object *clone() const; virtual Path *asPath(); virtual Type type() const; void setPathMode(TPathMode pm); void setStroke(Attribute stroke); void setFill(Attribute fill); void setPen(Attribute pen); void setDashStyle(Attribute dash); void setLineCap(TLineCap s); void setLineJoin(TLineJoin s); void setFillRule(TFillRule s); void setOpacity(Attribute opaq); void setStrokeOpacity(Attribute opaq); void setTiling(Attribute a); void setGradient(Attribute a); //! Return opacity of the opject. inline Attribute opacity() const { return iOpacity; } //! Return stroke opacity of the opject. inline Attribute strokeOpacity() const { return iStrokeOpacity; } //! Return tiling pattern. inline Attribute tiling() const { return iTiling; } //! Return gradient fill. inline Attribute gradient() const { return iGradient; } inline TPathMode pathMode() const; inline Attribute stroke() const; inline Attribute fill() const; inline Attribute pen() const; inline Attribute dashStyle() const; inline TLineCap lineCap() const; inline TLineJoin lineJoin() const; inline TFillRule fillRule() const; virtual void saveAsXml(Stream &stream, String layer) const; virtual void draw(Painter &painter) const; virtual void drawSimple(Painter &painter) const; virtual void accept(Visitor &visitor) const; virtual void addToBBox(Rect &box, const Matrix &m, bool cp) const; virtual double distance(const Vector &v, const Matrix &m, double bound) const; virtual void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void checkStyle(const Cascade *sheet, AttributeSeq &seq) const; virtual bool setAttribute(Property prop, Attribute value); virtual Attribute getAttribute(Property prop) const noexcept; inline bool arrow() const; inline bool rArrow() const; inline Attribute arrowShape() const; inline Attribute rArrowShape() const; inline Attribute arrowSize() const; inline Attribute rArrowSize() const; void setArrow(bool arrow, Attribute shape, Attribute size); void setRarrow(bool arrow, Attribute shape, Attribute size); static void drawArrow(Painter &painter, Vector pos, Angle alpha, Attribute shape, Attribute size, double radius); //! Return shape of the path object. const Shape &shape() const { return iShape; } void setShape(const Shape &shape); private: explicit Path(const XmlAttributes &attr); void init(const AllAttributes &attr, bool withArrows); void makeArrowData(); private: TPathMode iPathMode : 2; int iHasFArrow : 1; int iHasRArrow : 1; TLineJoin iLineJoin : 3; TLineCap iLineCap : 3; TFillRule iFillRule : 2; int iFArrowOk : 1; int iRArrowOk : 1; int iFArrowArc : 1; int iRArrowArc : 1; Attribute iStroke; Attribute iFill; Attribute iDashStyle; Attribute iPen; Attribute iOpacity; Attribute iStrokeOpacity; Attribute iTiling; Attribute iGradient; Attribute iFArrowShape; Attribute iRArrowShape; Attribute iFArrowSize; Attribute iRArrowSize; Vector iFArrowPos; Angle iFArrowDir; Vector iRArrowPos; Angle iRArrowDir; Shape iShape; }; // -------------------------------------------------------------------- //! Is the object stroked and filled? inline TPathMode Path::pathMode() const { return iPathMode; } //! Return stroke color. inline Attribute Path::stroke() const { return iStroke; } //! Return object fill color. inline Attribute Path::fill() const { return iFill; } //! Return object pen. inline Attribute Path::pen() const { return iPen; } //! Return object line style. inline Attribute Path::dashStyle() const { return iDashStyle; } //! Return line cap style. inline TLineCap Path::lineCap() const { return TLineCap(iLineCap); } //! Return line join style. inline TLineJoin Path::lineJoin() const { return TLineJoin(iLineJoin); } //! Return fill rule. inline TFillRule Path::fillRule() const { return TFillRule(iFillRule); } //! Does object have an arrow? inline bool Path::arrow() const { return iHasFArrow; } //! Does object have a reverse arrow? inline bool Path::rArrow() const { return iHasRArrow; } //! Return shape of arrow. inline Attribute Path::arrowShape() const { return iFArrowShape; } //! Return shape of reverse arrow. inline Attribute Path::rArrowShape() const { return iRArrowShape; } //! Return size of arrow. inline Attribute Path::arrowSize() const { return iFArrowSize; } //! Return size of reverse arrow. inline Attribute Path::rArrowSize() const { return iRArrowSize; } } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipeutils.h0000644000175000017500000001022513561570220016455 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Various utility classes // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEUTILS_H #define IPEUTILS_H #include "ipebitmap.h" #include "ipepainter.h" // -------------------------------------------------------------------- namespace ipe { class Page; class BitmapFinder : public Visitor { public: void scanPage(const Page *page); virtual void visitGroup(const Group *obj); virtual void visitImage(const Image *obj); public: std::vector iBitmaps; }; class BBoxPainter : public Painter { public: BBoxPainter(const Cascade *style); Rect bbox() const { return iBBox; } protected: virtual void doPush(); virtual void doPop(); virtual void doNewPath(); virtual void doMoveTo(const Vector &v); virtual void doLineTo(const Vector &v); virtual void doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3); virtual void doDrawPath(TPathMode mode); virtual void doDrawBitmap(Bitmap bitmap); virtual void doDrawText(const Text *text); virtual void doAddClipPath(); private: Rect iBBox; Vector iV; Rect iPathBox; std::list iClipBox; }; class A85Stream : public Stream { public: A85Stream(Stream &stream); virtual void putChar(char ch); virtual void close(); private: Stream &iStream; uint8_t iCh[4]; int iN; int iCol; }; class Base64Stream : public Stream { public: Base64Stream(Stream &stream); virtual void putChar(char ch); virtual void close(); private: Stream &iStream; uint8_t iCh[3]; int iN; int iCol; }; class DeflateStream : public Stream { public: DeflateStream(Stream &stream, int level); virtual ~DeflateStream(); virtual void putChar(char ch); virtual void close(); static Buffer deflate(const char *data, int size, int &deflatedSize, int compressLevel); private: struct Private; Stream &iStream; Private *iPriv; int iN; Buffer iIn; Buffer iOut; }; class A85Source : public DataSource { public: A85Source(DataSource &source); //! Get one more character, or EOF. virtual int getChar(); private: DataSource &iSource; bool iEof; int iN; int iIndex; uint8_t iBuf[4]; }; class Base64Source : public DataSource { public: Base64Source(DataSource &source); //! Get one more character, or EOF. virtual int getChar(); private: DataSource &iSource; bool iEof; int iIndex; int iBufLen; uint8_t iBuf[3]; }; class InflateSource : public DataSource { public: InflateSource(DataSource &source); virtual ~InflateSource(); //! Get one more character, or EOF. virtual int getChar(); private: void fillBuffer(); private: struct Private; DataSource &iSource; Private *iPriv; char *iP; Buffer iIn; Buffer iOut; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipesnap.h0000644000175000017500000000563613561570220016270 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Snapping. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPESNAP_H #define IPESNAP_H #include "ipegeo.h" #include "ipetoolbase.h" // -------------------------------------------------------------------- namespace ipe { class Page; class Snap { public: //! The different snap modes as bitmasks. enum TSnapModes { ESnapNone = 0, ESnapVtx = 1, ESnapCtl = 2, ESnapBd = 4, ESnapInt = 8, ESnapGrid = 0x10, ESnapAngle = 0x20, ESnapAuto = 0x40 }; int iSnap; //!< Activated snapping modes (TSnapModes) bool iGridVisible; //!< Is the grid visible? int iGridSize; //!< Snap grid spacing. double iAngleSize; //!< Angle for angular snapping. int iSnapDistance; //!< Snap distance (in pixels). bool iWithAxes; //!< Show coordinate system? Vector iOrigin; //!< Origin of coordinate system Angle iDir; //!< Direction of x-axis void intersectionSnap(const Vector &pos, Vector &fifi, const Page *page, int view, double &snapDist) const noexcept; bool snapAngularIntersection(Vector &pos, const Line &l, const Page *page, int view, double snapDist) const noexcept; TSnapModes simpleSnap(Vector &pos, const Page *page, int view, double snapDist, Tool *tool = nullptr) const noexcept; TSnapModes snap(Vector &pos, const Page *page, int view, double snapDist, Tool *tool = nullptr, Vector *autoOrg = nullptr) const noexcept; Line getLine(const Vector &mouse, const Vector &base) const noexcept; bool setEdge(const Vector &pos, const Page *page, int view) noexcept; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipelet.h0000644000175000017500000000667013561570220016112 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // Ipelets // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPELET_H #define IPELET_H #include "ipebase.h" #include "ipeattributes.h" #include "ipesnap.h" #ifdef __MINGW32__ #define IPELET_DECLARE extern "C" __declspec(dllexport) #else #define IPELET_DECLARE extern "C" #endif // -------------------------------------------------------------------- namespace ipe { class Page; class Document; class IpeletHelper { public: enum { EOkButton, EOkCancelButtons, EYesNoCancelButtons, EDiscardCancelButtons, ESaveDiscardCancelButtons }; virtual ~IpeletHelper() = 0; //! Show a message in the status bar. virtual void message(const char *msg) = 0; //! Pop up a modal message box. /*! The \a details can be null. Choose one of EOkButton, EOkCancelButtons, EYesNoCancelButtons, EDiscardCancelButtons, ESaveDiscardCancelButtons for \a buttons. Returns 1 for Ok or Yes, 0 for No, -1 for Cancel. */ virtual int messageBox(const char *text, const char *details, int buttons) = 0; /*! Pop up a modal dialog asking the user to enter a string. Returns true if the user didn't cancel the dialog. */ virtual bool getString(const char *prompt, String &str) = 0; /*! Retrieve a parameter value from a table in the Lua wrapper code. If no table has been passed, or the key is not in the table, or its value is not a string or a number, then an empty string is returned. */ virtual String getParameter(const char *key) = 0; }; //! Information provided to an ipelet when it is run. struct IpeletData { Page *iPage; const Document *iDoc; int iPageNo, iView, iLayer; AllAttributes iAttributes; Snap iSnap; }; // -------------------------------------------------------------------- class Ipelet { public: virtual ~Ipelet() = 0; //! Return the version of Ipelib the Ipelet was linked against. virtual int ipelibVersion() const = 0; //! Run a function from the Ipelet. /*! Return true if page was changed and undo registration is necessary. */ virtual bool run(int function, IpeletData *data, IpeletHelper *helper) = 0; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipedoc.h0000644000175000017500000001276213561570220016072 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // The Ipe document. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEDOC_H #define IPEDOC_H #include "ipeobject.h" #include "ipepage.h" #include "ipeimage.h" #include "ipestyle.h" // -------------------------------------------------------------------- namespace ipe { class BitmapFinder; class PdfResources; //! Flags for saving Ipe documents (to PDF) class SaveFlag { public: enum { SaveNormal = 0, //!< Nothing special Export = 1, //!< Don't include Ipe markup NoZip = 2, //!< Do not compress streams MarkedView = 4, //!< Create marked views only KeepNotes = 8, //!< Keep page notes as PDF annotations even when exporting }; }; //! There are several Ipe document formats. enum class FileFormat { Xml, //!< Save as XML Pdf, //!< Save as PDF Eps, //!< Encapsulated Postscript (loading only) Ipe5, //!< Ancient Ipe format Unknown //!< Unknown file format }; class Document { public: //! Properties of a document struct SProperties { String iTitle; String iAuthor; String iSubject; String iKeywords; String iPreamble; LatexType iTexEngine { LatexType::Default }; bool iFullScreen { false }; bool iNumberPages { false }; //! Date/time in PDF style "D:20010428191400" format. String iCreated; String iModified; //! Program that created this document (e.g. "Ipe 7.5"). String iCreator; }; //! Errors that can happen while loading documents enum LoadErrors { EVersionTooOld = -1, //!< The version of the file is too old. EVersionTooRecent = -2, //!< The file version is newer than this Ipelib. EFileOpenError = -3, //!< Error opening the file ENotAnIpeFile = -4, //!< The file was not created by Ipe. }; Document(); Document(const Document &rhs); Document &operator=(const Document &rhs) = delete; ~Document(); static FileFormat fileFormat(DataSource &source); static FileFormat formatFromFilename(String fn); static Document *load(DataSource &source, FileFormat format, int &reason); static Document *load(const char *fname, int &reason); static Document *loadWithErrorReport(const char *fname); bool save(TellStream &stream, FileFormat format, uint32_t flags) const; bool save(const char *fname, FileFormat format, uint32_t flags) const; bool exportPages(const char *fname, uint32_t flags, int fromPage, int toPage) const; bool exportView(const char *fname, FileFormat format, uint32_t flags, int pno, int vno) const; void saveAsXml(Stream &stream, bool usePdfBitmaps = false) const; //! Return number of pages of document. int countPages() const { return int(iPages.size()); } int countTotalViews() const; //! Return page (const version). /*! The first page is no 0. */ const Page *page(int no) const { return iPages[no]; } //! Return page. /*! The first page is no 0. */ Page *page(int no) { return iPages[no]; } int findPage(String nameOrNumber) const; Page *set(int no, Page *page); void insert(int no, Page *page); void push_back(Page *page); Page *remove(int no); //! Return document properties. inline SProperties properties() const { return iProperties; } void setProperties(const SProperties &info); //! Return stylesheet cascade. Cascade *cascade() { return iCascade; } //! Return stylesheet cascade (const version). const Cascade *cascade() const { return iCascade; } Cascade *replaceCascade(Cascade *cascade); void setResources(PdfResources *resources); //! Return the current PDF resources. inline const PdfResources *resources() const noexcept { return iResources; } void findBitmaps(BitmapFinder &bm) const; bool checkStyle(AttributeSeq &seq) const; //! Error codes returned by RunLatex. enum { ErrNone, ErrNoText, ErrNoDir, ErrWritingSource, ErrOldPdfLatex, ErrRunLatex, ErrLatex, ErrLatexOutput }; int runLatex(String docname, String &logFile); int runLatex(String docname); private: std::vector iPages; Cascade *iCascade; SProperties iProperties; PdfResources *iResources; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/include/ipegroup.h0000644000175000017500000000752513561570220016462 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // The group object. // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEGROUP_H #define IPEGROUP_H #include "ipeobject.h" #include "ipeshape.h" // -------------------------------------------------------------------- namespace ipe { class Shape; class Group : public Object { private: typedef std::vector List; public: typedef List::const_iterator const_iterator; explicit Group(); Group(const Group &rhs); virtual ~Group(); explicit Group(const XmlAttributes &attr); Group &operator=(const Group &rhs); virtual Object *clone() const; virtual Group *asGroup(); virtual const Group *asGroup() const; virtual Type type() const; virtual TPinned pinned() const; virtual void accept(Visitor &visitor) const; virtual void saveAsXml(Stream &stream, String layer) const; virtual void draw(Painter &painter) const; virtual void drawSimple(Painter &painter) const; virtual void addToBBox(Rect &box, const Matrix &m, bool cp) const; virtual double distance(const Vector &v, const Matrix &m, double bound) const; virtual void snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; virtual void snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const; inline const Shape &clip() const { return iClip; } void setClip(const Shape &clip); inline String url() const { return iUrl; } void setUrl(String url); //! Return number of component objects. inline int count() const { return iImp->iObjects.size(); } //! Return object at index \a i. inline const Object *object(int i) const { return iImp->iObjects[i]; } //! Return iterator for first object. inline const_iterator begin() const { return iImp->iObjects.begin(); } //! Return iterator for end of sequence. inline const_iterator end() const { return iImp->iObjects.end(); } void push_back(Object *); void saveComponentsAsXml(Stream &stream) const; virtual void checkStyle(const Cascade *sheet, AttributeSeq &seq) const; virtual Attribute getAttribute(Property prop) const noexcept; virtual bool setAttribute(Property prop, Attribute value); private: void detach(); private: struct Imp { List iObjects; int iRefCount; TPinned iPinned; // is any of the objects in the list pinned? }; Imp *iImp; Shape iClip; String iUrl; Attribute iDecoration; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipepresenter/0000755000175000017500000000000013561570220015530 5ustar otfriedotfriedipe-7.2.13/src/ipepresenter/mainmenu.xib0000644000175000017500000002261613561570220020054 0ustar otfriedotfried ipe-7.2.13/src/ipepresenter/timelabel_qt.h0000644000175000017500000000343713561570220020352 0ustar otfriedotfried// -------------------------------------------------------------------- // timelabel.h // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef TIMELABEL_H #define TIMELABEL_H #include #include #include class TimeLabel: public QLabel { Q_OBJECT public: TimeLabel(QWidget* parent); void mouseDoubleClickEvent(QMouseEvent* event); void toggleCounting(); void toggleCountdown(); void setTime(); void resetTime(); private: QTimer* timer; QTime time; bool counting; bool countingDown; private slots: void countTime(); }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipepresenter/ipepresenter_win.cpp0000644000175000017500000005112213561570220021617 0ustar otfriedotfried// -------------------------------------------------------------------- // IpePresenter with Windows UI // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepresenter.h" #include "ipepdfview_win.h" #include "ipethumbs.h" using namespace ipe; #include #include #include #define IDI_MYICON 1 #define IDD_INPUTBOX 103 #define IDC_INPUTBOX_PROMPT 1000 #define IDC_INPUTBOX_EDIT 1001 extern HBITMAP createBitmap(uint32_t *p, int w, int h); extern int showPageSelectDialog(int width, int height, const char * title, HIMAGELIST il, std::vector &labels, int startIndex); // -------------------------------------------------------------------- BOOL setWindowText(HWND h, const char *s) { int rw = MultiByteToWideChar(CP_UTF8, 0, s, -1, nullptr, 0); std::vector ws(rw); MultiByteToWideChar(CP_UTF8, 0, s, -1, &ws[0], rw); std::vector w; for (auto ch : ws) { if (ch != '\r') { if (ch == '\n') w.push_back('\r'); w.push_back(ch); } } w.push_back(0); return SetWindowTextW(h, &w[0]); } // -------------------------------------------------------------------- class AppUi : public Presenter { public: static void init(HINSTANCE hInstance); AppUi(HINSTANCE hInstance); void show(int nCmdShow); bool load(const char* fn); void cmd(int cmd); void toggleFullScreen(); void fitBoxAll(); void aboutIpePresenter(); private: void initUi(); virtual ~AppUi(); void setTimerValue(); void setView(); void setPdf(); void setTime(); void jumpTo(); void selectPage(); void layoutChildren(); void zoomMain(int delta); void timerElapsed(); void handlePdfViewMessage(int param); static LRESULT CALLBACK wndProc(HWND hwnd, UINT Message, WPARAM wParam, LPARAM lParam); static const wchar_t className[]; HWND hwnd; HWND hNotes; HWND hClock; HMENU hMenuBar; HFONT hFont; int iTime; bool iCountDown; bool iCountTime; PdfView *iCurrent; PdfView *iNext; PdfView *iScreen; int iMainPercentage; // for fullscreen mode bool iFullScreen; bool iWasMaximized; RECT iWindowRect; LONG iWindowStyle; LONG iWindowExStyle; HIMAGELIST iThumbNails; }; const wchar_t AppUi::className[] = L"ipePresenterWindowClass"; AppUi::AppUi(HINSTANCE hInstance) { iCurrent = nullptr; iNext = nullptr; iScreen = nullptr; iTime = 0; iCountDown = false; iCountTime = false; iMainPercentage = 70; iFullScreen = false; iThumbNails = nullptr; HWND hwnd = CreateWindowExW(WS_EX_CLIENTEDGE, className, L"IpePresenter", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, nullptr, nullptr, hInstance, this); if (hwnd == nullptr) { MessageBoxA(nullptr, "AppUi window creation failed!", "Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } assert(GetWindowLongPtr(hwnd, GWLP_USERDATA)); } void AppUi::initUi() { hMenuBar = CreateMenu(); /* HMENU hSubMenu = CreatePopupMenu(); AppendMenuA(hSubMenu, MF_STRING, EOpen, "&Open\tCtrl+O"); AppendMenuA(hSubMenu, MF_STRING, EQuit, "&Close\tCtrl+W"); AppendMenuA(hMenu, MF_STRING | MF_POPUP, UINT_PTR(hSubMenu), "&File"); */ HMENU hSubMenu = CreatePopupMenu(); AppendMenuA(hSubMenu, MF_STRING, EShowPresentation, "Show &Presentation"); AppendMenuA(hSubMenu, MF_STRING, EFullScreen, "Full &Screen\tF11"); AppendMenuA(hSubMenu, MF_STRING, EZoomIn, "Larger\tCtrl++"); AppendMenuA(hSubMenu, MF_STRING, EZoomOut, "Smaller\tCtrl+-"); AppendMenuA(hMenuBar, MF_STRING | MF_POPUP, UINT_PTR(hSubMenu), "&View"); hSubMenu = CreatePopupMenu(); AppendMenuA(hSubMenu, MF_STRING, ESetTime, "&Set time"); AppendMenuA(hSubMenu, MF_STRING, EResetTime, "&Reset time\tR"); AppendMenuA(hSubMenu, MF_STRING, ETimeCountdown, "Count down\t/"); AppendMenuA(hSubMenu, MF_STRING, EToggleTimeCounting, "Count time\tT"); AppendMenuA(hMenuBar, MF_STRING | MF_POPUP, UINT_PTR(hSubMenu), "&Time"); hSubMenu = CreatePopupMenu(); AppendMenuA(hSubMenu, MF_STRING, ENextView, "&Next view\tRight"); AppendMenuA(hSubMenu, MF_STRING, EPreviousView, "&Previous view\tLeft"); AppendMenuA(hSubMenu, MF_STRING, ENextPage, "&Next page\tN"); AppendMenuA(hSubMenu, MF_STRING, EPreviousPage, "&Previous page\tP"); AppendMenuA(hSubMenu, MF_STRING, EFirstView, "&First view\tHome"); AppendMenuA(hSubMenu, MF_STRING, ELastView, "&Last view\tEnd"); AppendMenuA(hSubMenu, MF_STRING, EJumpTo, "&Jump to\tJ"); AppendMenuA(hSubMenu, MF_STRING, ESelectPage, "&Select page\tS"); AppendMenuA(hMenuBar, MF_STRING | MF_POPUP, UINT_PTR(hSubMenu), "&Navigate"); hSubMenu = CreatePopupMenu(); AppendMenuA(hSubMenu, MF_STRING, EAbout, "&About IpePresenter"); AppendMenuA(hMenuBar, MF_STRING | MF_POPUP, UINT_PTR(hSubMenu), "&Help"); SetMenu(hwnd, hMenuBar); HINSTANCE hInstance = (HINSTANCE) GetWindowLongPtr(hwnd, GWLP_HINSTANCE); iCurrent = new PdfView(hwnd, hwnd); iNext = new PdfView(hwnd, hwnd); iScreen = new PdfView(nullptr, hwnd, hInstance); hNotes = CreateWindowExW(0, L"edit", nullptr, WS_CHILD | WS_VISIBLE | WS_BORDER | WS_VSCROLL | ES_READONLY | ES_LEFT | ES_MULTILINE | ES_AUTOVSCROLL, 0, 0, 0, 0, hwnd, nullptr, hInstance, nullptr); hClock = CreateWindowExW(0, L"static", nullptr, WS_CHILD | WS_VISIBLE | WS_BORDER | SS_CENTER, 0, 0, 0, 0, hwnd, nullptr, hInstance, nullptr); hFont = CreateFontW(48, 0, 0, 0, FW_DONTCARE, FALSE, FALSE, FALSE, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, L"MS Shell Dlg"); if (hFont != nullptr) SendMessage(hClock, WM_SETFONT, WPARAM (hFont), TRUE); SetTimer(hwnd, 1, 1000, nullptr); } AppUi::~AppUi() { if (iThumbNails) ImageList_Destroy(iThumbNails); KillTimer(hwnd, 1); delete iScreen; ipeDebug("AppUi::~AppUi()"); } // -------------------------------------------------------------------- void AppUi::layoutChildren() { if (iCurrent == nullptr) return; // no children yet RECT rc; GetClientRect(hwnd, &rc); int splitH = iMainPercentage * rc.right / 100; if (iPdf) { Rect box = mediaBox(-2); splitH = std::min(int(box.width() * rc.bottom / box.height()), splitH); } MoveWindow(iCurrent->windowId(), 0, 0, splitH, rc.bottom, TRUE); SIZE cts; int splitClock = 10 * rc.bottom / 100; HDC hdc = GetDC(hClock); if (hdc) SelectFont(hdc, hFont); if (hdc && GetTextExtentPoint32A(hdc, "1:23:45", 7, &cts)) { splitClock = cts.cy + 10; } int wid = rc.right - splitH - 10; MoveWindow(hClock, splitH + 10, 10, wid - 10, splitClock - 10, TRUE); int ht = rc.bottom / 2; // some simple default if (iPdf) { Rect box = mediaBox(-2); ht = std::min(long(box.height() * wid / box.width()) + 10, 80 * (rc.bottom - splitClock - 10) / 100); } int splitV = rc.bottom - ht; MoveWindow(iNext->windowId(), splitH + 10, splitV + 10, wid, ht - 10, TRUE); MoveWindow(hNotes, splitH + 10, splitClock + 10, wid, splitV - splitClock - 10, TRUE); InvalidateRect(hClock, nullptr, FALSE); } void AppUi::handlePdfViewMessage(int param) { // ignore all messages before PDF file loaded if (!iPdf) return; switch (param) { case 0: fitBoxAll(); break; case 1: cmd(ENextView); break; case 2: cmd(EPreviousView); break; } } void AppUi::toggleFullScreen() { HWND hwnd = iScreen->windowId(); if (!iFullScreen) { HMONITOR hmon = MonitorFromWindow(hwnd, MONITOR_DEFAULTTONEAREST); MONITORINFO mi = { sizeof(mi) }; if (!GetMonitorInfo(hmon, &mi)) return; iWasMaximized = IsZoomed(hwnd); if (iWasMaximized) SendMessage(hwnd, WM_SYSCOMMAND, SC_RESTORE, 0); GetWindowRect(hwnd, &iWindowRect); iWindowStyle = GetWindowLong(hwnd, GWL_STYLE); iWindowExStyle = GetWindowLong(hwnd, GWL_EXSTYLE); SetWindowLong(hwnd, GWL_STYLE, iWindowStyle & ~(WS_CAPTION | WS_THICKFRAME)); SetWindowLong(hwnd, GWL_EXSTYLE, iWindowExStyle & ~(WS_EX_DLGMODALFRAME | WS_EX_WINDOWEDGE | WS_EX_CLIENTEDGE | WS_EX_STATICEDGE)); SetWindowPos(hwnd, HWND_TOP, mi.rcMonitor.left, mi.rcMonitor.top, mi.rcMonitor.right - mi.rcMonitor.left, mi.rcMonitor.bottom - mi.rcMonitor.top, SWP_SHOWWINDOW); iFullScreen = true; } else { SetWindowLong(hwnd, GWL_STYLE, iWindowStyle); SetWindowLong(hwnd, GWL_EXSTYLE, iWindowExStyle); SetWindowPos(hwnd, nullptr, iWindowRect.left, iWindowRect.top, iWindowRect.right - iWindowRect.left, iWindowRect.bottom - iWindowRect.top, SWP_NOZORDER | SWP_NOACTIVATE | SWP_FRAMECHANGED); if (iWasMaximized) SendMessage(hwnd, WM_SYSCOMMAND, SC_MAXIMIZE, 0); iFullScreen = false; } } // -------------------------------------------------------------------- void AppUi::timerElapsed() { if (iCountTime) { if (iCountDown) { if (iTime > 0) --iTime; } else ++iTime; setTime(); } } // -------------------------------------------------------------------- bool AppUi::load(const char* fn) { bool result = Presenter::load(fn); if (result) { setPdf(); setView(); } return result; } void AppUi::setPdf() { iScreen->setPdf(iPdf.get()); iCurrent->setPdf(iPdf.get()); iNext->setPdf(iPdf.get()); } void AppUi::setView() { setViewPage(iScreen, iPdfPageNo); setViewPage(iCurrent, iPdfPageNo); setViewPage(iNext, iPdfPageNo < iPdf->countPages() - 1 ? iPdfPageNo + 1 : iPdfPageNo); setWindowText(hwnd, currentLabel().z()); setWindowText(hNotes, iAnnotations[iPdfPageNo].z()); setTime(); } void AppUi::setTime() { char buf[16]; sprintf(buf, "%d:%02d:%02d", iTime / 3600, (iTime / 60) % 60, iTime % 60); setWindowText(hClock, buf); } void AppUi::fitBoxAll() { fitBox(mediaBox(-1), iCurrent); fitBox(mediaBox(-2), iNext); fitBox(mediaBox(-1), iScreen); } void AppUi::zoomMain(int delta) { int nPerc = iMainPercentage + delta; if (50 <= nPerc && nPerc <= 80) iMainPercentage = nPerc; layoutChildren(); } // -------------------------------------------------------------------- void AppUi::cmd(int cmd) { // ipeDebug("Command %d", cmd); switch (cmd) { case EOpen: break; case EQuit: PostMessage(hwnd, WM_CLOSE, 0, 0); break; // case EShowPresentation: if (IsWindowVisible(iScreen->windowId())) ShowWindow(iScreen->windowId(), SW_HIDE); else ShowWindow(iScreen->windowId(), SW_SHOWNOACTIVATE); break; case EFullScreen: toggleFullScreen(); break; case EZoomIn: zoomMain(+1); break; case EZoomOut: zoomMain(-1); break; // case EToggleTimeCounting: iCountTime = !iCountTime; CheckMenuItem(hMenuBar, EToggleTimeCounting, iCountTime ? MF_CHECKED : MF_UNCHECKED); break; case ETimeCountdown: iCountDown = !iCountDown; CheckMenuItem(hMenuBar, ETimeCountdown, iCountDown ? MF_CHECKED : MF_UNCHECKED); break; case ESetTime: setTimerValue(); break; // case EResetTime: iTime = 0; setTime(); break; // case ELeftMouse: case ENextView: nextView(+1); setView(); break; case EOtherMouse: case EPreviousView: nextView(-1); setView(); break; case ENextPage: nextPage(+1); setView(); break; case EPreviousPage: nextPage(-1); setView(); break; case EFirstView: firstView(); setView(); break; case ELastView: lastView(); setView(); break; case EJumpTo: jumpTo(); break; case ESelectPage: selectPage(); break; case EAbout: aboutIpePresenter(); break; default: // unknown action return; } } // -------------------------------------------------------------------- static const char * const aboutText = "IpePresenter %d.%d.%d\n\n" "Copyright (c) 2019 Otfried Cheong\n\n" "A presentation tool for giving PDF presentations " "created in Ipe or using beamer.\n" "Originally invented by Dmitriy Morozov, " "IpePresenter is now released as part of Ipe under the GNU Public License.\n" "See http://ipe.otfried.org for details.\n\n" "You can \"like\" IpePresenter and follow IpePresenter announcements on Facebook " "(http://www.facebook.com/drawing.editor.Ipe7).\n\n" "If you are an IpePresenter fan and want to show others, have a look at the " "Ipe T-shirts (www.shirtee.com/en/store/ipe).\n\n" "Platinum sponsors\n\n" " * Hee-Kap Ahn\n" " * Martin Ziegler\n\n" "If you enjoy IpePresenter, you can become a member of the exclusive community of " "Ipe patrons (http://patreon.com/otfried). " "For the price of a cup of coffee per month you can make a meaningful contribution " "to the continuing development of IpePresenter and Ipe."; void AppUi::aboutIpePresenter() { std::vector buf(strlen(aboutText) + 100); sprintf(&buf[0], aboutText, IPELIB_VERSION / 10000, (IPELIB_VERSION / 100) % 100, IPELIB_VERSION % 100); MessageBoxA(hwnd, &buf[0], "About IpePresenter", MB_OK | MB_ICONINFORMATION | MB_APPLMODAL); } // -------------------------------------------------------------------- static String dialogInput; static String dialogPrompt; BOOL CALLBACK SetTimeProc(HWND hwndDlg, UINT message, WPARAM wParam, LPARAM lParam) { char buf[80]; switch (message) { case WM_INITDIALOG: SetDlgItemTextA(hwndDlg, IDC_INPUTBOX_PROMPT, dialogPrompt.z()); SetFocus(hwndDlg); break; case WM_COMMAND: switch (LOWORD(wParam)) { case IDOK: dialogInput.erase(); if (GetDlgItemTextA(hwndDlg, IDC_INPUTBOX_EDIT, buf, 80)) dialogInput = String(buf); // Fall through case IDCANCEL: EndDialog(hwndDlg, wParam); return TRUE; } } return FALSE; } void AppUi::setTimerValue() { HINSTANCE hInstance = (HINSTANCE) GetWindowLongPtr(hwnd, GWLP_HINSTANCE); dialogPrompt = "Enter time in minutes:"; if (DialogBox(hInstance, MAKEINTRESOURCE(IDD_INPUTBOX), hwnd, (DLGPROC) SetTimeProc) == IDOK) { Lex lex(dialogInput); int minutes = lex.getInt(); iTime = 60 * minutes; setTime(); } } void AppUi::jumpTo() { HINSTANCE hInstance = (HINSTANCE) GetWindowLongPtr(hwnd, GWLP_HINSTANCE); dialogPrompt = "Enter page label:"; if (DialogBox(hInstance, MAKEINTRESOURCE(IDD_INPUTBOX), hwnd, (DLGPROC) SetTimeProc) == IDOK) { jumpToPage(dialogInput); // trim? setView(); } } void AppUi::selectPage() { constexpr int iconWidth = 250; // Create thumbnails if (iThumbNails == nullptr) { PdfThumbnail r(iPdf.get(), iconWidth); int nItems = iPdf->countPages(); iThumbNails = ImageList_Create(r.width(), r.height(), ILC_COLOR32, nItems, 4); for (int i = 0; i < iPdf->countPages(); ++i) { Buffer bx = r.render(iPdf->page(i)); HBITMAP b = createBitmap((uint32_t *) bx.data(), r.width(), r.height()); ImageList_Add(iThumbNails, b, nullptr); } } const char *title = "IpePresenter: Select page"; std::vector labels; for (int i = 0; i < iPdf->countPages(); ++i) labels.push_back(pageLabel(i)); int width = 800; int height = 600; RECT rect; if (GetWindowRect(hwnd, &rect)) { width = rect.right - rect.left - 50; height = rect.bottom - rect.top - 80; } int sel = showPageSelectDialog(width, height, title, iThumbNails, labels, iPdfPageNo); if (sel >= 0) { iPdfPageNo = sel; setView(); } } // -------------------------------------------------------------------- LRESULT CALLBACK AppUi::wndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { AppUi *ui = (AppUi*) GetWindowLongPtr(hwnd, GWLP_USERDATA); switch (message) { case WM_CREATE: { LPCREATESTRUCT p = (LPCREATESTRUCT) lParam; ui = (AppUi *) p->lpCreateParams; ui->hwnd = hwnd; SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR) ui); ui->initUi(); } break; case WM_INITMENUPOPUP: if (ui && lParam == 0) { CheckMenuItem(ui->hMenuBar, EShowPresentation, IsWindowVisible(ui->iScreen->windowId()) ? MF_CHECKED : MF_UNCHECKED); CheckMenuItem(ui->hMenuBar, EFullScreen, ui->iFullScreen ? MF_CHECKED : MF_UNCHECKED); } break; case WM_COMMAND: if (ui) ui->cmd(LOWORD(wParam)); break; case WM_SIZE: if (ui) ui->layoutChildren(); break; case WM_TIMER: if (ui) ui->timerElapsed(); break; case WM_CLOSE: DestroyWindow(hwnd); break; case WM_DESTROY: PostQuitMessage(0); delete ui; break; case PdfView::WM_PDFVIEW: if (ui) ui->handlePdfViewMessage(lParam); break; default: break; } return DefWindowProc(hwnd, message, wParam, lParam); } void AppUi::init(HINSTANCE hInstance) { WNDCLASSEX wc; wc.cbSize = sizeof(WNDCLASSEX); wc.style = 0; wc.lpfnWndProc = wndProc; wc.cbClsExtra = 0; wc.cbWndExtra = 0; wc.hInstance = hInstance; wc.hCursor = LoadCursor(nullptr, IDC_ARROW); wc.hbrBackground = (HBRUSH)(COLOR_WINDOW+1); wc.lpszMenuName = nullptr; wc.lpszClassName = className; wc.hIcon = LoadIcon(GetModuleHandle(nullptr), MAKEINTRESOURCE(IDI_MYICON)); wc.hIconSm = HICON(LoadImage(GetModuleHandle(nullptr), MAKEINTRESOURCE(IDI_MYICON), IMAGE_ICON, 16, 16, 0)); if (!RegisterClassExW(&wc)) { MessageBoxA(nullptr, "AppUi registration failed!", "Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } PdfView::init(hInstance); } void AppUi::show(int nCmdShow) { ShowWindow(hwnd, nCmdShow); UpdateWindow(hwnd); } // -------------------------------------------------------------------- static String getFileName() { OPENFILENAMEW ofn; wchar_t szFileName[MAX_PATH] = L""; ZeroMemory(&ofn, sizeof(ofn)); ofn.lStructSize = sizeof(ofn); ofn.hwndOwner = nullptr; // hwnd? ofn.lpstrFilter = L"PDF Files\0*.pdf\0All Files\0*.*\0"; ofn.lpstrFile = szFileName; ofn.nMaxFile = MAX_PATH; ofn.Flags = OFN_EXPLORER | OFN_FILEMUSTEXIST; ofn.lpstrDefExt = L"pdf"; if (GetOpenFileNameW(&ofn)) return String(szFileName); return String(); } // -------------------------------------------------------------------- int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) { Platform::initLib(IPELIB_VERSION); AppUi::init(hInstance); AppUi *ui = new AppUi(hInstance); String fname { lpCmdLine }; if (fname.empty()) fname = getFileName(); if (fname.empty() || !ui->load(fname.z())) { MessageBoxA(nullptr, "Failed to load PDF file!", "IpePresenter Error!", MB_ICONEXCLAMATION | MB_OK); return 9; } ui->show(nCmdShow); ACCEL accel[] = { { FVIRTKEY, VK_PRIOR, AppUi::EPreviousView }, { FVIRTKEY, VK_NEXT, AppUi::ENextView }, { FVIRTKEY, VK_LEFT, AppUi::EPreviousView }, { FVIRTKEY, VK_RIGHT, AppUi::ENextView }, { FVIRTKEY, VK_UP, AppUi::EPreviousView }, { FVIRTKEY, VK_DOWN, AppUi::ENextView }, { FVIRTKEY|FCONTROL|FSHIFT, 0xbb, AppUi::EZoomIn }, { FVIRTKEY|FCONTROL, 0xbd, AppUi::EZoomOut }, { FVIRTKEY, 'N', AppUi::ENextPage }, { FVIRTKEY, 'P', AppUi::EPreviousPage }, { FVIRTKEY, 'T', AppUi::EToggleTimeCounting }, { FVIRTKEY, 'J', AppUi::EJumpTo }, { FVIRTKEY, 'S', AppUi::ESelectPage }, { FVIRTKEY, 'R', AppUi::EResetTime }, { FVIRTKEY, VK_OEM_2, AppUi::ETimeCountdown }, { FVIRTKEY, VK_HOME, AppUi::EFirstView }, { FVIRTKEY, VK_END, AppUi::ELastView }, { FVIRTKEY, VK_F11, AppUi::EFullScreen }, }; HACCEL hAccel = CreateAcceleratorTable(accel, sizeof(accel)/sizeof(ACCEL)); MSG msg; while (GetMessage(&msg, nullptr, 0, 0) > 0) { if (!TranslateAccelerator(msg.hwnd, hAccel, &msg)) { TranslateMessage(&msg); DispatchMessage(&msg); } } return msg.wParam; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipepresenter/ipepresenter_cocoa.cpp0000644000175000017500000003061413561570220022111 0ustar otfriedotfried// -*- objc -*- // -------------------------------------------------------------------- // IpePresenter with Cocoa UI // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepresenter.h" #include "ipepdfview_cocoa.h" #include "ipeselector_cocoa.h" #import using ipe::String; inline String N2I(NSString *aStr) { return String(aStr.UTF8String); } inline NSString *I2N(String s) {return [NSString stringWithUTF8String:s.z()];} // -------------------------------------------------------------------- @interface AppDelegate : NSObject @end @interface IpePdfSelectorProvider : IpeSelectorProvider @property ipe::PdfFile *pdf; @property ipe::PdfThumbnail *pdfThumb; @property NSMutableArray *pdfLabels; - (int) count; - (NSString *) title:(int) index; - (ipe::Buffer) renderImage:(int) index; @end // -------------------------------------------------------------------- @implementation IpePdfSelectorProvider - (int) count { return self.pdf->countPages(); } - (NSString *) title:(int) index { return self.pdfLabels[index]; } - (ipe::Buffer) renderImage:(int) index { return self.pdfThumb->render(self.pdf->page(index)); } @end // -------------------------------------------------------------------- class AppUi : public Presenter { public: AppUi(); bool load(NSString *aFname); void setPdf(); void setView(); void fitBoxAll(); void setTime(); void timerElapsed(); void selectPage(); public: int iTime; bool iCountDown; bool iCountTime; NSWindow *iWindow; NSWindow *iScreenWindow; NSSplitView *iContent; NSSplitView *iRightSide; NSStackView *iTopRight; NSTextField *iClock; NSTextView *iNotesView; NSScrollView *iNotes; IpePdfView *iCurrent; IpePdfView *iNext; IpePdfView *iScreen; IpePdfSelectorProvider *iProvider; }; AppUi::AppUi() : iTime{0}, iCountDown{false}, iCountTime{false}, iCurrent{nil}, iNext{nil}, iScreen{nil}, iProvider{nil} { NSRect contentRect = NSMakeRect(335., 390., 800., 600.); NSRect mainRect = NSMakeRect(0., 0., 200., 100.); NSRect subRect = NSMakeRect(0., 0., 100., 100.); NSRect clockRect = NSMakeRect(0., 0., 100., 30.); iWindow = [[NSWindow alloc] initWithContentRect:contentRect styleMask:(NSTitledWindowMask| NSClosableWindowMask| NSResizableWindowMask| NSMiniaturizableWindowMask) backing:NSBackingStoreBuffered defer:YES]; iContent = [[NSSplitView alloc] initWithFrame:subRect]; iContent.vertical = YES; iRightSide = [[NSSplitView alloc] initWithFrame:subRect]; iRightSide.vertical = NO; iCurrent = [[IpePdfView alloc] initWithFrame:mainRect]; iNext = [[IpePdfView alloc] initWithFrame:subRect]; iClock = [[NSTextField alloc] initWithFrame:clockRect]; iClock.bordered= NO; iClock.drawsBackground = NO; iClock.editable = NO; iClock.font = [NSFont labelFontOfSize:24.0]; iClock.alignment = NSCenterTextAlignment; iClock.usesSingleLineMode = YES; iNotes = [[NSScrollView alloc] initWithFrame:subRect]; iNotesView = [[NSTextView alloc] initWithFrame:subRect]; iNotesView.editable = NO; iNotesView.richText = NO; [iNotesView setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable]; [iNotes setDocumentView:iNotesView]; iNotes.hasVerticalScroller = YES; iTopRight = [NSStackView stackViewWithViews:@[iClock, iNotes]]; iTopRight.orientation = NSUserInterfaceLayoutOrientationVertical; [iContent addSubview:iCurrent]; [iContent addSubview:iRightSide]; [iRightSide addSubview:iTopRight]; [iRightSide addSubview:iNext]; [iContent adjustSubviews]; [iRightSide adjustSubviews]; double split = (0.6 * [iRightSide minPossiblePositionOfDividerAtIndex:0] + 0.4 * [iRightSide maxPossiblePositionOfDividerAtIndex:0]); [iRightSide setPosition:split ofDividerAtIndex:0]; [iWindow setContentView:iContent]; iScreenWindow = [[NSWindow alloc] initWithContentRect:contentRect styleMask:(NSTitledWindowMask| NSResizableWindowMask| NSMiniaturizableWindowMask) backing:NSBackingStoreBuffered defer:YES]; iScreen = [[IpePdfView alloc] initWithFrame:subRect]; [iScreenWindow setContentView:iScreen]; } bool AppUi::load(NSString *aFname) { bool result = Presenter::load(N2I(aFname).z()); if (result) { setPdf(); setView(); fitBoxAll(); iProvider = nil; } return result; } void AppUi::setPdf() { iCurrent.pdfView->setPdf(iPdf.get()); iNext.pdfView->setPdf(iPdf.get()); iScreen.pdfView->setPdf(iPdf.get()); } void AppUi::setView() { setViewPage(iScreen.pdfView, iPdfPageNo); setViewPage(iCurrent.pdfView, iPdfPageNo); setViewPage(iNext.pdfView, iPdfPageNo < iPdf->countPages() - 1 ? iPdfPageNo + 1 : iPdfPageNo); [iWindow setTitle:I2N(currentLabel())]; NSAttributedString *n = [[NSAttributedString alloc] initWithString:I2N(iAnnotations[iPdfPageNo])]; [[iNotesView textStorage] setAttributedString:n]; iNotesView.textColor = [NSColor textColor]; iNotesView.font = [NSFont labelFontOfSize:14.0]; setTime(); } void AppUi::fitBoxAll() { if (!iPdf) return; fitBox(mediaBox(-1), iCurrent.pdfView); fitBox(mediaBox(-2), iNext.pdfView); fitBox(mediaBox(-1), iScreen.pdfView); } void AppUi::setTime() { [iClock setStringValue:[NSString stringWithFormat:@"%d:%02d:%02d", iTime / 3600, (iTime / 60) % 60, iTime % 60]]; [iRightSide adjustSubviews]; } void AppUi::timerElapsed() { if (iCountTime) { if (iCountDown) { if (iTime > 0) --iTime; } else ++iTime; setTime(); } } void AppUi::selectPage() { constexpr int iconWidth = 250; if (!iProvider) { iProvider = [IpePdfSelectorProvider new]; iProvider.pdf = iPdf.get(); iProvider.pdfThumb = new ipe::PdfThumbnail(iPdf.get(), iconWidth); iProvider.pdfLabels = [NSMutableArray new]; for (int i = 0; i < iPdf->countPages(); ++i) [iProvider.pdfLabels addObject:I2N(pageLabel(i))]; NSSize tnSize; tnSize.width = iProvider.pdfThumb->width() / 2.0; tnSize.height = iProvider.pdfThumb->height() / 2.0; iProvider.tnSize = tnSize; } const char *title = "IpePresenter: Select page"; int width = 800; int height = 600; int sel = showPageSelectDialog(width, height, title, iProvider, iPdfPageNo); if (sel >= 0) { iPdfPageNo = sel; setView(); } } // -------------------------------------------------------------------- static void setItemShortcut(NSMenu *menu, int index, unichar code) { NSMenuItem *item = [menu itemAtIndex:index]; item.keyEquivalent = [NSString stringWithFormat:@"%C", code]; item.keyEquivalentModifierMask = 0; } // -------------------------------------------------------------------- @implementation AppDelegate { AppUi *ui; } - (instancetype) init { self = [super init]; if (self) ui = new AppUi(); return self; } - (BOOL) applicationShouldTerminateAfterLastWindowClosed:(NSApplication *) app { return YES; } - (void) applicationWillFinishLaunching:(NSNotification *) notification { [ui->iWindow setDelegate:(id) self]; [ui->iScreenWindow setDelegate:(id) self]; [ui->iContent setDelegate:(id) self]; [ui->iRightSide setDelegate:(id) self]; } - (void) applicationDidFinishLaunching:(NSNotification *) aNotification { NSMenu *menu = [NSApp menu]; int i = [menu indexOfItemWithTag:13]; NSMenu *navi = [menu itemAtIndex:i].submenu; setItemShortcut(navi, 0, NSRightArrowFunctionKey); setItemShortcut(navi, 1, NSDownArrowFunctionKey); setItemShortcut(navi, 2, NSLeftArrowFunctionKey); setItemShortcut(navi, 3, NSUpArrowFunctionKey); [ui->iWindow makeKeyAndOrderFront:self]; ui->fitBoxAll(); [NSTimer scheduledTimerWithTimeInterval:1.0 target:self selector:@selector(timerFired:) userInfo:nil repeats:YES]; if (ui->iFileName.empty()) [self openDocument:self]; } - (BOOL) application:(NSApplication *) app openFile:(NSString *) filename { return ui->load(filename); } - (void) windowDidEndLiveResize:(NSNotification *) notification { ui->fitBoxAll(); } - (void) splitViewDidResizeSubviews:(NSNotification *) notification { ui->fitBoxAll(); } - (void) windowDidExitFullScreen:(NSNotification *) notification { ui->fitBoxAll(); } - (BOOL) validateMenuItem:(NSMenuItem *) item { if (item.action == @selector(countDown:)) { item.state = ui->iCountDown ? NSOnState : NSOffState; } else if (item.action == @selector(countTime:)) { item.state = ui->iCountTime ? NSOnState : NSOffState; } return YES; } - (void) pdfViewMouseButton:(NSEvent *) event { int button = event.buttonNumber; if (button == 0) [self nextView:event.window]; else if (button == 1) [self previousView:event.window]; } - (BOOL) windowShouldClose:(id) sender { if (sender == ui->iWindow) [ui->iScreenWindow close]; // also close presentation window return true; } - (void) timerFired:(NSTimer *) timer { ui->timerElapsed(); } // -------------------------------------------------------------------- - (void) openDocument:(id) sender { NSOpenPanel *panel = [NSOpenPanel openPanel]; [panel beginSheetModalForWindow:ui->iWindow completionHandler: ^(NSInteger result) { if (result == NSFileHandlingPanelOKButton) { NSURL *url = [[panel URLs] objectAtIndex:0]; if ([url isFileURL]) ui->load([url path]); } // canceled or failed to load and we didn't have a document before if (ui->iFileName.empty()) [NSApp terminate:self]; } ]; } - (void) showPresentation:(id) sender { [ui->iScreenWindow setIsVisible:true]; } - (void) setTime:(id) sender { NSString *input = [self input:@"Enter time in minutes:" defaultValue:@""]; if (input) { ipe::Lex lex(N2I(input)); int minutes = lex.getInt(); ui->iTime = 60 * minutes; ui->setTime(); } } - (void) resetTime:(id) sender { ui->iTime = 0; ui->setTime(); } - (void) countDown:(id) sender { ui->iCountDown = !ui->iCountDown; } - (void) countTime:(id) sender { ui->iCountTime = !ui->iCountTime; } - (void) nextView:(id) sender { ui->nextView(+1); ui->setView(); } - (void) previousView:(id) sender { ui->nextView(-1); ui->setView(); } - (void) nextPage:(id) sender { ui->nextPage(+1); ui->setView(); } - (void) previousPage:(id) sender { ui->nextPage(-1); ui->setView(); } - (void) jumpTo:(id) sender { NSString *input = [self input:@"Enter page label:" defaultValue:@""]; if (input) { ui->jumpToPage(N2I(input)); ui->setView(); } } - (void) selectPage:(id) sender { ui->selectPage(); } - (NSString *) input: (NSString *) prompt defaultValue: (NSString *)defaultValue { NSAlert *alert = [[NSAlert alloc] init]; alert.messageText = prompt; [alert addButtonWithTitle:@"Ok"]; [alert addButtonWithTitle:@"Cancel"]; NSTextField *input = [[NSTextField alloc] initWithFrame:NSMakeRect(0, 0, 200, 24)]; input.stringValue = defaultValue; alert.accessoryView = input; NSInteger button = [alert runModal]; if (button == NSAlertFirstButtonReturn) { [input validateEditing]; return [input stringValue]; } else return nil; } @end // -------------------------------------------------------------------- int main(int argc, const char * argv[]) { ipe::Platform::initLib(ipe::IPELIB_VERSION); return NSApplicationMain(argc, argv); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipepresenter/ipepresenter.exe.manifest0000644000175000017500000000315513561570220022551 0ustar otfriedotfried Presentation tool of the Ipe extensible drawing editor. True ipe-7.2.13/src/ipepresenter/ipepresenter_qt.cpp0000644000175000017500000003211113561570220021443 0ustar otfriedotfried// -------------------------------------------------------------------- // IpePresenter for Qt // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepresenter_qt.h" #include "ipethumbs.h" #include #include #include #include #include #include #include #include #include using namespace ipe; // -------------------------------------------------------------------- inline QString QIpe(const String &str) { return QString::fromUtf8(str.z()); } // -------------------------------------------------------------------- IpeAction::IpeAction(int cmd, const QString &text, const char *shortcut, MainWindow *parent): QAction(text, parent), iCommand{cmd} { if (shortcut) setShortcut(QKeySequence(shortcut)); connect(this, &QAction::triggered, [=] () { parent->cmd(iCommand); }); } // -------------------------------------------------------------------- BeamerView::BeamerView(Qt::WindowFlags f) : QMainWindow(nullptr, f) { iView = new PdfView(this); setCentralWidget(iView); } // -------------------------------------------------------------------- MainWindow::MainWindow(BeamerView* bv, Qt::WindowFlags f) : QMainWindow(nullptr, f), iScreen(bv) { QWidget *centralwidget = new QWidget(this); QHBoxLayout *horizontalLayout = new QHBoxLayout(centralwidget); QSplitter *splitV = new QSplitter(centralwidget); splitV->setOrientation(Qt::Horizontal); iCurrent = new PdfView(splitV); QSizePolicy sizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); sizePolicy.setHorizontalStretch(0); sizePolicy.setVerticalStretch(0); sizePolicy.setHeightForWidth(iCurrent->sizePolicy().hasHeightForWidth()); iCurrent->setSizePolicy(sizePolicy); iCurrent->setMinimumSize(QSize(600, 0)); splitV->addWidget(iCurrent); QSplitter *splitH = new QSplitter(splitV); splitH->setOrientation(Qt::Vertical); QWidget *clockNotes = new QWidget(splitH); QVBoxLayout *clockNotesLayout = new QVBoxLayout(clockNotes); clockNotesLayout->setContentsMargins(0, 0, 0, 0); iClock = new TimeLabel(clockNotes); QFont clockFont; clockFont.setPointSize(28); iClock->setFont(clockFont); clockNotesLayout->addWidget(iClock); QLabel *notesLabel = new QLabel(clockNotes); clockNotesLayout->addWidget(notesLabel); iNotes = new QPlainTextEdit(clockNotes); iNotes->setReadOnly(true); QFont notesFont; notesFont.setFamily(QStringLiteral("Monospace")); iNotes->setFont(notesFont); clockNotesLayout->addWidget(iNotes); splitH->addWidget(clockNotes); QWidget *nextView = new QWidget(splitH); QVBoxLayout *nextLayout = new QVBoxLayout(nextView); nextLayout->setContentsMargins(0, 0, 0, 0); QLabel *nextLabel = new QLabel(nextView); QSizePolicy sizePolicy1(QSizePolicy::Preferred, QSizePolicy::Fixed); sizePolicy1.setHorizontalStretch(0); sizePolicy1.setVerticalStretch(0); sizePolicy1.setHeightForWidth(nextLabel->sizePolicy().hasHeightForWidth()); nextLabel->setSizePolicy(sizePolicy1); nextLayout->addWidget(nextLabel); iNext = new PdfView(nextView); QSizePolicy sizePolicy2(QSizePolicy::Expanding, QSizePolicy::Expanding); sizePolicy2.setHorizontalStretch(0); sizePolicy2.setVerticalStretch(0); sizePolicy2.setHeightForWidth(iNext->sizePolicy().hasHeightForWidth()); iNext->setSizePolicy(sizePolicy2); nextLayout->addWidget(iNext); splitH->addWidget(nextView); splitV->addWidget(splitH); horizontalLayout->addWidget(splitV); setCentralWidget(centralwidget); iClock->setText("00:00:00"); notesLabel->setText("Notes:"); nextLabel->setText("Next view:"); QMenuBar *menubar = new QMenuBar(this); setMenuBar(menubar); iViewMenu = menuBar()->addMenu(tr("&View")); iTimeMenu = menuBar()->addMenu(tr("&Time")); iMoveMenu = menuBar()->addMenu(tr("&Navigate")); iHelpMenu = menuBar()->addMenu(tr("&Help")); iShowPresentationAction = new IpeAction(EShowPresentation, "Show presentation", nullptr, this); iShowPresentationAction->setCheckable(true); iViewMenu->addAction(iShowPresentationAction); iFullScreenAction = new IpeAction(EFullScreen, "Full screen", "F11", this); iFullScreenAction->setCheckable(true); iViewMenu->addAction(iFullScreenAction); connect(iViewMenu, &QMenu::aboutToShow, [=] () { iShowPresentationAction->setChecked(iScreen->isVisible()); iFullScreenAction->setChecked((iScreen->windowState() & Qt::WindowFullScreen) != 0); }); iTimeMenu->addAction(new IpeAction(ESetTime, "Set time", "", this)); iTimeMenu->addAction(new IpeAction(EResetTime, "Reset time", "R", this)); IpeAction *countDown = new IpeAction(ETimeCountdown, "Count down", "/", this); countDown->setCheckable(true); iTimeMenu->addAction(countDown); IpeAction* countTime = new IpeAction(EToggleTimeCounting, "Count time", "T", this); countTime->setCheckable(true); iTimeMenu->addAction(countTime); IpeAction *next = new IpeAction(ENextView, "Next view", nullptr, this); IpeAction *prev = new IpeAction(EPreviousView, "Previous view", nullptr, this); QList nextKeys { QKeySequence("Right"), QKeySequence("Down"), QKeySequence("PgDown"),}; QList prevKeys { QKeySequence("Left"), QKeySequence("Up"), QKeySequence("PgUp") }; next->setShortcuts(nextKeys); prev->setShortcuts(prevKeys); iMoveMenu->addAction(next); iMoveMenu->addAction(prev); iMoveMenu->addAction(new IpeAction(ENextPage, "Next page", "N", this)); iMoveMenu->addAction(new IpeAction(EPreviousPage, "Previous page", "P", this)); iMoveMenu->addAction(new IpeAction(EFirstView, "First view", "Home", this)); iMoveMenu->addAction(new IpeAction(ELastView, "Last view", "End", this)); iMoveMenu->addAction(new IpeAction(EJumpTo, "Jump to...", "J", this)); iMoveMenu->addAction(new IpeAction(ESelectPage, "Select page...", "S", this)); iHelpMenu->addAction(new IpeAction(EAbout, "About IpePresenter", nullptr, this)); connect(iScreen->pdfView(), &PdfView::sizeChanged, [=] () { fitBox(mediaBox(-1), iScreen->pdfView()); }); connect(iCurrent, &PdfView::sizeChanged, [=] () { fitBox(mediaBox(-1), iCurrent); }); connect(iNext, &PdfView::sizeChanged, [=] () { fitBox(mediaBox(-2), iNext); }); connect(iCurrent, &PdfView::mouseButton, this, &MainWindow::cmd); connect(iScreen->pdfView(), &PdfView::mouseButton, this, &MainWindow::cmd); } // -------------------------------------------------------------------- void MainWindow::cmd(int c) { // ipeDebug("Command %d", c); switch (c) { case EOpen: break; case EQuit: QApplication::exit(); break; // case EShowPresentation: if (iScreen->isVisible()) iScreen->hide(); else iScreen->show(); break; case EFullScreen: iScreen->setWindowState(iScreen->windowState() ^ Qt::WindowFullScreen); break; // case EToggleTimeCounting: iClock->toggleCounting(); break; case ETimeCountdown: iClock->toggleCountdown(); break; case ESetTime: iClock->setTime(); break; case EResetTime: iClock->resetTime(); break; // case ELeftMouse: case ENextView: nextView(+1); setView(); break; case EOtherMouse: case EPreviousView: nextView(-1); setView(); break; case ENextPage: nextPage(+1); setView(); break; case EPreviousPage: nextPage(-1); setView(); break; case EFirstView: firstView(); setView(); break; case ELastView: lastView(); setView(); break; case EJumpTo: jumpTo(); break; case ESelectPage: selectPage(); break; case EAbout: aboutIpePresenter(); break; default: // unknown action return; } } // -------------------------------------------------------------------- bool MainWindow::load(const char* fn) { bool result = Presenter::load(fn); if (result) { setPdf(); setView(); } return result; } void MainWindow::jumpTo() { auto str = QInputDialog::getText(this, tr("Jump to page"), tr("Enter page label:")); if (!str.isEmpty()) { jumpToPage(String(str.trimmed().toUtf8())); setView(); } } void MainWindow::setPdf() { iScreen->pdfView()->setPdf(iPdf.get()); iCurrent->setPdf(iPdf.get()); iNext->setPdf(iPdf.get()); } void MainWindow::setView() { setViewPage(iScreen->pdfView(), iPdfPageNo); setViewPage(iCurrent, iPdfPageNo); setViewPage(iNext, iPdfPageNo < iPdf->countPages() - 1 ? iPdfPageNo + 1 : iPdfPageNo); setWindowTitle(QIpe(currentLabel())); iNotes->setPlainText(QIpe(iAnnotations[iPdfPageNo])); } void MainWindow::selectPage() { constexpr int iconWidth = 250; std::vector labels; for (int i = 0; i < iPdf->countPages(); ++i) labels.push_back(pageLabel(i)); if (iPageIcons.empty()) { PdfThumbnail r(iPdf.get(), iconWidth); for (int i = 0; i < iPdf->countPages(); ++i) { Buffer b = r.render(iPdf->page(i)); QImage bits((const uchar *) b.data(), r.width(), r.height(), QImage::Format_RGB32); // need to copy bits since buffer b is temporary iPageIcons.push_back(QPixmap::fromImage(bits.copy())); } } QDialog *d = new QDialog(); d->setWindowTitle("IpePresenter: Select page"); QLayout *lo = new QVBoxLayout; PageSelector *p = new PageSelector(d); p->fill(iPageIcons, labels); p->setCurrentRow(iPdfPageNo); lo->addWidget(p); d->setLayout(lo); QWidget::connect(p, SIGNAL(selectionMade()), d, SLOT(accept())); d->setWindowState(Qt::WindowMaximized); int result = d->exec(); int sel = p->selectedIndex(); delete d; if (result == QDialog::Accepted) { iPdfPageNo = sel; setView(); } } // -------------------------------------------------------------------- void MainWindow::closeEvent(QCloseEvent *event) { iScreen->close(); QMainWindow::closeEvent(event); } // -------------------------------------------------------------------- static const char * const aboutText = "

IpePresenter %d.%d.%d

" "

Copyright (c) 2019 Otfried Cheong

" "

A presentation tool for giving PDF presentations " "created in Ipe or using beamer.

" "

Originally invented by Dmitriy Morozov, " "IpePresenter is now released as part of Ipe under the GNU Public License.

" "

See the Ipe homepage" " for further information.

" "

You can \"like\" IpePresenter and follow IpePresenter announcements on " "Facebook.

" "

If you are an IpePresenter fan and want to show others, have a look at the " "Ipe T-shirts.

" "

Platinum sponsors

" "
  • Hee-Kap Ahn
  • " "
  • Martin Ziegler
" "

If you enjoy IpePresenter, you can become a member of the exclusive community of " "Ipe patrons. " "For the price of a cup of coffee per month you can make a meaningful contribution " "to the continuing development of IpePresenter and Ipe.

" "
"; void MainWindow::aboutIpePresenter() { std::vector buf(strlen(aboutText) + 100); sprintf(&buf[0], aboutText, IPELIB_VERSION / 10000, (IPELIB_VERSION / 100) % 100, IPELIB_VERSION % 100); QMessageBox msgBox(this); msgBox.setWindowTitle("About IpePresenter"); msgBox.setInformativeText(&buf[0]); msgBox.setStandardButtons(QMessageBox::Ok); msgBox.exec(); } // -------------------------------------------------------------------- static void usage() { fprintf(stderr, "Usage: ipepresenter \n"); exit(1); } int main(int argc, char *argv[]) { Platform::initLib(IPELIB_VERSION); QApplication a(argc, argv); if (argc != 2) usage(); const char *load = argv[1]; BeamerView *bv = new BeamerView(); MainWindow *mw = new MainWindow(bv); if (!mw->load(load)) exit(2); mw->show(); QObject::connect(&a, SIGNAL(lastWindowClosed()), &a, SLOT(quit())); return a.exec(); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipepresenter/ipepresenter_qt.h0000644000175000017500000000546513561570220021124 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // IpePresenter for Qt // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPRESENTER_QT_H #define IPEPRESENTER_QT_H #include "ipeselector_qt.h" #include "ipepdfview_qt.h" #include "timelabel_qt.h" #include "ipepresenter.h" #include #include #include #include #include // -------------------------------------------------------------------- class MainWindow; class IpeAction: public QAction { Q_OBJECT public: IpeAction(int cmd, const QString &text, const char *shortcut, MainWindow *parent); private: int iCommand; }; // -------------------------------------------------------------------- class BeamerView: public QMainWindow { Q_OBJECT public: BeamerView(Qt::WindowFlags f = nullptr); PdfView *pdfView() { return iView; } private: PdfView *iView; }; // -------------------------------------------------------------------- class MainWindow: public QMainWindow, public Presenter { Q_OBJECT public: MainWindow(BeamerView* bv, Qt::WindowFlags f = nullptr); bool load(const char* fn); void cmd(int c); void aboutIpePresenter(); private: void closeEvent(QCloseEvent *event); void setPdf(); void setView(); void jumpTo(); void selectPage(); private: QMenu *iViewMenu; QMenu *iTimeMenu; QMenu *iMoveMenu; QMenu *iHelpMenu; IpeAction *iShowPresentationAction; IpeAction *iFullScreenAction; PdfView *iCurrent; PdfView *iNext; BeamerView *iScreen; QPlainTextEdit *iNotes; TimeLabel *iClock; std::vector iPageIcons; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipepresenter/ipepresenter.cpp0000644000175000017500000001564013561570220020747 0ustar otfriedotfried// -------------------------------------------------------------------- // IpePresenter common base // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepresenter.h" using namespace ipe; // -------------------------------------------------------------------- bool Presenter::load(const char *fname) { std::FILE *pdfFile = Platform::fopen(fname, "rb"); if (!pdfFile) return false; FileSource source(pdfFile); std::unique_ptr pdf = std::make_unique(); bool okay = pdf->parse(source); std::fclose(pdfFile); if (!okay) return false; iPdf = std::move(pdf); iFileName = fname; iPdfPageNo = 0; collectAnnotations(); makePageLabels(); return true; } // read annotations from PDF void Presenter::collectAnnotations() { iAnnotations.clear(); for (int i = 0; i < iPdf->countPages(); ++i) { String notes; const PdfDict *page = iPdf->page(i); const PdfObj *annots = page->get("Annots", iPdf.get()); if (annots && annots->array()) { for (int j = 0; j < annots->array()->count(); ++j) { const PdfObj *a = annots->array()->obj(j, iPdf.get()); if (a && a->dict()) { const PdfObj *type = a->dict()->get("Type", iPdf.get()); const PdfObj *subtype = a->dict()->get("Subtype", iPdf.get()); const PdfObj *contents = a->dict()->get("Contents", iPdf.get()); if (type && type->name() && type->name()->value() == "Annot" && subtype && subtype->name() && subtype->name()->value() == "Text" && contents && contents->string()) { if (!notes.empty()) notes += "\n"; notes += contents->string()->value(); } } } } iAnnotations.push_back(notes); } } // create the page labels void Presenter::makePageLabels() { iPageLabels.clear(); const PdfObj *d1 = iPdf->catalog()->get("PageLabels", iPdf.get()); if (d1 && d1->dict()) { collectPageLabels(d1->dict()); } else { for (int pno = 0; pno < iPdf->countPages(); ++pno) { char buf[16]; sprintf(buf, "%d", pno + 1); iPageLabels.push_back(std::make_pair(String(buf), -1)); } } } // this is not a complete implementation, // just meant to work for beamer output and Ipe void Presenter::collectPageLabels(const PdfDict *d) { const PdfObj *nums = d->get("Nums", iPdf.get()); if (nums && nums->array()) { int prevNum = 0; String prevLabel; for (int j = 0; j < nums->array()->count() - 1; j += 2) { const PdfObj *num = nums->array()->obj(j, iPdf.get()); const PdfObj *label = nums->array()->obj(j + 1, iPdf.get()); if (num->number() && label->dict()) { int newNum = int(num->number()->value()); const PdfObj *p = label->dict()->get("P", iPdf.get()); String newLabel; if (p && p->string()) newLabel = p->string()->value(); bool moreThanOne = (newNum - prevNum) > 1; while (size(iPageLabels) < newNum) iPageLabels.push_back(std::make_pair(prevLabel, moreThanOne ? iPageLabels.size() - prevNum : -1)); prevNum = newNum; prevLabel = newLabel; } } bool moreThanOne = (iPdf->countPages() - iPageLabels.size()) > 1; while (size(iPageLabels) < iPdf->countPages()) iPageLabels.push_back(std::make_pair(prevLabel, moreThanOne ? iPageLabels.size() - prevNum : -1)); } } // -------------------------------------------------------------------- void Presenter::setViewPage(PdfViewBase *view, int pdfpno) { view->setPage(iPdf->page(pdfpno), mediaBox(pdfpno)); view->updatePdf(); } void Presenter::fitBox(const Rect &box, PdfViewBase *view) { if (box.isEmpty()) return; double xfactor = box.width() > 0.0 ? (view->viewWidth() / box.width()) : 20.0; double yfactor = box.height() > 0.0 ? (view->viewHeight() / box.height()) : 20.0; double zoom = (xfactor > yfactor) ? yfactor : xfactor; view->setPan(0.5 * (box.bottomLeft() + box.topRight())); view->setZoom(zoom); view->updatePdf(); } // -------------------------------------------------------------------- String Presenter::pageLabel(int pdfno) { auto & pl = iPageLabels[pdfno]; String s; ipe::StringStream ss(s); ss << pl.first; if (pl.second >= 0) { if (pl.first.right(1) != "-") ss << "-"; ss << pl.second + 1; } return s; } String Presenter::currentLabel() { String s = iFileName; if (iFileName.rfind('/') >= 0) s = iFileName.substr(iFileName.rfind('/') + 1); ipe::StringStream ss(s); ss << " : " << pageLabel(iPdfPageNo) << " / " << iPageLabels.back().first << " (" << iPdfPageNo + 1 << " / " << iPdf->countPages() << ")"; return s; } Rect Presenter::mediaBox(int pdfpno) const { if (pdfpno == -1) pdfpno = iPdfPageNo; else if (pdfpno == -2) pdfpno = (iPdfPageNo < iPdf->countPages() - 1) ? iPdfPageNo + 1 : iPdfPageNo; return iPdf->mediaBox(iPdf->page(pdfpno)); } // -------------------------------------------------------------------- void Presenter::jumpToPage(String page) { if (page.empty()) return; for (int i = 0; i < size(iPageLabels); ++i) { auto pl = pageLabel(i); if (page == pl || (page + "-1" == pl) || page == (pl + "-1")) { iPdfPageNo = i; return; } } } void Presenter::nextView(int delta) { int npno = iPdfPageNo + delta; if (0 <= npno && npno < iPdf->countPages()) { iPdfPageNo = npno; } } void Presenter::nextPage(int delta) { String now = iPageLabels[iPdfPageNo].first; while (iPageLabels[iPdfPageNo].first == now && 0 <= iPdfPageNo + delta && iPdfPageNo + delta < iPdf->countPages()) iPdfPageNo += delta; if (delta < 0) { // go back to first view of the same page String cur = iPageLabels[iPdfPageNo].first; while (0 < iPdfPageNo && iPageLabels[iPdfPageNo-1].first == cur) iPdfPageNo += delta; } } void Presenter::firstView() { iPdfPageNo = 0; } void Presenter::lastView() { iPdfPageNo = iPdf->countPages() - 1; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipepresenter/Makefile0000644000175000017500000000472613561570220017201 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for IpePresenter # -------------------------------------------------------------------- BUNDLEDIR = $(BUILDDIR)/IpePresenter.app/Contents OBJDIR = $(BUILDDIR)/obj/ipepresenter include ../common.mak TARGET = $(call exe_target,ipepresenter) CPPFLAGS += -I../include -I../ipecanvas -I../ipecairo \ $(UI_CFLAGS) $(CAIRO_CFLAGS) $(ZLIB_CFLAGS) LIBS += -L$(buildlib) -lipecanvas -lipecairo -lipe \ $(UI_LIBS) $(CAIRO_LIBS) $(ZLIB_LIBS) all: $(TARGET) sources = ipepresenter.cpp win_sources = ipepresenter_win.cpp cocoa_sources = ipepresenter_cocoa.cpp qt_sources = ipepresenter_qt.cpp timelabel_qt.cpp moc_headers = ipepresenter_qt.h timelabel_qt.h ifdef WIN32 CXXFLAGS += -mwindows LDFLAGS += -mwindows resource = $(OBJDIR)/res.o $(resource): ipepresenter.rc $(WINDRES) -i ipepresenter.rc -o $@ --include-dir=. else resource = endif ifdef IPEUI_COCOA CXXFLAGS += $(IPEOBJCPP) nib = $(RESOURCEDIR)/mainmenu.nib $(nib): mainmenu.xib ibtool --compile $(nib) mainmenu.xib # libraries to link against are here buildlib = $(BUILDDIR)/Ipe.app/Contents/Frameworks else nib = endif $(TARGET): $(objects) $(resource) $(nib) $(MAKE_BINDIR) $(CXX) $(LDFLAGS) -o $@ $(objects) $(resource) $(LIBS) clean: @-rm -f $(objects) $(resource) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPEBINDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPEBINDIR) ifdef IPEUI_COCOA IPELIBS = $(BUILDDIR)/Ipe.app/Contents/Frameworks APPLIBS = $(BUILDDIR)/IpePresenter.app/Contents/Frameworks dll_symlinks = ln -sf lib$1.$(IPEVERS).dylib $(APPLIBS)/lib$1.dylib app: $(INSTALL_DIR) $(RESOURCEDIR) $(INSTALL_DIR) $(APPLIBS) $(INSTALL_FILES) Info.plist $(BUNDLEDIR) $(INSTALL_FILES) ../ipe/ipe.icns $(RESOURCEDIR) $(INSTALL_PROGRAMS) $(IPELIBS)/libipe.$(IPEVERS).dylib $(APPLIBS) $(INSTALL_PROGRAMS) $(IPELIBS)/libipecairo.$(IPEVERS).dylib $(APPLIBS) $(INSTALL_PROGRAMS) $(IPELIBS)/libipecanvas.$(IPEVERS).dylib $(APPLIBS) $(call dll_symlinks,ipe) $(call dll_symlinks,ipecairo) $(call dll_symlinks,ipecanvas) $(INSTALL_PROGRAMS) $(IPEDEPS)/lib/libpng16.16.dylib $(APPLIBS) $(INSTALL_PROGRAMS) $(IPEDEPS)/lib/libpixman-1.0.dylib $(APPLIBS) $(INSTALL_PROGRAMS) $(IPEDEPS)/lib/libfreetype.6.dylib $(APPLIBS) $(INSTALL_PROGRAMS) $(IPEDEPS)/lib/libcairo.2.dylib $(APPLIBS) endif # -------------------------------------------------------------------- ipe-7.2.13/src/ipepresenter/ipepresenter.h0000644000175000017500000000505013561570220020406 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // IpePresenter // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPRESENTER_H #define IPEPRESENTER_H #include "ipepdfview.h" using ipe::String; // -------------------------------------------------------------------- class Presenter { public: enum TAction { ELeftMouse, EOtherMouse, EOpen, EQuit, EShowPresentation, EFullScreen, EZoomIn, EZoomOut, ESetTime, EToggleTimeCounting, ETimeCountdown, EResetTime, ENextView, EPreviousView, EFirstView, ELastView, ENextPage, EPreviousPage, EJumpTo, ESelectPage, EAbout, }; public: void nextView(int delta); void nextPage(int delta); void firstView(); void lastView(); void fitBox(const ipe::Rect &box, ipe::PdfViewBase *view); bool load(const char* fn); void jumpToPage(String page); // use -1 for current and -2 for next ipe::Rect mediaBox(int pdfpno) const; protected: void collectAnnotations(); void makePageLabels(); void collectPageLabels(const ipe::PdfDict *d); void setViewPage(ipe::PdfViewBase *view, int pdfpno); String pageLabel(int pdfno); String currentLabel(); public: String iFileName; protected: std::unique_ptr iPdf; int iPdfPageNo; std::vector iAnnotations; std::vector> iPageLabels; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipepresenter/timelabel_qt.cpp0000644000175000017500000000502313561570220020676 0ustar otfriedotfried// -------------------------------------------------------------------- // timelabel.cpp // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "timelabel_qt.h" #include TimeLabel::TimeLabel(QWidget* parent): QLabel(parent), time(0,0,0), counting(false), countingDown(false) { timer = new QTimer(this); connect(timer, SIGNAL(timeout()), this, SLOT(countTime())); timer->start(1000); // one second } void TimeLabel::countTime() { if (!counting) return; if (countingDown && !(time.hour() == 0 && time.minute() == 0 && time.second() == 0)) time = time.addSecs(-1); if (!countingDown) time = time.addSecs(1); setText(time.toString("hh:mm:ss")); } void TimeLabel::mouseDoubleClickEvent(QMouseEvent* event) { setTime(); } void TimeLabel::setTime() { bool counting_state = counting; counting = false; bool ok; int minutes = QInputDialog::getInt(this, tr("Minutes"), tr("Minutes to count down:"), 0, 0, 10000, 1, &ok); if (ok && minutes >= 0) time.setHMS(minutes/60,minutes%60,0); counting = counting_state; setText(time.toString("hh:mm:ss")); } void TimeLabel::resetTime() { time.setHMS(0, 0, 0); setText(time.toString("hh:mm:ss")); } void TimeLabel::toggleCounting() { counting = !counting; } void TimeLabel::toggleCountdown() { countingDown = !countingDown; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipepresenter/ipepresenter.rc0000644000175000017500000000263613561570220020572 0ustar otfriedotfried#include #define IDI_MYICON 1 #define IDD_INPUTBOX 103 #define IDC_INPUTBOX_PROMPT 1000 #define IDC_INPUTBOX_EDIT 1001 #define IDC_STATIC -1 IDI_MYICON ICON DISCARDABLE "../ipe/ipe.ico" VS_VERSION_INFO VERSIONINFO FILEVERSION 7,2,13,1 PRODUCTVERSION 7,2,13,1 FILEFLAGSMASK VS_FF_PRERELEASE FILEFLAGS VS_FF_PRERELEASE FILEOS VOS__WINDOWS32 FILETYPE VFT_APP FILESUBTYPE 0x0L BEGIN BLOCK "StringFileInfo" BEGIN BLOCK "040904B0" BEGIN VALUE "CompanyName", "Otfried Cheong\0" VALUE "FileDescription", "Ipe presentation tool\0" VALUE "FileVersion", "7.2.13\0" VALUE "InternalName", "IpePresenter\0" VALUE "LegalCopyright", "Copyright (c) 2019\0" VALUE "OriginalFilename", "IpePresenter.exe\0" VALUE "ProductName", "IpePresenter\0" VALUE "ProductVersion", "7.2.13\0" END END END IDD_INPUTBOX DIALOGEX 22, 17, 220, 60 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_CAPTION | WS_SYSMENU CAPTION "IpePresenter" FONT 8, "MS Shell Dlg", 700, 0, 0x0 BEGIN LTEXT "Enter time in minutes:",IDC_INPUTBOX_PROMPT,6,4,157,14,SS_NOPREFIX EDITTEXT IDC_INPUTBOX_EDIT,6,20,200,14,ES_AUTOHSCROLL DEFPUSHBUTTON "Ok",IDOK,100,40,50,14,WS_GROUP PUSHBUTTON "Cancel",IDCANCEL,156,40,50,14,WS_GROUP END CREATEPROCESS_MANIFEST_RESOURCE_ID RT_MANIFEST "ipepresenter.exe.manifest" ipe-7.2.13/src/ipepresenter/Info.plist0000644000175000017500000000370413561570220017504 0ustar otfriedotfried CFBundleDocumentTypes CFBundleTypeName PDF document CFBundleTypeIconFile ipe.icns LSHandlerRank Alternate CFBundleTypeRole Viewer CFBundleTypeExtensions pdf PDF CFBundleTypeMIMETypes application/pdf CFBundleDevelopmentRegion English CFBundleExecutable ipepresenter CFBundleIconFile ipe CFBundleIdentifier org.otfried.ipe.IpePresenter CFBundleInfoDictionaryVersion 6.0 LSEnvironment PATH /Library/TeX/texbin:/usr/texbin:/usr/local/texbin:/usr/local/bin:/opt/local/bin:/usr/bin:/bin LSApplicationCategoryType public.app-category.graphics-design LSMinimumSystemVersion 10.10 NSPrincipalClass NSApplication NSMainNibFile mainmenu NSHighResolutionCapable True CFBundleName IpePresenter CFBundlePackageType APPL CFBundleShortVersionString 7.2.13 CFBundleSignature IpePresenter CFBundleVersion 7.2.13 NSHumanReadableCopyright Copyright © 1993-2019 Otfried Cheong ipe-7.2.13/src/ipecanvas/0000755000175000017500000000000013561570220014774 5ustar otfriedotfriedipe-7.2.13/src/ipecanvas/ipepdfview.h0000644000175000017500000000616213561570220017314 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPDFVIEW_H #define IPEPDFVIEW_H #include "ipelib.h" #include "ipepdfparser.h" // -------------------------------------------------------------------- // Avoid including cairo.h typedef struct _cairo cairo_t; typedef struct _cairo_surface cairo_surface_t; // -------------------------------------------------------------------- namespace ipe { class Fonts; class PdfFileResources; // -------------------------------------------------------------------- class PdfViewBase { public: virtual ~PdfViewBase(); void setPdf(const PdfFile *pdf); void setPage(const PdfDict *page, const Rect &paper); //! Return current pan. inline Vector pan() const { return iPan; } //! Return current zoom. inline double zoom() const { return iZoom; } //! Return center of view. inline Vector center() const { return 0.5 * Vector(iWidth, iHeight); } //! Return width of view. int viewWidth() const { return iWidth; } //! Return height of view. int viewHeight() const { return iHeight; } Vector devToUser(const Vector &arg) const; Vector userToDev(const Vector &arg) const; void setPan(const Vector &v); void setZoom(double zoom); Matrix canvasTfm() const; void updatePdf(); virtual void invalidate(int x, int y, int w, int h) = 0; virtual void invalidate() = 0; protected: PdfViewBase(); void drawPaper(cairo_t *cc); void refreshSurface(); protected: double iWidth, iHeight; double iBWidth, iBHeight; // size of backing store Vector iPan; double iZoom; bool iRepaint; cairo_surface_t *iSurface; std::unique_ptr iCascade; // dummy stylesheet const PdfDict *iPage; Rect iPaperBox; const PdfDict *iStream; const PdfFile *iPdf; std::unique_ptr iResources; std::unique_ptr iFonts; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipecanvas_qt.cpp0000644000175000017500000002367013561570220020165 0ustar otfriedotfried// -------------------------------------------------------------------- // ipe::Canvas for Qt // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipecanvas_qt.h" #include "ipepainter.h" #include "ipetool.h" #include #include #include using namespace ipe; // -------------------------------------------------------------------- class IpeQtPainter : public Painter { public: IpeQtPainter(const Cascade *sheet, QPainter *painter); virtual ~IpeQtPainter(); protected: virtual void doNewPath(); virtual void doMoveTo(const Vector &v); virtual void doLineTo(const Vector &v); virtual void doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3); virtual void doClosePath(); virtual void doDrawPath(TPathMode mode); private: QPainter *iQP; QPainterPath iPP; }; IpeQtPainter::IpeQtPainter(const Cascade *sheet, QPainter *painter) : Painter(sheet) { iQP = painter; } IpeQtPainter::~IpeQtPainter() { // nothing } void IpeQtPainter::doNewPath() { iPP = QPainterPath(); } void IpeQtPainter::doMoveTo(const Vector &v) { iPP.moveTo(QPt(v)); } void IpeQtPainter::doLineTo(const Vector &v) { iPP.lineTo(QPt(v)); } void IpeQtPainter::doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3) { iPP.cubicTo(QPt(v1), QPt(v2), QPt(v3)); } void IpeQtPainter::doClosePath() { iPP.closeSubpath(); } void IpeQtPainter::doDrawPath(TPathMode mode) { if (mode >= EStrokedAndFilled) { QBrush qbrush(QIpe(fill())); iQP->fillPath(iPP, qbrush); } if (mode <= EStrokedAndFilled) { QPen qpen(QIpe(stroke())); qpen.setWidthF(pen().toDouble()); iQP->strokePath(iPP, qpen); } } // -------------------------------------------------------------------- //! Construct a new canvas. #if QT_VERSION < 0x050000 Canvas::Canvas(QWidget* parent, Qt::WFlags f) #else Canvas::Canvas(QWidget* parent, Qt::WindowFlags f) #endif : QWidget(parent, f) { setAttribute(Qt::WA_NoBackground); setMouseTracking(true); setFocusPolicy(Qt::ClickFocus); } QSize Canvas::sizeHint() const { return QSize(640, 480); } void Canvas::setCursor(TCursor cursor, double w, Color *color) { switch (cursor) { case EStandardCursor: default: QWidget::unsetCursor(); break; case EHandCursor: QWidget::setCursor(QCursor(Qt::PointingHandCursor)); break; case ECrossCursor: QWidget::setCursor(QCursor(Qt::CrossCursor)); break; case EDotCursor: { QPixmap p(32, 32); p.fill(QColor(255, 255, 255, 0)); QPainter painter(&p); double s = 0.5 * w * zoom(); if (s < 1.0) s = 1.0; if (s > 10.0) s = 10.0; int r = 255 * color->iRed.internal() / 1000; int g = 255 * color->iGreen.internal() / 1000; int b = 255 * color->iBlue.internal() / 1000; painter.setBrush(QColor(r, g, b)); painter.setPen(Qt::NoPen); painter.drawEllipse(QRectF(16.0 - s, 16.0 - s, 2 * s, 2 * s)); painter.end(); QWidget::setCursor(QCursor(p)); } break; } } // -------------------------------------------------------------------- void Canvas::invalidate() { QWidget::update(); } void Canvas::invalidate(int x, int y, int w, int h) { QWidget::update(QRect(x, y, w, h)); } // -------------------------------------------------------------------- static int convertModifiers(int qmod) { int mod = 0; if (qmod & Qt::ShiftModifier) mod |= CanvasBase::EShift; if (qmod & Qt::ControlModifier) mod |= CanvasBase::EControl; if (qmod & Qt::AltModifier) mod |= CanvasBase::EAlt; if (qmod & Qt::MetaModifier) mod |= CanvasBase::EMeta; return mod; } void Canvas::keyPressEvent(QKeyEvent *ev) { if (iTool && iTool->key(IpeQ(ev->text()), (convertModifiers(ev->modifiers()) | iAdditionalModifiers))) ev->accept(); else ev->ignore(); } void Canvas::mouseButton(QMouseEvent *ev, int button, bool press) { iGlobalPos = Vector(ev->globalPos().x(), ev->globalPos().y()); computeFifi(ev->x(), ev->y()); int mod = convertModifiers(ev->modifiers()) | iAdditionalModifiers; if (iTool) iTool->mouseButton(button | mod, press); else if (press && iObserver) iObserver->canvasObserverMouseAction(button | mod); } void Canvas::mouseDoubleClickEvent(QMouseEvent *ev) { mouseButton(ev, 0x81, true); } void Canvas::mousePressEvent(QMouseEvent *ev) { mouseButton(ev, ev->button(), true); } void Canvas::mouseReleaseEvent(QMouseEvent *ev) { mouseButton(ev, ev->button(), false); } void Canvas::mouseMoveEvent(QMouseEvent *ev) { computeFifi(ev->x(), ev->y()); if (iTool) iTool->mouseMove(); if (iObserver) iObserver->canvasObserverPositionChanged(); } void Canvas::tabletEvent(QTabletEvent *ev) { #if QT_VERSION < 0x050000 Vector globalPos(ev->hiResGlobalPos().x(), ev->hiResGlobalPos().y()); QPointF hiPos = ev->hiResGlobalPos() - (ev->globalPos() - ev->pos()); #else Vector globalPos(ev->hiResGlobalX(), ev->hiResGlobalY()); QPointF hiPos = ev->posF(); #endif ev->accept(); switch (ev->type()) { case QEvent::TabletPress: ipeDebug("TabletPress: %d %d", ev->button(), ev->pointerType()); iGlobalPos = globalPos; computeFifi(hiPos.x(), hiPos.y()); if (ev->pointerType() == QTabletEvent::Eraser) { if (iObserver) iObserver->canvasObserverMouseAction(Qt::XButton1 | iAdditionalModifiers); } else if (iTool) iTool->mouseButton(ev->button() | iAdditionalModifiers, true); else if (iObserver) iObserver->canvasObserverMouseAction(ev->button() | iAdditionalModifiers); break; case QEvent::TabletMove: if (ev->pressure() > 0.01) { computeFifi(hiPos.x(), hiPos.y()); if (iTool) iTool->mouseMove(); if (iObserver) iObserver->canvasObserverPositionChanged(); break; } // else fall through and consider it a release event case QEvent::TabletRelease: iGlobalPos = globalPos; computeFifi(hiPos.x(), hiPos.y()); if (iTool) iTool->mouseButton(Qt::LeftButton, false); break; default: ipeDebug("Unknown tablet event"); break; } } void Canvas::wheelEvent(QWheelEvent *ev) { QPoint p = ev->angleDelta(); int kind = (ev->modifiers() & Qt::ControlModifier) ? 2 : 0; if (iObserver) iObserver->canvasObserverWheelMoved(p.x() / 8.0, p.y() / 8.0, kind); ev->accept(); } static void draw_plus(const Vector &p, QPainter &q) { q.drawLine(QPt(p - Vector(8, 0)), QPt(p + Vector(8, 0))); q.drawLine(QPt(p - Vector(0, 8)), QPt(p + Vector(0, 8))); } static void draw_rhombus(const Vector &p, QPainter &q) { QPainterPath path; path.moveTo(QPt(p - Vector(8, 0))); path.lineTo(QPt(p + Vector(0, 8))); path.lineTo(QPt(p + Vector(8, 0))); path.lineTo(QPt(p + Vector(0, -8))); path.closeSubpath(); q.drawPath(path); } static void draw_square(const Vector &p, QPainter &q) { QPainterPath path; path.moveTo(QPt(p + Vector(-7, -7))); path.lineTo(QPt(p + Vector(7, -7))); path.lineTo(QPt(p + Vector(7, 7))); path.lineTo(QPt(p + Vector(-7, 7))); path.closeSubpath(); q.drawPath(path); } static void draw_x(const Vector &p, QPainter &q) { q.drawLine(QPt(p - Vector(5.6, 5.6)), QPt(p + Vector(5.6, 5.6))); q.drawLine(QPt(p - Vector(5.6, -5.6)), QPt(p + Vector(5.6, -5.6))); } static void draw_star(const Vector &p, QPainter &q) { q.drawLine(QPt(p - Vector(8, 0)), QPt(p + Vector(8, 0))); q.drawLine(QPt(p + Vector(-4, 7)), QPt(p + Vector(4, -7))); q.drawLine(QPt(p + Vector(-4, -7)), QPt(p + Vector(4, 7))); } void Canvas::drawFifi(QPainter &q) { Vector p = userToDev(iMousePos); switch (iFifiMode) { case Snap::ESnapNone: // don't draw at all break; case Snap::ESnapVtx: q.setPen(QColor(255, 0, 0, 255)); draw_rhombus(p, q); break; case Snap::ESnapCtl: q.setPen(QColor(255, 0, 0, 255)); draw_square(p, q); break; break; case Snap::ESnapBd: q.setPen(QColor(255, 0, 0, 255)); draw_plus(p, q); break; case Snap::ESnapInt: q.setPen(QColor(255, 0, 0, 255)); draw_x(p, q); break; case Snap::ESnapGrid: q.setPen(QColor(0, 128, 0, 255)); draw_plus(p, q); break; case Snap::ESnapAngle: case Snap::ESnapAuto: default: q.setPen(QColor(255, 0, 0, 255)); draw_star(p, q); break; } iOldFifi = p; } void Canvas::paintEvent(QPaintEvent * ev) { iBWidth = iWidth = width(); iBHeight = iHeight = height(); refreshSurface(); QPainter qPainter; qPainter.begin(this); QRect r = ev->rect(); QRect source(r.left(), r.top(), r.width(), r.height()); QImage bits(cairo_image_surface_get_data(iSurface), iWidth, iHeight, QImage::Format_RGB32); qPainter.drawImage(r, bits, source); qPainter.translate(-1, -1); if (iFifiVisible) drawFifi(qPainter); if (iPage) { IpeQtPainter qp(iCascade, &qPainter); qp.transform(canvasTfm()); qp.pushMatrix(); drawTool(qp); qp.popMatrix(); } qPainter.end(); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipecanvas_gtk.h0000644000175000017500000000516413561570220017771 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::Canvas for GTK // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPECANVAS_GTK_H #define IPECANVAS_GTK_H // -------------------------------------------------------------------- #include "ipecanvas.h" #include namespace ipe { class Canvas : public CanvasBase { public: Canvas(GtkWidget *parent); ~Canvas(); GtkWidget *window() const { return GTK_WIDGET(iWindow); } private: virtual void setCursor(TCursor cursor, double w = 1.0, Color *color = 0); virtual void invalidate(); virtual void invalidate(int x, int y, int w, int h); #if GTK_MAJOR_VERSION >= 3 static gboolean expose_cb(GtkWidget *widget, cairo_t *cr, Canvas *canvas); void exposeHandler(cairo_t *cr); #else static gboolean expose_cb(GtkWidget *widget, GdkEvent *event, Canvas *canvas); void exposeHandler(GdkEventExpose *event); #endif void buttonHandler(GdkEventButton *event); void motionHandler(GdkEventMotion *event); void scrollHandler(GdkEventScroll *event); static gboolean button_cb(GtkWidget *widget, GdkEvent *event, Canvas *data); static gboolean motion_cb(GtkWidget *widget, GdkEvent *event, Canvas *canvas); static gboolean scroll_cb(GtkWidget *widget, GdkEvent *event, Canvas *canvas); private: GtkWidget *iWindow; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipepdfview.cpp0000644000175000017500000001260313561570220017644 0ustar otfriedotfried// -------------------------------------------------------------------- // ipe::PdfViewBase // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepdfview.h" #include "ipecairopainter.h" using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::PdfViewBase \ingroup canvas \brief A widget (control) that displays a PDF document. */ //! Construct a new canvas. PdfViewBase::PdfViewBase() { iSurface = nullptr; iPdf = nullptr; iPage = nullptr; iStream = nullptr; iPan = Vector::ZERO; iZoom = 1.0; iWidth = 0; // not yet known (view is not yet mapped) iHeight = 0; iBWidth = 0; iBHeight = 0; iRepaint = false; iCascade = std::make_unique(); iCascade->insert(0, StyleSheet::standard()); } //! destructor. PdfViewBase::~PdfViewBase() { if (iSurface) cairo_surface_destroy(iSurface); ipeDebug("PdfViewBase::~PdfViewBase"); } // -------------------------------------------------------------------- //! Provide the PDF document. void PdfViewBase::setPdf(const PdfFile *pdf) { iFonts.reset(); iPage = nullptr; iStream = nullptr; iPdf = pdf; iResources = std::make_unique(iPdf); iFonts = std::make_unique(iResources.get()); } //! Provide the page to view. void PdfViewBase::setPage(const PdfDict *page, const Rect &paper) { iPage = page; iPaperBox = paper; const PdfObj *stream = iPage->get("Contents", iPdf); iStream = stream ? stream->dict() : nullptr; } // -------------------------------------------------------------------- //! Set current pan position. /*! The pan position is the user coordinate that is displayed at the very center of the canvas. */ void PdfViewBase::setPan(const Vector &v) { iPan = v; } //! Set current zoom factor. /*! The zoom factor maps user coordinates to screen pixel coordinates. */ void PdfViewBase::setZoom(double zoom) { iZoom = zoom; } //! Convert canvas (device) coordinates to user coordinates. Vector PdfViewBase::devToUser(const Vector &arg) const { Vector v = arg - center(); v.x /= iZoom; v.y /= -iZoom; v += iPan; return v; } //! Convert user coordinates to canvas (device) coordinates. Vector PdfViewBase::userToDev(const Vector &arg) const { Vector v = arg - iPan; v.x *= iZoom; v.y *= -iZoom; v += center(); return v; } //! Matrix mapping user coordinates to canvas coordinates Matrix PdfViewBase::canvasTfm() const { return Matrix(center()) * Linear(iZoom, 0, 0, -iZoom) * Matrix(-iPan); } // -------------------------------------------------------------------- void PdfViewBase::drawPaper(cairo_t *cc) { if (!iPaperBox.isEmpty()) { cairo_rectangle(cc, iPaperBox.left(), iPaperBox.bottom(), iPaperBox.width(), iPaperBox.height()); cairo_set_source_rgb(cc, 1.0, 1.0, 1.0); cairo_fill(cc); } } // -------------------------------------------------------------------- //! Mark for update with redrawing of PDF document. void PdfViewBase::updatePdf() { iRepaint = true; invalidate(); } // -------------------------------------------------------------------- void PdfViewBase::refreshSurface() { if (!iSurface || iBWidth != cairo_image_surface_get_width(iSurface) || iBHeight != cairo_image_surface_get_height(iSurface)) { // size has changed // ipeDebug("size has changed to %g x %g (%g x %g)", // iWidth, iHeight, iBWidth, iBHeight); if (iSurface) cairo_surface_destroy(iSurface); iSurface = nullptr; iRepaint = true; } if (iRepaint) { iRepaint = false; if (!iSurface) iSurface = cairo_image_surface_create(CAIRO_FORMAT_RGB24, iBWidth, iBHeight); cairo_t *cc = cairo_create(iSurface); // background cairo_set_source_rgb(cc, 0.4, 0.4, 0.4); cairo_rectangle(cc, 0, 0, iBWidth, iBHeight); cairo_fill(cc); cairo_translate(cc, 0.5 * iBWidth, 0.5 * iBHeight); cairo_scale(cc, iBWidth / iWidth, iBHeight / iHeight); cairo_scale(cc, iZoom, -iZoom); cairo_translate(cc, -iPan.x, -iPan.y); drawPaper(cc); if (iStream) { CairoPainter painter(iCascade.get(), iFonts.get(), cc, iZoom, false); painter.executeStream(iStream, iPage); } cairo_surface_flush(iSurface); cairo_destroy(cc); } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipecanvas_qt.h0000644000175000017500000000617713561570220017635 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::Canvas for QT // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPECANVAS_QT_H #define IPECANVAS_QT_H #include "ipecanvas.h" #include // -------------------------------------------------------------------- namespace ipe { inline QPointF QPt(const Vector &v) { return QPointF(v.x, v.y); } inline String IpeQ(const QString &str) { return String(str.toUtf8()); } inline QString QIpe(const String &str) { return QString::fromUtf8(str.z()); } inline QColor QIpe(Color color) { return QColor(int(color.iRed.toDouble() * 255 + 0.5), int(color.iGreen.toDouble() * 255 + 0.5), int(color.iBlue.toDouble() * 255 + 0.5)); } inline Color IpeQ(QColor color) { return Color(color.red() * 1000 / 255, color.green() * 1000 / 255, color.blue() * 1000 / 255); } // -------------------------------------------------------------------- class Canvas : public QWidget, public CanvasBase { Q_OBJECT public: #if QT_VERSION < 0x050000 Canvas(QWidget* parent, Qt::WFlags f=0); #else Canvas(QWidget* parent, Qt::WindowFlags f=nullptr); #endif virtual void setCursor(TCursor cursor, double w = 1.0, Color *color = nullptr); protected: virtual void invalidate(); virtual void invalidate(int x, int y, int w, int h); void drawFifi(QPainter &q); protected: virtual void paintEvent(QPaintEvent *ev); void mouseButton(QMouseEvent *ev, int button, bool press); virtual void mouseDoubleClickEvent(QMouseEvent *ev); virtual void mousePressEvent(QMouseEvent *ev) ; virtual void mouseReleaseEvent(QMouseEvent *ev); virtual void mouseMoveEvent(QMouseEvent *ev); virtual void tabletEvent(QTabletEvent *ev); virtual void wheelEvent(QWheelEvent *ev); virtual void keyPressEvent(QKeyEvent *ev); virtual QSize sizeHint() const; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipepdfview_win.h0000644000175000017500000000420513561570220020165 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::PdfView for Win32 // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPDFVIEWWIN_H #define IPEPDFVIEWWIN_H // -------------------------------------------------------------------- #include "ipepdfview.h" #include namespace ipe { class PdfView : public PdfViewBase { public: static constexpr int WM_PDFVIEW = 0x8000; static void init(HINSTANCE hInstance); PdfView(HWND parent, HWND target, HINSTANCE hInstance = nullptr); HWND windowId() const { return hwnd; } private: void wndPaint(); void updateSize(); virtual void invalidate(); virtual void invalidate(int x, int y, int w, int h); private: static const wchar_t className[]; static LRESULT CALLBACK wndProc(HWND hwnd, UINT Message, WPARAM wParam, LPARAM lParam); private: HWND hwnd; HWND target; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipeselector_cocoa.h0000644000175000017500000000426213561570220020633 0ustar otfriedotfried// -*- objc -*- // ipeselector_cocoa.h /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPESELECTOR_COCOA_H #define IPESELECTOR_COCOA_H #include "ipedoc.h" #include "ipethumbs.h" #include // -------------------------------------------------------------------- @interface IpeSelectorProvider : NSObject @property NSMutableArray *images; @property ipe::Document *doc; @property ipe::Thumbnail *thumb; @property int page; @property NSSize tnSize; - (int) count; - (NSString *) title:(int) index; - (NSImage *) image:(int) index; - (ipe::Buffer) renderImage:(int) index; - (NSImage *) createImage:(ipe::Buffer) b; @end @interface IpeSelectorItem : NSObject @property int index; @property (assign) IpeSelectorProvider *provider; @end @interface IpeSelectorView : NSView @property (assign) NSButton *button; - (void) ipeSet:(IpeSelectorItem *) item; @end @interface IpeSelectorPrototype : NSCollectionViewItem @end extern int showPageSelectDialog(int width, int height, const char * title, IpeSelectorProvider *provider, int startIndex); // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipecanvas_gtk.cpp0000644000175000017500000001355213561570220020324 0ustar otfriedotfried// -------------------------------------------------------------------- // ipe::Canvas for GTK // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipecanvas_gtk.h" #include "ipecairopainter.h" #include "ipetool.h" #include using namespace ipe; // -------------------------------------------------------------------- void Canvas::invalidate() { GdkRectangle r; r.x = r.y = 0; #if GTK_MAJOR_VERSION >= 3 r.width = gtk_widget_get_allocated_width(iWindow); r.height = gtk_widget_get_allocated_height(iWindow); #else r.width = iWindow->allocation.width; r.height = iWindow->allocation.height; #endif gdk_window_invalidate_rect(gtk_widget_get_window(iWindow), &r, FALSE); } void Canvas::invalidate(int x, int y, int w, int h) { GdkRectangle r; r.x = x; r.y = y; r.width = w; r.height = h; gdk_window_invalidate_rect(gtk_widget_get_window(iWindow), &r, FALSE); } // -------------------------------------------------------------------- void Canvas::buttonHandler(GdkEventButton *ev) { // ipeDebug("Canvas::button %d %d %g %g", ev->button, ev->type, ev->x, ev->y); iGlobalPos = Vector(ev->x_root, ev->y_root); computeFifi(ev->x, ev->y); // TODO: int mod = getModifiers() | iAdditionalModifiers; int mod = iAdditionalModifiers; bool down = (ev->type == GDK_BUTTON_PRESS); if (iTool) iTool->mouseButton(ev->button | mod, down); else if (down && iObserver) iObserver->canvasObserverMouseAction(ev->button | mod); } void Canvas::motionHandler(GdkEventMotion *event) { // ipeDebug("Canvas::mouseMove %g %g", event->x, event->y); computeFifi(event->x, event->y); if (iTool) iTool->mouseMove(); if (iObserver) iObserver->canvasObserverPositionChanged(); } void Canvas::scrollHandler(GdkEventScroll *event) { int zDelta = (event->direction == GDK_SCROLL_UP) ? 120 : -120; // ipeDebug("Canvas::wheel %d", zDelta); if (iObserver) iObserver->canvasObserverWheelMoved(zDelta); } #if GTK_MAJOR_VERSION >= 3 void Canvas::exposeHandler(cairo_t *cr) { iWidth = gtk_widget_get_allocated_width(iWindow); iHeight = gtk_widget_get_allocated_height(iWindow); #else void Canvas::exposeHandler(GdkEventExpose *event) { iWidth = iWindow->allocation.width; iHeight = iWindow->allocation.height; #endif refreshSurface(); #if GTK_MAJOR_VERSION < 3 cairo_t *cr = gdk_cairo_create(iWindow->window); cairo_rectangle(cr, event->area.x, event->area.y, event->area.width, event->area.height); cairo_clip(cr); #endif cairo_set_source_surface(cr, iSurface, 0.0, 0.0); cairo_paint(cr); if (iFifiVisible) drawFifi(cr); if (iPage) { CairoPainter cp(iCascade, iFonts, cr, iZoom, false); cp.transform(canvasTfm()); cp.pushMatrix(); drawTool(cp); cp.popMatrix(); } #if GTK_MAJOR_VERSION < 3 cairo_destroy(cr); #endif } // -------------------------------------------------------------------- gboolean Canvas::button_cb(GtkWidget *widget, GdkEvent *event, Canvas *canvas) { canvas->buttonHandler((GdkEventButton *) event); return TRUE; } #if GTK_MAJOR_VERSION < 3 gboolean Canvas::expose_cb(GtkWidget *widget, GdkEvent *event, Canvas *canvas) { canvas->exposeHandler((GdkEventExpose *) event); return TRUE; } #else gboolean Canvas::expose_cb(GtkWidget *widget, cairo_t *cr, Canvas *canvas) { canvas->exposeHandler(cr); return TRUE; } #endif gboolean Canvas::motion_cb(GtkWidget *widget, GdkEvent *event, Canvas *canvas) { canvas->motionHandler((GdkEventMotion *) event); return TRUE; } gboolean Canvas::scroll_cb(GtkWidget *widget, GdkEvent *event, Canvas *canvas) { canvas->scrollHandler((GdkEventScroll *) event); return TRUE; } void Canvas::setCursor(TCursor cursor, double w, Color *color) { // TODO } // -------------------------------------------------------------------- Canvas::Canvas(GtkWidget *parent) { iWindow = gtk_drawing_area_new(); gtk_widget_add_events(iWindow, GDK_BUTTON_PRESS_MASK| GDK_BUTTON_RELEASE_MASK| GDK_POINTER_MOTION_MASK); gtk_widget_set_size_request(iWindow, 600, 400); gtk_widget_set_can_focus(iWindow, TRUE); g_signal_connect(G_OBJECT(iWindow), "button-release-event", G_CALLBACK(button_cb), this); g_signal_connect(G_OBJECT(iWindow), "button-press-event", G_CALLBACK(button_cb), this); #if GTK_MAJOR_VERSION < 3 g_signal_connect(G_OBJECT(iWindow), "expose-event", G_CALLBACK(expose_cb), this); #else g_signal_connect(G_OBJECT(iWindow), "draw", G_CALLBACK(expose_cb), this); #endif g_signal_connect(G_OBJECT(iWindow), "motion-notify-event", G_CALLBACK(motion_cb), this); g_signal_connect(G_OBJECT(iWindow), "scroll-event", G_CALLBACK(scroll_cb), this); } Canvas::~Canvas() { // do I need to delete the GTK Window? It is owned by its parent. } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipecanvas.cpp0000644000175000017500000004576113561570220017466 0ustar otfriedotfried// -------------------------------------------------------------------- // ipe::Canvas // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipecanvas.h" #include "ipetool.h" #include "ipecairopainter.h" using namespace ipe; // -------------------------------------------------------------------- /*! \defgroup canvas Ipe canvas \brief A widget (control) that displays an Ipe document page. This module contains the classes needed to display and edit Ipe objects using the selected toolkit. These classes are not in Ipelib, but in a separate library libipecanvas. */ // -------------------------------------------------------------------- CanvasObserver::~CanvasObserver() { /* nothing */ } void CanvasObserver::canvasObserverWheelMoved(double xDegrees, double yDegrees, int kind) { /* nothing */ } void CanvasObserver::canvasObserverMouseAction(int button) { /* nothing */ } void CanvasObserver::canvasObserverPositionChanged() { /* nothing */ } void CanvasObserver::canvasObserverToolChanged(bool hasTool) { /* nothing */ } void CanvasObserver::canvasObserverSizeChanged() { /* nothing */ } /*! \class ipe::Canvas \ingroup canvas \brief A widget (control) that displays an Ipe document page. */ //! Construct a new canvas. CanvasBase::CanvasBase() { iObserver = nullptr; iTool = nullptr; iPage = nullptr; iCascade = nullptr; iSurface = nullptr; iPan = Vector::ZERO; iZoom = 1.0; iDimmed = false; iWidth = 0; // not yet known (canvas is not yet mapped) iHeight = 0; iBWidth = 0; iBHeight = 0; iRepaintObjects = false; iResources = nullptr; iAutoSnap = false; iFifiVisible = false; iFifiMode = Snap::ESnapNone; iSelectionVisible = true; isInkMode = false; iAdditionalModifiers = 0; iStyle.paperColor = Color(1000,1000,1000); iStyle.primarySelectionColor = Color(1000, 0, 0); iStyle.secondarySelectionColor= Color(1000, 0, 1000); iStyle.pretty = false; iStyle.classicGrid = false; iStyle.thinLine = 0.2; iStyle.thickLine = 0.9; iStyle.thinStep = 1; iStyle.thickStep = 4; iStyle.paperClip = false; iStyle.numberPages = false; iSnap.iSnap = 0; iSnap.iGridVisible = false; iSnap.iGridSize = 8; iSnap.iAngleSize = IPE_PI / 6.0; iSnap.iSnapDistance = 10; iSnap.iWithAxes = false; iSnap.iOrigin = Vector::ZERO; iSnap.iDir = 0; } //! destructor. CanvasBase::~CanvasBase() { if (iSurface) cairo_surface_destroy(iSurface); delete iTool; ipeDebug("CanvasBase::~CanvasBase"); } // -------------------------------------------------------------------- //! set information about Latex fonts (from ipe::Document) void CanvasBase::setResources(const PdfResources *resources) { iFonts.reset(); iResources = resources; iFonts = std::make_unique(resources); } // -------------------------------------------------------------------- //! Set the page to be displayed. /*! Doesn't take ownership of any argument. The page number \a pno is only needed if page numbering is turned on. */ void CanvasBase::setPage(const Page *page, int pno, int view, const Cascade *sheet) { iPage = page; iPageNumber = pno; iView = view; iCascade = sheet; } //! Set style of canvas drawing. /*! Includes paper color, pretty text, and grid. */ void CanvasBase::setCanvasStyle(const Style &style) { iStyle = style; } //! Set current pan position. /*! The pan position is the user coordinate that is displayed at the very center of the canvas. */ void CanvasBase::setPan(const Vector &v) { iPan = v; } //! Set current zoom factor. /*! The zoom factor maps user coordinates to screen pixel coordinates. */ void CanvasBase::setZoom(double zoom) { iZoom = zoom; } //! Set the snapping information. void CanvasBase::setSnap(const Snap &s) { iSnap = s; } //! Dim whole canvas, except for the Tool. /*! This mode will be reset when the Tool finishes. */ void CanvasBase::setDimmed(bool dimmed) { iDimmed = dimmed; } //! Set additional modifiers. /*! These modifier bits are passed to the Tool when a key is pressed or a drawing action is performed in addition to the actual keyboard modifiers. */ void CanvasBase::setAdditionalModifiers(int mod) { iAdditionalModifiers = mod; } //! Enable automatic angular snapping with this origin. void CanvasBase::setAutoOrigin(const Vector &v) { iAutoOrigin = v; iAutoSnap = true; } //! Convert canvas (device) coordinates to user coordinates. Vector CanvasBase::devToUser(const Vector &arg) const { Vector v = arg - center(); v.x /= iZoom; v.y /= -iZoom; v += iPan; return v; } //! Convert user coordinates to canvas (device) coordinates. Vector CanvasBase::userToDev(const Vector &arg) const { Vector v = arg - iPan; v.x *= iZoom; v.y *= -iZoom; v += center(); return v; } //! Matrix mapping user coordinates to canvas coordinates Matrix CanvasBase::canvasTfm() const { return Matrix(center()) * Linear(iZoom, 0, 0, -iZoom) * Matrix(-iPan); } // -------------------------------------------------------------------- void CanvasBase::drawAxes(cairo_t *cc) { double alpha = 0.0; double ep = (iWidth + iHeight) / iZoom; cairo_save(cc); cairo_set_source_rgb(cc, 0.0, 1.0, 0.0); cairo_set_line_width(cc, 2.0 / iZoom); while (alpha < IpeTwoPi) { double beta = iSnap.iDir + alpha; cairo_move_to(cc, iSnap.iOrigin.x, iSnap.iOrigin.y); Vector dir(beta); cairo_rel_line_to(cc, ep * dir.x, ep * dir.y); if (alpha == 0.0) { cairo_stroke(cc); cairo_set_line_width(cc, 1.0 / iZoom); } alpha += iSnap.iAngleSize; } cairo_stroke(cc); cairo_restore(cc); } void CanvasBase::drawGrid(cairo_t *cc) { int step = iSnap.iGridSize * iStyle.thinStep; double pixstep = step * iZoom; if (pixstep < 3.0) return; // Rect paper = iCascade->findLayout()->paper(); // Vector ll = paper.bottomLeft(); // Vector ur = paper.topRight(); Vector ll = Vector::ZERO; Vector ur = iCascade->findLayout()->iFrameSize; int left = step * int(ll.x / step); if (left < ll.x) ++left; int bottom = step * int(ll.y / step); if (bottom < ll.y) ++bottom; // only draw lines that intersect canvas Vector screenUL = devToUser(Vector::ZERO); Vector screenLR = devToUser(Vector(iWidth, iHeight)); cairo_save(cc); cairo_set_source_rgb(cc, 0.3, 0.3, 0.3); if (iStyle.classicGrid) { double lw = iStyle.thinLine / iZoom; cairo_set_line_width(cc, lw); for (int y = bottom; y < ur.y; y += step) { if (screenLR.y <= y && y <= screenUL.y) { for (int x = left; x < ur.x; x += step) { if (screenUL.x <= x && x <= screenLR.x) { cairo_move_to(cc, x, y - 0.5 * lw); cairo_line_to(cc, x, y + 0.5 * lw); cairo_stroke(cc); } } } } } else { double thinLine = iStyle.thinLine / iZoom; double thickLine = iStyle.thickLine / iZoom; int thickStep = iStyle.thickStep * step; // draw horizontal lines for (int y = bottom; y < ur.y; y += step) { if (screenLR.y <= y && y <= screenUL.y) { cairo_set_line_width(cc, (y % thickStep) ? thinLine : thickLine); cairo_move_to(cc, ll.x, y); cairo_line_to(cc, ur.x, y); cairo_stroke(cc); } } // draw vertical lines for (int x = left; x < ur.x; x += step) { if (screenUL.x <= x && x <= screenLR.x) { cairo_set_line_width(cc, (x % thickStep) ? thinLine : thickLine); cairo_move_to(cc, x, ll.y); cairo_line_to(cc, x, ur.y); cairo_stroke(cc); } } } cairo_restore(cc); } void CanvasBase::drawPaper(cairo_t *cc) { const Layout *l = iCascade->findLayout(); cairo_rectangle(cc, -l->iOrigin.x, -l->iOrigin.y, l->iPaperSize.x, l->iPaperSize.y); cairo_set_source_rgb(cc, iStyle.paperColor.iRed.toDouble(), iStyle.paperColor.iGreen.toDouble(), iStyle.paperColor.iBlue.toDouble()); cairo_fill(cc); } void CanvasBase::drawFrame(cairo_t *cc) { const Layout *l = iCascade->findLayout(); cairo_set_source_rgb(cc, 0.5, 0.5, 0.5); cairo_save(cc); double dashes[2] = {3.0 / iZoom, 7.0 / iZoom}; cairo_set_dash(cc, dashes, 2, 0.0); cairo_set_line_width(cc, 2.5 / iZoom); cairo_move_to(cc, 0.0, 0.0); cairo_line_to(cc, 0.0, l->iFrameSize.y); cairo_line_to(cc, l->iFrameSize.x, l->iFrameSize.y); cairo_line_to(cc, l->iFrameSize.x, 0); cairo_close_path(cc); cairo_stroke(cc); cairo_restore(cc); } void CanvasBase::drawObjects(cairo_t *cc) { if (!iPage) return; if (iStyle.paperClip) { const Layout *l = iCascade->findLayout(); cairo_rectangle(cc, -l->iOrigin.x, -l->iOrigin.y, l->iPaperSize.x, l->iPaperSize.y); cairo_clip(cc); } CairoPainter painter(iCascade, iFonts.get(), cc, iZoom, iStyle.pretty); painter.setDimmed(iDimmed); // painter.Transform(CanvasTfm()); painter.pushMatrix(); const Symbol *background = iCascade->findSymbol(Attribute::BACKGROUND()); if (background && iPage->findLayer("BACKGROUND") < 0) background->iObject->draw(painter); if (iResources && iStyle.numberPages) { const Text *pn = iResources->pageNumber(iPageNumber, iView); if (pn) pn->draw(painter); } const Text *title = iPage->titleText(); if (title) title->draw(painter); for (int i = 0; i < iPage->count(); ++i) { if (iPage->objectVisible(iView, i)) iPage->object(i)->draw(painter); } painter.popMatrix(); } // -------------------------------------------------------------------- static void draw_plus(const Vector &p, cairo_t *cr) { cairo_move_to(cr, p.x - 8, p.y); cairo_line_to(cr, p.x + 8, p.y); cairo_move_to(cr, p.x, p.y - 8); cairo_line_to(cr, p.x, p.y + 8); cairo_stroke(cr); } static void draw_rhombus(const Vector &p, cairo_t *cr) { cairo_move_to(cr, p.x - 8, p.y); cairo_line_to(cr, p.x, p.y + 8); cairo_line_to(cr, p.x + 8, p.y); cairo_line_to(cr, p.x, p.y - 8); cairo_close_path(cr); cairo_stroke(cr); } static void draw_square(const Vector &p, cairo_t *cr) { cairo_move_to(cr, p.x - 7, p.y - 7); cairo_line_to(cr, p.x + 7, p.y - 7); cairo_line_to(cr, p.x + 7, p.y + 7); cairo_line_to(cr, p.x - 7, p.y + 7); cairo_close_path(cr); cairo_stroke(cr); } static void draw_x(const Vector &p, cairo_t *cr) { cairo_move_to(cr, p.x - 5.6, p.y - 5.6); cairo_line_to(cr, p.x + 5.6, p.y + 5.6); cairo_move_to(cr, p.x - 5.6, p.y + 5.6); cairo_line_to(cr, p.x + 5.6, p.y - 5.6); cairo_stroke(cr); } static void draw_star(const Vector &p, cairo_t *cr) { cairo_move_to(cr, p.x - 8, p.y); cairo_line_to(cr, p.x + 8, p.y); cairo_move_to(cr, p.x - 4, p.y + 7); cairo_line_to(cr, p.x + 4, p.y - 7); cairo_move_to(cr, p.x - 4, p.y - 7); cairo_line_to(cr, p.x + 4, p.y + 7); cairo_stroke(cr); } void CanvasBase::drawFifi(cairo_t *cr) { Vector p = userToDev(iMousePos); switch (iFifiMode) { case Snap::ESnapNone: // don't draw at all break; case Snap::ESnapVtx: cairo_set_source_rgb(cr, 1.0, 0.0, 0.0); draw_rhombus(p, cr); break; case Snap::ESnapCtl: cairo_set_source_rgb(cr, 1.0, 0.0, 0.0); draw_square(p, cr); break; case Snap::ESnapBd: cairo_set_source_rgb(cr, 1.0, 0.0, 0.0); draw_plus(p, cr); break; case Snap::ESnapInt: cairo_set_source_rgb(cr, 1.0, 0.0, 0.0); draw_x(p, cr); break; case Snap::ESnapGrid: cairo_set_source_rgb(cr, 0.0, 0.5, 0.0); draw_plus(p, cr); break; case Snap::ESnapAngle: case Snap::ESnapAuto: default: cairo_set_source_rgb(cr, 1.0, 0.0, 0.0); draw_star(p, cr); break; } iOldFifi = p; } // -------------------------------------------------------------------- //! Draw the current canvas tool. /*! If no tool is set, it draws the selected objects. */ void CanvasBase::drawTool(Painter &painter) { if (iTool) { iTool->draw(painter); } else if (iSelectionVisible) { for (int i = 0; i < iPage->count(); ++i) { if (iPage->objectVisible(iView, i)) { if (iPage->select(i) == EPrimarySelected) { painter.setStroke(Attribute(iStyle.primarySelectionColor)); painter.setPen(Attribute(Fixed(2))); iPage->object(i)->drawSimple(painter); } else if (iPage->select(i) == ESecondarySelected) { painter.setStroke(Attribute(iStyle.secondarySelectionColor)); painter.setPen(Attribute(Fixed(1))); iPage->object(i)->drawSimple(painter); } } } } } //! Set an observer. /*! Use 0 to delete current observer. */ void CanvasBase::setObserver(CanvasObserver *observer) { iObserver = observer; } //! Set a new tool. /*! Calls canvasObserverToolChanged(). */ void CanvasBase::setTool(Tool *tool) { assert(tool); iTool = tool; updateTool(); if (iObserver) iObserver->canvasObserverToolChanged(true); } // Current tool has done its job. /* Tool is deleted, canvas fully updated, and cursor reset. Calls canvasObserverToolChanged(). */ void CanvasBase::finishTool() { delete iTool; iTool = nullptr; iDimmed = false; iAutoSnap = false; update(); if (iSelectionVisible) setCursor(EStandardCursor); if (iObserver) iObserver->canvasObserverToolChanged(false); } // -------------------------------------------------------------------- void CanvasBase::snapToPaperAndFrame() { double snapDist = iSnap.iSnapDistance / iZoom; double d = snapDist; Vector fifi = iMousePos; const Layout *layout = iCascade->findLayout(); Rect paper = layout->paper(); Rect frame(Vector::ZERO, layout->iFrameSize); // vertices if (iSnap.iSnap & Snap::ESnapVtx) { paper.bottomLeft().snap(iMousePos, fifi, d); paper.topRight().snap(iMousePos, fifi, d); paper.topLeft().snap(iMousePos, fifi, d); paper.bottomRight().snap(iMousePos, fifi, d); frame.bottomLeft().snap(iMousePos, fifi, d); frame.topRight().snap(iMousePos, fifi, d); frame.topLeft().snap(iMousePos, fifi, d); frame.bottomRight().snap(iMousePos, fifi, d); } // Return if snapping has occurred if (d < snapDist) { iMousePos = fifi; iFifiMode = Snap::ESnapVtx; return; } // boundary if (iSnap.iSnap & Snap::ESnapBd) { Segment(paper.bottomLeft(), paper.bottomRight()).snap(iMousePos, fifi, d); Segment(paper.bottomRight(), paper.topRight()).snap(iMousePos, fifi, d); Segment(paper.topRight(), paper.topLeft()).snap(iMousePos, fifi, d); Segment(paper.topLeft(), paper.bottomLeft()).snap(iMousePos, fifi, d); Segment(frame.bottomLeft(), frame.bottomRight()).snap(iMousePos, fifi, d); Segment(frame.bottomRight(), frame.topRight()).snap(iMousePos, fifi, d); Segment(frame.topRight(), frame.topLeft()).snap(iMousePos, fifi, d); Segment(frame.topLeft(), frame.bottomLeft()).snap(iMousePos, fifi, d); } if (d < snapDist) { iMousePos = fifi; iFifiMode = Snap::ESnapBd; } } // -------------------------------------------------------------------- //! Set whether Fifi should be shown. /*! Fifi will only be shown if a snapping mode is active. */ void CanvasBase::setFifiVisible(bool visible) { iFifiVisible = visible; if (!visible) updateTool(); // when making visible, wait for position update } //! Set whether selection should be shown when there is no tool. void CanvasBase::setSelectionVisible(bool visible) { iSelectionVisible = visible; updateTool(); } //! Return snapped mouse position without angular snapping. Vector CanvasBase::simpleSnapPos() const { Vector pos = iUnsnappedMousePos; iSnap.simpleSnap(pos, iPage, iView, iSnap.iSnapDistance / iZoom); return pos; } // -------------------------------------------------------------------- //! Mark for update with redrawing of objects. void CanvasBase::update() { iRepaintObjects = true; invalidate(); } //! Mark for update with redrawing of tool only. void CanvasBase::updateTool() { invalidate(); } // -------------------------------------------------------------------- /*! Stores the mouse position in iUnsnappedMousePos, computes Fifi if snapping is enabled, and stores snapped position in iMousePos. */ void CanvasBase::computeFifi(double x, double y) { iUnsnappedMousePos = devToUser(Vector(x, y)); iMousePos = iUnsnappedMousePos; if (!iPage) return; int mask = iAutoSnap ? 0 : Snap::ESnapAuto; if (iSnap.iSnap & ~mask) { iFifiMode = iSnap.snap(iMousePos, iPage, iView, iSnap.iSnapDistance / iZoom, iTool, (iAutoSnap ? &iAutoOrigin : nullptr)); if (iFifiMode == Snap::ESnapNone) snapToPaperAndFrame(); // convert fifi coordinates back into device space Vector fifi = userToDev(iMousePos); if (iFifiVisible && fifi != iOldFifi) { invalidate(int(iOldFifi.x - 10), int(iOldFifi.y - 10), 21, 21); invalidate(int(fifi.x - 10), int(fifi.y - 10), 21, 21); } } else if (iFifiVisible) { // remove old fifi invalidate(int(iOldFifi.x - 10), int(iOldFifi.y - 10), 21, 21); iFifiVisible = false; } } // -------------------------------------------------------------------- void CanvasBase::refreshSurface() { if (!iSurface || iBWidth != cairo_image_surface_get_width(iSurface) || iBHeight != cairo_image_surface_get_height(iSurface)) { // size has changed ipeDebug("size has changed to %g x %g (%g x %g)", iWidth, iHeight, iBWidth, iBHeight); if (iSurface) cairo_surface_destroy(iSurface); iSurface = nullptr; iRepaintObjects = true; // give Ipe a chance to set pan and zoom according to new size if (iObserver) iObserver->canvasObserverSizeChanged(); } if (iRepaintObjects) { iRepaintObjects = false; if (!iSurface) iSurface = cairo_image_surface_create(CAIRO_FORMAT_RGB24, iBWidth, iBHeight); cairo_t *cc = cairo_create(iSurface); // background cairo_set_source_rgb(cc, 0.4, 0.4, 0.4); cairo_rectangle(cc, 0, 0, iBWidth, iBHeight); cairo_fill(cc); cairo_translate(cc, 0.5 * iBWidth, 0.5 * iBHeight); cairo_scale(cc, iBWidth / iWidth, iBHeight / iHeight); cairo_scale(cc, iZoom, -iZoom); cairo_translate(cc, -iPan.x, -iPan.y); if (iPage) { drawPaper(cc); if (!iStyle.pretty) drawFrame(cc); if (iSnap.iGridVisible) drawGrid(cc); drawObjects(cc); if (iSnap.iWithAxes) drawAxes(cc); } cairo_surface_flush(iSurface); cairo_destroy(cc); } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipeselector_qt.cpp0000644000175000017500000001262613561570220020531 0ustar otfriedotfried// -------------------------------------------------------------------- // PageSelector for QT // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeselector_qt.h" #include "ipethumbs.h" #include "ipecanvas.h" #include #include using namespace ipe; // -------------------------------------------------------------------- /*! \class ipe::PageSelector \ingroup canvas \brief A Qt widget that displays a list of Ipe pages. */ //! Construct the widget. /*! If \a page is negative, the last view of each page is shown. Otherwise, all views of this page are shown. \a itemWidth is the width of the page thumbnails (the height is computed automatically). */ PageSelector::PageSelector(QWidget *parent) : QListWidget(parent) { setViewMode(QListView::IconMode); setSelectionMode(QAbstractItemView::SingleSelection); setResizeMode(QListView::Adjust); setWrapping(true); setUniformItemSizes(true); setFlow(QListView::LeftToRight); setSpacing(10); setMovement(QListView::Static); connect(this, SIGNAL(itemActivated(QListWidgetItem *)), SLOT(pageSelected(QListWidgetItem *))); } void PageSelector::pageSelected(QListWidgetItem *item) { emit selectionMade(); } void PageSelector::fill(std::vector &icons, std::vector &labels) { int maxWidth = 0; int maxHeight = 0; for (const auto & icon : icons) { if (icon.width() > maxWidth) maxWidth = icon.width(); if (icon.height() > maxHeight) maxHeight = icon.height(); } setGridSize(QSize(maxWidth + 10, maxHeight + 50)); setIconSize(QSize(maxWidth, maxHeight)); for (size_t i = 0; i < icons.size(); ++i) { QString s = QString::fromUtf8(labels[i].z()); QListWidgetItem *item = new QListWidgetItem(QIcon(icons[i]), s); item->setFlags(Qt::ItemIsSelectable|Qt::ItemIsEnabled); item->setToolTip(s); addItem(item); } } // -------------------------------------------------------------------- static void fillWithPages(PageSelector *sel, Document *doc, int page, int itemWidth) { Thumbnail r(doc, itemWidth); std::vector icons; std::vector labels; if (page >= 0) { Page *p = doc->page(page); for (int i = 0; i < p->countViews(); ++i) { Buffer b = r.render(p, i); QImage bits((const uchar *) b.data(), itemWidth, r.height(), QImage::Format_RGB32); // need to copy bits since buffer b is temporary icons.push_back(QPixmap::fromImage(bits.copy())); String s; StringStream ss(s); if (!p->viewName(i).empty()) ss << i+1 << ": " << p->viewName(i); else ss << "View " << i+1; labels.push_back(s); } } else { for (int i = 0; i < doc->countPages(); ++i) { Page *p = doc->page(i); Buffer b = r.render(p, p->countViews() - 1); QImage bits((const uchar *) b.data(), itemWidth, r.height(), QImage::Format_RGB32); // need to copy bits since buffer b is temporary icons.push_back(QPixmap::fromImage(bits.copy())); String s; StringStream ss(s); if (!p->title().empty()) ss << i+1 << ": " << p->title(); else ss << "Page " << i+1; labels.push_back(s); } } sel->fill(icons, labels); } // -------------------------------------------------------------------- //! Show dialog to select a page or a view. /*! If \a page is negative (the default), shows thumbnails of all pages of the document in a dialog. If the user selects a page, the page number is returned. If the dialog is canceled, -1 is returned. If \a page is non-negative, all views of this page are shown, and the selected view number is returned. */ int CanvasBase::selectPageOrView(Document *doc, int page, int startIndex, int pageWidth, int width, int height) { QDialog *d = new QDialog(); d->setWindowTitle((page >= 0) ? "Ipe: Select view" : "Ipe: Select page"); QLayout *lo = new QVBoxLayout; PageSelector *p = new PageSelector(d); fillWithPages(p, doc, page, pageWidth); lo->addWidget(p); d->setLayout(lo); QWidget::connect(p, SIGNAL(selectionMade()), d, SLOT(accept())); d->resize(width, height); p->setCurrentRow(startIndex); int result = d->exec(); int sel = p->selectedIndex(); delete d; return (result == QDialog::Rejected) ? -1 : sel; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipepdfview_qt.h0000644000175000017500000000374713561570220020026 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::PdfView for QT // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPDFVIEW_QT_H #define IPEPDFVIEW_QT_H #include "ipepdfview.h" #include // -------------------------------------------------------------------- namespace ipe { class PdfView : public QWidget, public PdfViewBase { Q_OBJECT public: PdfView(QWidget* parent, Qt::WindowFlags f = nullptr); virtual void invalidate(); virtual void invalidate(int x, int y, int w, int h); signals: void sizeChanged(); void mouseButton(int); protected: virtual void paintEvent(QPaintEvent *ev); virtual void mousePressEvent(QMouseEvent *ev); virtual QSize sizeHint() const; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipecanvas_cocoa.cpp0000644000175000017500000002205013561570220020614 0ustar otfriedotfried// -*- objc -*- // ipecanvas_cocoa.cpp /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipecanvas_cocoa.h" #include "ipecairopainter.h" #include #include #include using namespace ipe; // -------------------------------------------------------------------- Canvas::Canvas(IpeCanvasView *view) { iView = view; // iLayer = nullptr; } Canvas::~Canvas() { // CGLayerRelease(iLayer); } void Canvas::invalidate() { [iView setNeedsDisplayInRect:[iView bounds]]; } void Canvas::invalidate(int x, int y, int w, int h) { NSRect rect; rect.origin.x = x; rect.origin.y = iHeight - 1 - y - h; rect.size.width = w; rect.size.height = h; [iView setNeedsDisplayInRect:rect]; } void Canvas::setCursor(TCursor cursor, double w, Color *color) { // TODO: not implemented // [[NSCursor closedHandCursor] push]; } /* not using CGLayer for the moment, because in Cairo 1.16.0 this doesn't handle Retina displays correctly. */ #if 0 void Canvas::refreshLayer() { bool copyLayer = iRepaintObjects; refreshSurface(); CGSize layerSize = { 0.0, 0.0 }; if (iLayer) layerSize = CGLayerGetSize(iLayer); // need to be careful here: layerSize is rounded to integers, // iWidth/iHeight is in points and could be something + 0.5 if (layerSize.width != iWidth || layerSize.height != iHeight) { // size has changed if (iLayer) CGLayerRelease(iLayer); iLayer = nullptr; } if (!iLayer || copyLayer) { CGContextRef myContext = [[NSGraphicsContext currentContext] CGContext]; if (!iLayer) { CGSize size = { CGFloat(iWidth), CGFloat(iHeight) }; iLayer = CGLayerCreateWithContext(myContext, size, nullptr); } // Using a cairo context for the layer and drawing directly into the layer // doesn't work with Freetype fonts in Cairo 1.16.0 CGContextRef layerContext = CGLayerGetContext(iLayer); cairo_surface_t *surface = cairo_quartz_surface_create_for_cg_context(layerContext, iWidth, iHeight); cairo_t *cr = cairo_create(surface); cairo_set_source_surface(cr, iSurface, 0.0, 0.0); if (iWidth != iBWidth) { cairo_matrix_t matrix; cairo_matrix_init_scale(&matrix, iBWidth / iWidth, iBHeight / iHeight); cairo_pattern_set_matrix(cairo_get_source(cr), &matrix); } cairo_paint(cr); cairo_destroy(cr); cairo_surface_finish(surface); cairo_surface_destroy(surface); } } #endif void Canvas::drawRect(NSRect rect) { bool resize = [iView inLiveResize]; NSSize s = [iView bounds].size; NSSize sb = [iView convertSizeToBacking:s]; iWidth = s.width; iHeight = s.height; iBWidth = sb.width; iBHeight = sb.height; if (!resize) refreshSurface(); // instead of refreshLayer(); CGContextRef myContext = [[NSGraphicsContext currentContext] CGContext]; CGContextTranslateCTM(myContext, 0.0, iHeight); CGContextScaleCTM(myContext, 1.0, -1.0); // if (iLayer) // CGContextDrawLayerInRect(myContext, [iView bounds], iLayer); if (resize) return; cairo_surface_t *surface = cairo_quartz_surface_create_for_cg_context(myContext, iWidth, iHeight); cairo_t *cr = cairo_create(surface); if (iSurface) { cairo_set_source_surface(cr, iSurface, 0.0, 0.0); if (iWidth != iBWidth) { cairo_matrix_t matrix; cairo_matrix_init_scale(&matrix, iBWidth / iWidth, iBHeight / iHeight); cairo_pattern_set_matrix(cairo_get_source(cr), &matrix); } cairo_paint(cr); } // don't draw tool during live resize if (!resize) { if (iFifiVisible) drawFifi(cr); if (iPage) { CairoPainter cp(iCascade, iFonts.get(), cr, iZoom, false); cp.transform(canvasTfm()); cp.pushMatrix(); drawTool(cp); cp.popMatrix(); } } cairo_destroy(cr); cairo_surface_finish(surface); cairo_surface_destroy(surface); } static int getModifiers(NSEvent *event) { uint modifierFlags = [event modifierFlags]; int mod = 0; if (modifierFlags & NSShiftKeyMask) mod |= CanvasBase::EShift; if (modifierFlags & NSControlKeyMask) mod |= CanvasBase::EControl; if (modifierFlags & NSCommandKeyMask) mod |= CanvasBase::ECommand; if (modifierFlags & NSAlternateKeyMask) mod |= CanvasBase::EAlt; return mod; } void Canvas::button(bool down, NSEvent *event) { // pw is in window coordinates, p in view coordinates, // ps in screen coordinates NSPoint pw = [event locationInWindow]; NSRect rw = { pw, { 100.0, 100.0 }}; NSRect rs = [[iView window] convertRectToScreen:rw]; NSPoint ps = rs.origin; NSPoint p = [iView convertPoint:pw fromView:nil]; // flip y-axis p.y = iHeight - 1 - p.y; // 0, 1, 2 for left, right, middle int cbutton = [event buttonNumber]; // change to 1, 2, 4 .. int button = 1; while (cbutton--) button *= 2; if (down && button == 1 && [event clickCount] == 2) button = 0x81; // left double click iGlobalPos = Vector(ps.x, ps.y); computeFifi(p.x, p.y); int mod = getModifiers(event) | iAdditionalModifiers; if (iTool) iTool->mouseButton(button | mod, down); else if (down && iObserver) iObserver->canvasObserverMouseAction(button | mod); } void Canvas::mouseMove(NSEvent *event) { NSPoint p = [iView convertPoint:[event locationInWindow] fromView:nil]; computeFifi(p.x, iHeight - 1 - p.y); if (iTool) iTool->mouseMove(); if (iObserver) iObserver->canvasObserverPositionChanged(); } bool Canvas::key(NSEvent *event) { if (iTool) { int mod = getModifiers(event); NSString *characters = [event charactersIgnoringModifiers]; String t(characters.UTF8String); return iTool->key(t, mod); } else return false; } void Canvas::magnify(NSEvent *event) { NSPoint q = [iView convertPoint:[event locationInWindow] fromView:nil]; Vector origin = devToUser(Vector(q.x, iHeight - 1 - q.y)); Vector offset = iZoom * (pan() - origin); double nzoom = iZoom * (1.0 + event.magnification); setZoom(nzoom); setPan(origin + (1.0/nzoom) * offset); update(); if (iObserver) // scroll wheel hasn't moved, but update display of ppi iObserver->canvasObserverWheelMoved(0, 0, 0); } void Canvas::scrollWheel(NSEvent *event) { if (iObserver) { double xDelta = [event scrollingDeltaX]; double yDelta = [event scrollingDeltaY]; int kind = ([event modifierFlags] & (NSCommandKeyMask | NSControlKeyMask)) ? 2: [event hasPreciseScrollingDeltas] ? 1 : 0; iObserver->canvasObserverWheelMoved(-xDelta, yDelta, kind); } } // -------------------------------------------------------------------- @implementation IpeCanvasView - (instancetype) initWithFrame:(NSRect) rect { if ([super initWithFrame:rect]) _canvas = new Canvas(self); return self; } - (BOOL) acceptsFirstResponder { return YES; } - (BOOL) isOpaque { return YES; } - (void) drawRect:(NSRect) rect { self.canvas->drawRect(rect); } - (void) mouseDown:(NSEvent *) event { self.canvas->button(true, event); } - (void) mouseUp:(NSEvent *) event { self.canvas->button(false, event); } - (void) mouseDragged:(NSEvent *) event { self.canvas->mouseMove(event); } - (void) rightMouseDown:(NSEvent *) event { self.canvas->button(true, event); } - (void) rightMouseUp:(NSEvent *) event { self.canvas->button(false, event); } - (void) rightMouseDragged:(NSEvent *) event { self.canvas->mouseMove(event); } - (void) otherMouseDown:(NSEvent *) event { self.canvas->button(true, event); } - (void) otherMouseUp:(NSEvent *) event { self.canvas->button(false, event); } - (void) otherMouseDragged:(NSEvent *) event { self.canvas->mouseMove(event); } - (void) mouseMoved:(NSEvent *) event { self.canvas->mouseMove(event); } - (void) keyDown:(NSEvent *) event { if (!self.canvas->key(event)) [super keyDown:event]; } - (void) scrollWheel:(NSEvent *) event { self.canvas->scrollWheel(event); } - (void) magnifyWithEvent:(NSEvent *) event { self.canvas->magnify(event); } - (void) dealloc { // TODO: Is this actually called? NSLog(@"IpeCanvasView:dealloc"); delete self.canvas; } @end // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipetool.cpp0000644000175000017500000002770413561570220017165 0ustar otfriedotfried// -------------------------------------------------------------------- // ipe::Tool // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipecanvas.h" #include "ipetool.h" using namespace ipe; #define EPS 1e-12 // -------------------------------------------------------------------- /*! \class ipe::PanTool \ingroup canvas \brief A tool for panning the canvas. */ PanTool::PanTool(CanvasBase *canvas, const Page *page, int view) : Tool(canvas), iPage(page), iView(view) { iPan = Vector::ZERO; iMouseDown = iCanvas->unsnappedPos(); iCanvas->setCursor(CanvasBase::EHandCursor); } void PanTool::draw(Painter &painter) const { painter.translate(iPan); painter.setStroke(Attribute(Color(0, 0, 1000))); painter.newPath(); const Layout *l = iCanvas->cascade()->findLayout(); painter.rect(Rect(-l->iOrigin, -l->iOrigin + l->iPaperSize)); painter.drawPath(EStrokedOnly); for (int i = 0; i < iPage->count(); ++i) { if (iPage->objectVisible(iView, i)) iPage->object(i)->drawSimple(painter); } } void PanTool::mouseButton(int button, bool press) { if (!press) { Vector dpan = iCanvas->unsnappedPos() - iMouseDown; iCanvas->setPan(iCanvas->pan() - dpan); } iCanvas->finishTool(); } void PanTool::mouseMove() { iPan = iCanvas->unsnappedPos() - iMouseDown; iCanvas->updateTool(); } // -------------------------------------------------------------------- /*! \class ipe::SelectTool \ingroup canvas \brief A tool for selecting objects. */ class SelectCompare { public: int operator()(const SelectTool::SObj &lhs, const SelectTool::SObj &rhs) const { return (lhs.distance < rhs.distance); } }; //! Constructor starts selection. SelectTool::SelectTool(CanvasBase *canvas, Page *page, int view, double selectDistance, bool nonDestructive) : Tool(canvas) { iPage = page; iView = view; iNonDestructive = nonDestructive; iSelectDistance = selectDistance; // coordinates in user space Vector v = iCanvas->unsnappedPos(); iMouseDown = v; iDragging = false; double bound = iSelectDistance / iCanvas->zoom(); // Collect objects close enough double d; for (int i = iPage->count() - 1; i >= 0; --i) { if (iPage->objectVisible(iView, i) && !iPage->isLocked(iPage->layerOf(i))) { if ((d = iPage->distance(i, v, bound)) < bound) { SObj obj; obj.index = i; obj.distance = d; iObjs.push_back(obj); } } } iCur = 0; std::stable_sort(iObjs.begin(), iObjs.end(), SelectCompare()); iCanvas->setCursor(CanvasBase::ECrossCursor); } void SelectTool::draw(Painter &painter) const { if (iDragging) { Rect r(iMouseDown, iCorner); painter.setStroke(Attribute(Color(1000, 0, 1000))); painter.newPath(); painter.rect(r); painter.drawPath(EStrokedOnly); } else { painter.setStroke(Attribute(Color(1000, 0, 1000))); painter.newPath(); double d = iSelectDistance / iCanvas->zoom(); painter.drawArc(Arc(Matrix(d, 0, 0, d, iMouseDown.x, iMouseDown.y))); painter.closePath(); painter.drawPath(EStrokedOnly); if (iObjs.size() > 0) { // display current object painter.setStroke(Attribute(Color(1000, 0, 0))); iPage->object(iObjs[iCur].index)->drawSimple(painter); } } } void SelectTool::mouseButton(int button, bool press) { // ipeDebug("SelectTool::mouseButton(%d, %d)", button, press); if (press) { iCanvas->finishTool(); return; } bool changed = false; if (iDragging) { Rect r(iMouseDown, iCorner); // dragging from right to left behaves differently bool alternate = (iCorner.x < iMouseDown.x); if (iNonDestructive) { // xor selection status of objects in range // last object that is not selected is made primary selection int new_primary = -1; for (int i = 0; i < iPage->count(); ++i) { Matrix id; if (iPage->objectVisible(iView, i) && !iPage->isLocked(iPage->layerOf(i))) { Rect s; iPage->object(i)->addToBBox(s, id, false); if (alternate ? r.intersects(s) : r.contains(s)) { changed = true; // in range if (iPage->select(i)) iPage->setSelect(i, ENotSelected); else { new_primary = i; iPage->setSelect(i, ESecondarySelected); } } } } if (new_primary >= 0) { // deselect old primary, select new primary int old_primary = iPage->primarySelection(); if (old_primary >= 0) iPage->setSelect(old_primary, ESecondarySelected); iPage->setSelect(new_primary, EPrimarySelected); } } else { // deselect all objects outside range, // secondary select all objects in range, for (int i = 0; i < iPage->count(); ++i) { iPage->setSelect(i, ENotSelected); Matrix id; if (iPage->objectVisible(iView, i) && !iPage->isLocked(iPage->layerOf(i))) { Rect s; iPage->object(i)->addToBBox(s, id, false); if (alternate ? r.intersects(s) : r.contains(s)) iPage->setSelect(i, ESecondarySelected); } } changed = true; // XXX not accurate, but not used now anyway iPage->ensurePrimarySelection(); } } else if (iObjs.size() > 0) { int index = iObjs[iCur].index; if (iNonDestructive) { if (!iPage->select(index)) { // selecting unselected object as primary int old = iPage->primarySelection(); if (old >= 0) iPage->setSelect(old, ESecondarySelected); iPage->setSelect(index, EPrimarySelected); } else // deselecting selected object iPage->setSelect(index, ENotSelected); changed = true; iPage->ensurePrimarySelection(); } else { // destructive: unselect all for (int i = 0; i < iPage->count(); ++i) { if (i != index && iPage->select(i)) { changed = true; iPage->setSelect(i, ENotSelected); } } if (iPage->select(index) != EPrimarySelected) changed = true; iPage->setSelect(index, EPrimarySelected); } } else { // no object in range, deselect all if (!iNonDestructive) { changed = iPage->hasSelection(); iPage->deselectAll(); } } iCanvas->finishTool(); // not using right now (void) changed; } void SelectTool::mouseMove() { iCorner = iCanvas->unsnappedPos(); if ((iCorner - iMouseDown).sqLen() > 9.0) iDragging = true; iCanvas->updateTool(); } bool SelectTool::key(String text, int modifiers) { if (!iDragging && text == " " && iObjs.size() > 0) { iCur++; if (iCur >= int(iObjs.size())) iCur = 0; iCanvas->updateTool(); return true; } else if (text == "\027") { iCanvas->finishTool(); return true; } else return false; } // -------------------------------------------------------------------- /*! \class ipe::TransformTool \ingroup canvas \brief A tool for transforming the selected objects on the canvas. Supports moving, rotating, scaling, stretching, and shearing. */ //! Constructor starts transformation. /*! After constructing a TransformTool, you must call isValid() to ensure that the transformation can be performed. A transformation can fail because the selection contains pinned objects, or because the initial mouse position is identical to the transformation origin. */ TransformTool::TransformTool(CanvasBase *canvas, Page *page, int view, TType type, bool withShift) : Tool(canvas) { iPage = page; iView = view; iType = type; iWithShift = withShift; iMouseDown = iCanvas->pos(); if (iType == ETranslate) iCanvas->setAutoOrigin(iMouseDown); iOnlyHorizontal = false; iOnlyVertical = false; iValid = true; // check if objects are pinned TPinned pin = ENoPin; for (int i = 0; i < page->count(); ++i) { if (page->select(i)) pin = TPinned(pin | page->object(i)->pinned()); } // rotating, scaling, stretching, shearing are not allowed on pinned objects if (pin == EFixedPin || (pin && iType != ETranslate)) { iValid = false; return; } if (pin) { if (pin == EVerticalPin) iOnlyHorizontal = true; else iOnlyVertical = true; iWithShift = false; // ignore this and follow pinning restriction } // compute origin const Snap &sd = iCanvas->snap(); if (sd.iWithAxes) { iOrigin = sd.iOrigin; iDir = sd.iDir; } else { iDir = 0.0; // find bounding box of selected objects Rect bbox; for (int i = 0; i < iPage->count(); ++i) { if (iPage->select(i)) bbox.addRect(iPage->bbox(i)); } iOrigin = 0.5 * (bbox.bottomLeft() + bbox.topRight()); if (iType == EStretch || iType == EScale || iType == EShear) { if (iMouseDown.x > iOrigin.x) iOrigin.x = bbox.bottomLeft().x; else iOrigin.x = bbox.topRight().x; if (iMouseDown.y > iOrigin.y) iOrigin.y = bbox.bottomLeft().y; else iOrigin.y = bbox.topRight().y; } } if (iType == EShear && abs((Linear(-iDir) * (iMouseDown - iOrigin)).y) < 0.1) iValid = false; else if (iType != ETranslate && iMouseDown == iOrigin) iValid = false; else iCanvas->setCursor(CanvasBase::EHandCursor); } //! Check that the transformation can be performed. bool TransformTool::isValid() const { return iValid; } void TransformTool::draw(Painter &painter) const { painter.setStroke(Attribute(Color(0, 600, 0))); painter.transform(iTransform); for (int i = 0; i < iPage->count(); ++i) { if (iPage->select(i)) iPage->object(i)->drawSimple(painter); } } // compute iTransform void TransformTool::compute(const Vector &v1) { Vector u0 = iMouseDown - iOrigin; Vector u1 = v1 - iOrigin; switch (iType) { case ETranslate: { Vector d = v1 - iMouseDown; if (iOnlyHorizontal || (iWithShift && ipe::abs(d.x) > ipe::abs(d.y))) d.y = 0.0; else if (iOnlyVertical || iWithShift) d.x = 0.0; iTransform = Matrix(d); break; } case ERotate: iTransform = (Matrix(iOrigin) * Linear(Angle(u1.angle() - u0.angle())) * Matrix(-iOrigin)); break; case EScale: { double factor = sqrt(u1.sqLen() / u0.sqLen()); iTransform = (Matrix(iOrigin) * Linear(factor, 0, 0, factor) * Matrix(-iOrigin)); break; } case EStretch: { double xfactor = (abs(u0.x) < EPS) ? 1.0 : u1.x / u0.x; double yfactor = (abs(u0.y) < EPS) ? 1.0 : u1.y / u0.y; iTransform = (Matrix(iOrigin) * Linear(xfactor, 0, 0, yfactor) * Matrix(-iOrigin)); break; } case EShear: { auto rot = Linear(-iDir); auto v0 = rot * u0; auto v1 = rot * u1; double s = (v1.x - v0.x) / v0.y; iTransform = (Matrix(iOrigin) * Linear(iDir) * Linear(1.0, 0, s, 1.0) * rot * Matrix(-iOrigin)); break; } } } void TransformTool::mouseButton(int button, bool press) { if (!press) { compute(iCanvas->pos()); report(); } iCanvas->finishTool(); } //! Report the final transformation chosen. /*! The implementation in TransformTool does nothing. Derived classes should reimplement report(). */ void TransformTool::report() { // nothing yet } void TransformTool::mouseMove() { compute(iCanvas->pos()); iCanvas->updateTool(); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipepdfview_qt.cpp0000644000175000017500000000511413561570220020347 0ustar otfriedotfried// -------------------------------------------------------------------- // ipe::PdfView for Qt // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepdfview_qt.h" #include #include #include using namespace ipe; // -------------------------------------------------------------------- PdfView::PdfView(QWidget* parent, Qt::WindowFlags f) : QWidget(parent, f) { setAttribute(Qt::WA_NoBackground); } QSize PdfView::sizeHint() const { return QSize(640, 480); } // -------------------------------------------------------------------- void PdfView::invalidate() { QWidget::update(); } void PdfView::invalidate(int x, int y, int w, int h) { QWidget::update(QRect(x, y, w, h)); } // -------------------------------------------------------------------- void PdfView::paintEvent(QPaintEvent * ev) { if (iBWidth != width() || iBHeight != height()) { iBWidth = iWidth = width(); iBHeight = iHeight = height(); emit sizeChanged(); } refreshSurface(); QPainter qPainter; qPainter.begin(this); QRect r = ev->rect(); QRect source(r.left(), r.top(), r.width(), r.height()); QImage bits(cairo_image_surface_get_data(iSurface), iWidth, iHeight, QImage::Format_RGB32); qPainter.drawImage(r, bits, source); qPainter.end(); } void PdfView::mousePressEvent(QMouseEvent *ev) { emit mouseButton(ev->button() != Qt::LeftButton ? 1 : 0); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipeselector_qt.h0000644000175000017500000000366613561570220020202 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::PageSelector // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPESELECTOR_H #define IPESELECTOR_H #include "ipedoc.h" #include "ipepdfparser.h" #include using namespace ipe; // -------------------------------------------------------------------- namespace ipe { class PageSelector : public QListWidget { Q_OBJECT public: PageSelector(QWidget *parent = nullptr); void fill(std::vector &icons, std::vector &labels); int selectedIndex() const { return currentRow(); } signals: void selectionMade(); private slots: void pageSelected(QListWidgetItem *item); }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipepdfview_cocoa.h0000644000175000017500000000367513561570220020466 0ustar otfriedotfried// -*- objc -*- // -------------------------------------------------------------------- // ipe::PdfView for Cocoa // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPEPDFVIEW_COCOA_H #define IPEPDFVIEW_COCOA_H #include "ipepdfview.h" #import // -------------------------------------------------------------------- class PdfView; @interface IpePdfView : NSView @property PdfView *pdfView; @end // -------------------------------------------------------------------- class PdfView : public ipe::PdfViewBase { public: PdfView(IpePdfView *view); virtual ~PdfView(); void drawRect(NSRect rect); private: virtual void invalidate(); virtual void invalidate(int x, int y, int w, int h); private: IpePdfView *iView; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipeselector_gtk.cpp0000644000175000017500000000434513561570220020671 0ustar otfriedotfried// -------------------------------------------------------------------- // PageSelector for GTK // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipecanvas_gtk.h" #include "ipethumbs.h" using namespace ipe; // -------------------------------------------------------------------- //! Show dialog to select a page or a view. /*! If \a page is negative (the default), shows thumbnails of all pages of the document in a dialog. If the user selects a page, the page number is returned. If the dialog is canceled, -1 is returned. If \a page is non-negative, all views of this page are shown, and the selected view number is returned. \a itemWidth is the width of the page thumbnails (the height is computed automatically). */ int CanvasBase::selectPageOrView(Document *doc, int page, int startIndex, int pageWidth, int width, int height) { // Create image list Thumbnail r(doc, pageWidth); int nItems = (page >= 0) ? doc->page(page)->countViews() : doc->countPages(); (void) nItems; // TODO return 0; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/Makefile0000644000175000017500000000273213561570220016440 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for ipe::Canvas # -------------------------------------------------------------------- OBJDIR = $(BUILDDIR)/obj/ipecanvas include ../common.mak TARGET = $(call dll_target,ipecanvas) MAKE_SYMLINKS = $(call dll_symlinks,ipecanvas) SONAME = $(call soname,ipecanvas) INSTALL_SYMLINKS = $(call install_symlinks,ipecanvas) CPPFLAGS += -I../include -I../ipecairo $(CAIRO_CFLAGS) $(UI_CFLAGS) LIBS += -L$(buildlib) -lipecairo -lipe $(CAIRO_LIBS) $(UI_LIBS) CXXFLAGS += $(DLL_CFLAGS) all: $(TARGET) sources = ipetool.cpp ipecanvas.cpp ipepdfview.cpp cocoa_sources = ipecanvas_cocoa.cpp ipeselector_cocoa.cpp ipepdfview_cocoa.cpp win_sources = ipecanvas_win.cpp ipeselector_win.cpp ipepdfview_win.cpp gtk_sources = ipecanvas_gtk.cpp ipeselector_gtk.cpp qt_sources = ipecanvas_qt.cpp ipeselector_qt.cpp ipepdfview_qt.cpp moc_headers = ipecanvas_qt.h ipeselector_qt.h ipepdfview_qt.h $(TARGET): $(objects) $(MAKE_LIBDIR) $(CXX) $(LDFLAGS) $(DLL_LDFLAGS) $(SONAME) -o $@ $^ $(LIBS) $(MAKE_SYMLINKS) clean: @-rm -f $(objects) $(TARGET) $(DEPEND) $(DEPEND): Makefile $(MAKE_DEPEND) -include $(DEPEND) install: $(TARGET) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_DIR) $(INSTALL_ROOT)$(IPEHEADERDIR) $(INSTALL_PROGRAMS) $(TARGET) $(INSTALL_ROOT)$(IPELIBDIR) $(INSTALL_FILES) *.h $(INSTALL_ROOT)$(IPEHEADERDIR) $(INSTALL_SYMLINKS) # -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipeselector_win.cpp0000644000175000017500000001746513561570220020710 0ustar otfriedotfried// -------------------------------------------------------------------- // PageSelector for Win32 // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipecanvas_win.h" #include "ipethumbs.h" #include #include using namespace ipe; extern HBITMAP createBitmap(uint32_t *p, int w, int h); // -------------------------------------------------------------------- #define IDBASE 9000 #define BORDER 6 static void buildFlags(std::vector &t, DWORD flags) { union { DWORD dw; short s[2]; } a; a.dw = flags; t.push_back(a.s[0]); t.push_back(a.s[1]); t.push_back(0); t.push_back(0); } static void buildString(std::vector &t, const char *s) { const char *p = s; while (*p) t.push_back(*p++); t.push_back(0); } // -------------------------------------------------------------------- struct SData { HIMAGELIST hImageList; std::vector labels; int startIndex; }; static void populateView(HWND h, SData *d) { LVITEM lvI; lvI.mask = LVIF_TEXT | LVIF_IMAGE; lvI.iSubItem = 0; for (int i = 0; i < size(d->labels); ++i) { lvI.pszText = d->labels[i].w().data(); lvI.iItem = i; lvI.iImage = i; (void) ListView_InsertItem(h, &lvI); } SendMessage(h, LVM_ENSUREVISIBLE, (WPARAM) d->startIndex, FALSE); } static INT_PTR CALLBACK dialogProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { SData *d = (SData *) GetWindowLongPtr(hwnd, GWLP_USERDATA); switch (message) { case WM_INITDIALOG: { d = (SData *) lParam; SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR) d); HWND h = GetDlgItem(hwnd, IDBASE); SendMessage(h, LVM_SETIMAGELIST, (WPARAM) LVSIL_NORMAL, (LPARAM) d->hImageList); populateView(h, d); return (INT_PTR) TRUE; } case WM_NOTIFY: switch (((LPNMHDR)lParam)->code) { case LVN_ITEMACTIVATE: EndDialog(hwnd, ((LPNMITEMACTIVATE) lParam)->iItem); return (INT_PTR) TRUE; default: return (INT_PTR) FALSE; } case WM_CLOSE: EndDialog(hwnd, -1); return (INT_PTR) TRUE; default: return (INT_PTR) FALSE; } } int showPageSelectDialog(int width, int height, const char * title, HIMAGELIST il, std::vector &labels, int startIndex) { SData sData; sData.hImageList = il; sData.labels = std::move(labels); sData.startIndex = startIndex; // Convert to dialog units: LONG base = GetDialogBaseUnits(); int baseX = LOWORD(base); int baseY = HIWORD(base); int w = width * 4 / baseX; int h = height * 8 / baseY; std::vector t; // Dialog flags buildFlags(t, WS_POPUP | WS_BORDER | DS_SHELLFONT | WS_SYSMENU | DS_MODALFRAME | WS_CAPTION); t.push_back(1); // no of elements t.push_back(100); // position of popup-window t.push_back(30); t.push_back(w); t.push_back(h); // menu t.push_back(0); // class t.push_back(0); // title buildString(t, title); // for DS_SHELLFONT t.push_back(10); buildString(t,"MS Shell Dlg"); // Item if (t.size() % 2 != 0) t.push_back(0); // LVS_SHAREIMAGELISTS: do not destroy imagelist when dialog is destroyed buildFlags(t, WS_CHILD|WS_VISIBLE|LVS_ICON|LVS_SHAREIMAGELISTS| WS_VSCROLL|LVS_SINGLESEL|WS_BORDER); t.push_back(BORDER); t.push_back(BORDER); t.push_back(w - 2 * BORDER); t.push_back(h - 2 * BORDER); t.push_back(IDBASE); // control id buildString(t, WC_LISTVIEWA); t.push_back(0); t.push_back(0); int res = DialogBoxIndirectParamW(nullptr, (LPCDLGTEMPLATE) &t[0], nullptr, dialogProc, (LPARAM) &sData); return res; } // -------------------------------------------------------------------- //! Show dialog to select a page or a view. /*! If \a page is negative (the default), shows thumbnails of all pages of the document in a dialog. If the user selects a page, the page number is returned. If the dialog is canceled, -1 is returned. If \a page is non-negative, all views of this page are shown, and the selected view number is returned. \a itemWidth is the width of the page thumbnails (the height is computed automatically). */ int CanvasBase::selectPageOrView(Document *doc, int page, int startIndex, int pageWidth, int width, int height) { // Create image list Thumbnail r(doc, pageWidth); int nItems = (page >= 0) ? doc->page(page)->countViews() : doc->countPages(); // Image list will be destroyed when ListView is destroyed HIMAGELIST il = ImageList_Create(pageWidth, r.height(), ILC_COLOR32, nItems, 4); if (page >= 0) { Page *p = doc->page(page); for (int i = 0; i < p->countViews(); ++i) { Buffer bx = r.render(p, i); HBITMAP b = createBitmap((uint32_t *) bx.data(), pageWidth, r.height()); ImageList_Add(il, b, nullptr); } } else { for (int i = 0; i < doc->countPages(); ++i) { Page *p = doc->page(i); Buffer bx = r.render(p, p->countViews() - 1); HBITMAP b = createBitmap((uint32_t *) bx.data(), pageWidth, r.height()); ImageList_Add(il, b, nullptr); } } const char *title = (page >= 0) ? "Ipe: Select view" : "Ipe: Select page"; std::vector labels; if (page >= 0) { Page *p = doc->page(page); for (int i = 0; i < p->countViews(); ++i) { String text; StringStream ss(text); if (!p->viewName(i).empty()) ss << i+1 << ": " << p->viewName(i); else ss << "View " << i+1; labels.push_back(text); } } else { for (int i = 0; i < doc->countPages(); ++i) { Page *p = doc->page(i); String t = p->title(); String text; StringStream ss(text); if (t != "") ss << i+1 << ": " << t; else ss << "Page " << i+1; labels.push_back(text); } } int result = showPageSelectDialog(width, height, title, il, labels, startIndex); ImageList_Destroy(il); return result; } // -------------------------------------------------------------------- HBITMAP createBitmap(uint32_t *p, int w, int h) { BITMAPINFO bmi; ZeroMemory(&bmi, sizeof(bmi)); bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); bmi.bmiHeader.biWidth = w; bmi.bmiHeader.biHeight = h; bmi.bmiHeader.biPlanes = 1; bmi.bmiHeader.biBitCount = 24; bmi.bmiHeader.biCompression = BI_RGB; void *pbits = nullptr; HBITMAP bm = CreateDIBSection(nullptr, &bmi, DIB_RGB_COLORS, &pbits, nullptr, 0); uint8_t *q = (uint8_t *) pbits; int stride = (3 * w + 3) & ~3; for (int y = 0; y < h; ++y) { uint32_t *src = p + w * y; uint8_t *dst = q + stride * (h - 1 - y); for (int x = 0; x < w; ++x) { uint32_t pixel = *src++; *dst++ = pixel & 0xff; // B Windows ordering *dst++ = (pixel >> 8) & 0xff; // G *dst++ = (pixel >> 16) & 0xff; // R } } return bm; } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipecanvas_cocoa.h0000644000175000017500000000441413561570220020265 0ustar otfriedotfried// -*- objc -*- // -------------------------------------------------------------------- // ipe::Canvas for Cocoa // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPECANVAS_COCOA_H #define IPECANVAS_COCOA_H #include "ipecanvas.h" #import // -------------------------------------------------------------------- class Canvas; @interface IpeCanvasView : NSView @property Canvas *canvas; @end // -------------------------------------------------------------------- class Canvas : public ipe::CanvasBase { public: Canvas(IpeCanvasView *view); virtual ~Canvas(); IpeCanvasView *view() { return iView; } void button(bool press, NSEvent *event); void mouseMove(NSEvent *event); bool key(NSEvent *event); void scrollWheel(NSEvent *event); void magnify(NSEvent *event); void drawRect(NSRect rect); private: // void refreshLayer(); virtual void invalidate(); virtual void invalidate(int x, int y, int w, int h); virtual void setCursor(TCursor cursor, double w, ipe::Color *color); private: IpeCanvasView *iView; // CGLayer *iLayer; }; // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipetool.h0000644000175000017500000000652313561570220016626 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::Tool // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPETOOL_H #define IPETOOL_H #include "ipepage.h" #include "ipetoolbase.h" namespace ipe { class CanvasBase; // -------------------------------------------------------------------- class PanTool : public Tool { public: PanTool(CanvasBase *canvas, const Page *page, int view); virtual void draw(Painter &painter) const; virtual void mouseButton(int button, bool press); virtual void mouseMove(); private: const Page *iPage; int iView; Vector iPan; Vector iMouseDown; }; // -------------------------------------------------------------------- class SelectTool : public Tool { public: SelectTool(CanvasBase *canvas, Page *page, int view, double selectDistance, bool nonDestructive); virtual void draw(Painter &painter) const; virtual void mouseButton(int button, bool press); virtual void mouseMove(); virtual bool key(String text, int modifiers); private: void ensurePrimary(); public: struct SObj { int index; double distance; }; private: Page *iPage; int iView; bool iNonDestructive; double iSelectDistance; Vector iMouseDown; std::vector iObjs; int iCur; bool iDragging; Vector iCorner; }; // -------------------------------------------------------------------- class TransformTool : public Tool { public: enum TType { ETranslate, EScale, EStretch, ERotate, EShear }; TransformTool(CanvasBase *canvas, Page *page, int view, TType type, bool withShift); bool isValid() const; virtual void draw(Painter &painter) const; virtual void mouseButton(int button, bool press); virtual void mouseMove(); virtual void report(); protected: void compute(const Vector &v); protected: Page *iPage; int iView; TType iType; bool iWithShift; bool iOnlyHorizontal; bool iOnlyVertical; Vector iMouseDown; Matrix iTransform; Vector iOrigin; Angle iDir; bool iValid; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipecanvas_win.h0000644000175000017500000000562013561570220017776 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::Canvas for Win32 // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPECANVASWIN_H #define IPECANVASWIN_H // -------------------------------------------------------------------- #include "ipecanvas.h" #include namespace ipe { class Canvas : public CanvasBase { public: static void init(HINSTANCE hInstance); static UINT getDpiForWindow(HWND hwnd); Canvas(HWND parent, HINSTANCE hInstance = nullptr); HWND windowId() const { return hwnd; } static HBITMAP createBitmap(uint8_t *p, int w, int h); private: void button(int button, bool down, int mod, Vector v); void key(WPARAM wParam, LPARAM lParam); void mouseMove(Vector v); void wndPaint(); void updateSize(); Vector location(HWND hwnd, POINT q, POINT h); LRESULT handlePointerEvent(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam); LRESULT handlePanGesture(DWORD flags, POINTS &p); LRESULT handleZoomGesture(DWORD flags, POINTS &p, ULONG d); virtual void invalidate(); virtual void invalidate(int x, int y, int w, int h); virtual void setCursor(TCursor cursor, double w, Color *color); private: static const wchar_t className[]; static LRESULT CALLBACK wndProc(HWND hwnd, UINT Message, WPARAM wParam, LPARAM lParam); static void mouseButton(Canvas *canvas, int button, bool down, WPARAM wParam, LPARAM lParam); private: HWND hwnd; // Gesture support Vector iGestureStart; int iGestureDist; Vector iGesturePan; double iGestureZoom; UINT32 iPointerId; Vector iHimetric; bool isTransient; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/ipecanvas/ipeselector_cocoa.cpp0000644000175000017500000001762213561570220021172 0ustar otfriedotfried// -*- objc -*- // -------------------------------------------------------------------- // PageSelector for Cocoa // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipeselector_cocoa.h" #include "ipecanvas.h" #include #include using namespace ipe; inline NSString *C2N(const char *s) {return [NSString stringWithUTF8String:s];} // -------------------------------------------------------------------- // not thread-safe, but don't know how to do it otherwise... // currently this is no problem because we run this as a modal dialog. NSSize thumbnail_size; @implementation IpeSelectorProvider - (int) count { if (self.page >= 0) return self.doc->page(self.page)->countViews(); else return self.doc->countPages(); } - (NSString *) title:(int) index { if (self.page >= 0) { String t = self.doc->page(self.page)->viewName(index); if (t.empty()) return [NSString stringWithFormat:@"View %d", index + 1]; else return [NSString stringWithFormat:@"%d: %@", index + 1, C2N(t.z())]; } else { String t = self.doc->page(index)->title(); if (t.empty()) return [NSString stringWithFormat:@"Page %d", index + 1]; else return [NSString stringWithFormat:@"%d: %@", index + 1, C2N(t.z())]; } } - (NSImage *) image:(int) index { if (!self.images) { self.images = [NSMutableArray arrayWithCapacity:[self count]]; for (int i = 0; i < [self count]; ++i) [self.images addObject:[NSNull null]]; } if (self.images[index] == [NSNull null]) { Buffer b = [self renderImage:index]; self.images[index] = [self createImage:b]; } return (NSImage *) self.images[index]; } - (Buffer) renderImage:(int) index { if (self.page >= 0) return self.thumb->render(self.doc->page(self.page), index); else { Page *p = self.doc->page(index); return self.thumb->render(p, p->countViews() - 1); } } - (NSImage *) createImage:(Buffer) b { int w = 2 * self.tnSize.width; int h = 2 * self.tnSize.height; return [NSImage imageWithSize:self.tnSize flipped:YES drawingHandler:^(NSRect rect) { cairo_surface_t *image = cairo_image_surface_create_for_data((uint8_t *) b.data(), CAIRO_FORMAT_ARGB32, w, h, 4 * w); CGContextRef ctx = [[NSGraphicsContext currentContext] CGContext]; cairo_surface_t *surface = cairo_quartz_surface_create_for_cg_context(ctx, w, h); cairo_t *cr = cairo_create(surface); cairo_set_source_surface(cr, image, 0.0, 0.0); cairo_matrix_t matrix; cairo_matrix_init_scale(&matrix, 2.0, 2.0); cairo_pattern_set_matrix(cairo_get_source(cr), &matrix); cairo_paint(cr); cairo_destroy(cr); cairo_surface_finish(surface); cairo_surface_destroy(surface); cairo_surface_destroy(image); return YES; }]; } @end // -------------------------------------------------------------------- @implementation IpeSelectorItem @end // -------------------------------------------------------------------- @implementation IpeSelectorView - (id) initWithFrame:(NSRect) frameRect { NSSize buttonSize = { thumbnail_size.width + 6, thumbnail_size.height + 30 }; NSSize itemSize = { buttonSize.width + 20, buttonSize.height + 20 }; const NSPoint buttonOrigin = { 10, 10 }; self = [super initWithFrame:(NSRect){frameRect.origin, itemSize}]; if (self) { NSButton *b = [[NSButton alloc] initWithFrame:(NSRect){buttonOrigin, buttonSize}]; b.imagePosition = NSImageAbove; b.buttonType = NSMomentaryPushInButton; b.action = @selector(ipePageSelected:); [self addSubview:b]; self.button = b; } return self; } - (void) ipeSet:(IpeSelectorItem *) item { self.button.tag = item.index; self.button.title = [item.provider title:item.index]; self.button.image = [item.provider image:item.index]; } @end // -------------------------------------------------------------------- @implementation IpeSelectorPrototype - (void) loadView { self.view = [[IpeSelectorView alloc] initWithFrame:NSZeroRect]; } - (void) setRepresentedObject:(id) representedObject { [super setRepresentedObject:representedObject]; [(IpeSelectorView *)[self view] ipeSet:representedObject]; } @end // -------------------------------------------------------------------- @interface IpeSelectorDelegate : NSObject - (void) ipePageSelected:(id) sender; @end @implementation IpeSelectorDelegate - (void) ipePageSelected:(id) sender { [NSApp stopModalWithCode:[sender tag]]; NSWindow *panel = [NSApp modalWindow]; if (panel) [panel close]; } - (BOOL) windowShouldClose:(id) sender { [NSApp stopModalWithCode:-1]; // [NSApp abortModal]; return YES; } @end // -------------------------------------------------------------------- int showPageSelectDialog(int width, int height, const char * title, IpeSelectorProvider *provider, int startIndex) { thumbnail_size = provider.tnSize; NSPanel *panel = [[NSPanel alloc] initWithContentRect:NSMakeRect(200., 100., width, height) styleMask:NSTitledWindowMask| NSResizableWindowMask|NSClosableWindowMask backing:NSBackingStoreBuffered defer:YES]; panel.title = C2N(title); IpeSelectorDelegate *delegate = [IpeSelectorDelegate new]; panel.delegate = delegate; NSMutableArray *elements = [NSMutableArray arrayWithCapacity:[provider count]]; for (int i = 0; i < [provider count]; ++i) { IpeSelectorItem *item = [IpeSelectorItem new]; item.index = i; item.provider = provider; [elements addObject:item]; } NSScrollView *scroll = [[NSScrollView alloc] initWithFrame:[panel.contentView frame]]; scroll.autoresizingMask = NSViewWidthSizable|NSViewHeightSizable; scroll.hasVerticalScroller = YES; panel.contentView = scroll; NSCollectionView *cv = [[NSCollectionView alloc] initWithFrame:NSZeroRect]; cv.autoresizingMask = NSViewWidthSizable|NSViewHeightSizable; scroll.documentView = cv; cv.itemPrototype = [IpeSelectorPrototype new]; cv.content = elements; int result = [NSApp runModalForWindow:panel]; return result; } // -------------------------------------------------------------------- int CanvasBase::selectPageOrView(Document *doc, int page, int startIndex, int pageWidth, int width, int height) { // for retina displays, create bitmap with twice the resolution Thumbnail thumbs(doc, 2 * pageWidth); NSSize tnSize; tnSize.width = thumbs.width() / 2.0; tnSize.height = thumbs.height() / 2.0; const char *title = (page >= 0) ? "Ipe: Select view" : "Ipe: Select page"; IpeSelectorProvider *provider = [IpeSelectorProvider new]; provider.doc = doc; provider.thumb = &thumbs; provider.page = page; provider.tnSize = tnSize; return showPageSelectDialog(width, height, title, provider, startIndex); } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipecanvas_win.cpp0000644000175000017500000004240013561570220020326 0ustar otfriedotfried// -------------------------------------------------------------------- // ipe::Canvas for Win // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ // for touch gestures: need at least Windows 7 #define WINVER 0x0601 #define _WIN32_WINNT 0x0601 #include "ipecanvas_win.h" #include "ipecairopainter.h" #include "ipetool.h" #include #include #include #include using namespace ipe; // -------------------------------------------------------------------- // some definitions from Windows 8 #define WM_POINTERUPDATE 0x245 // 581 #define WM_POINTERDOWN 0x246 // 582 #define WM_POINTERUP 0x247 // 583 #define WM_POINTERCAPTURECHANGED 0x24c typedef enum { PT_POINTER = 0x00000001, PT_TOUCH = 0x00000002, PT_PEN = 0x00000003, PT_MOUSE = 0x00000004, PT_TOUCHPAD = 0x00000005 } POINTER_INPUT_TYPE; typedef struct { POINTER_INPUT_TYPE pointerType; UINT32 pointerId; UINT32 frameId; // POINTER_FLAGS pointerFlags; UINT32 pointerFlags; HANDLE sourceDevice; HWND hwndTarget; POINT ptPixelLocation; POINT ptHimetricLocation; POINT ptPixelLocationRaw; POINT ptHimetricLocationRaw; DWORD dwTime; UINT32 historyCount; INT32 inputData; DWORD dwKeyStates; UINT64 PerformanceCount; // POINTER_BUTTON_CHANGE_TYPE ButtonChangeType; UINT32 ButtonChangeType; } POINTER_INFO; typedef struct { POINTER_INFO pointerInfo; UINT32 penFlags; UINT32 penMask; UINT32 pressure; UINT32 rotation; INT32 tiltX; INT32 tiltY; } POINTER_PEN_INFO; // -------------------------------------------------------------------- typedef WINBOOL WINAPI (*LPSetGestureConfig)(HWND hwnd, DWORD dwReserved, UINT cIDs, PGESTURECONFIG pGestureConfig, UINT cbSize); static LPSetGestureConfig pSetGestureConfig = nullptr; typedef WINBOOL WINAPI (*LPGetGestureInfo)(HGESTUREINFO hGestureInfo, PGESTUREINFO pGestureInfo); static LPGetGestureInfo pGetGestureInfo = nullptr; typedef WINBOOL WINAPI (*LPCloseGestureInfoHandle)(HGESTUREINFO hGestureInfo); static LPCloseGestureInfoHandle pCloseGestureInfoHandle = nullptr; typedef WINBOOL WINAPI (*LPGetPointerType)(UINT32 pointerId, POINTER_INPUT_TYPE *pointerType); static LPGetPointerType pGetPointerType = nullptr; typedef WINBOOL WINAPI (*LPGetPointerPenInfo)(UINT32 pointerId, POINTER_PEN_INFO *penInfo); static LPGetPointerPenInfo pGetPointerPenInfo = nullptr; typedef WINBOOL WINAPI (*LPGetPointerPenInfoHistory)(UINT32 pointerId, UINT32 *entriesCount, POINTER_PEN_INFO *penInfo); static LPGetPointerPenInfoHistory pGetPointerPenInfoHistory = nullptr; typedef UINT WINAPI (*LPGetDpiForWindow)(HWND hwnd); static LPGetDpiForWindow pGetDpiForWindow = nullptr; // -------------------------------------------------------------------- const wchar_t Canvas::className[] = L"ipeCanvasWindowClass"; // -------------------------------------------------------------------- void Canvas::invalidate() { InvalidateRect(hwnd, nullptr, FALSE); } void Canvas::invalidate(int x, int y, int w, int h) { RECT r; r.left = x; r.right = x + w; r.top = y; r.bottom = y + h; // ipeDebug("invalidate %d %d %d %d\n", r.left, r.right, r.top, r.bottom); InvalidateRect(hwnd, &r, FALSE); /* if (immediate && !isTransient) UpdateWindow(hwnd); // force immediate update */ } // -------------------------------------------------------------------- void Canvas::key(WPARAM wParam, LPARAM lParam) { int mod = 0; if (GetKeyState(VK_SHIFT) < 0) mod |= EShift; if (GetKeyState(VK_CONTROL) < 0) mod |= EControl; if (GetKeyState(VK_MENU) < 0) mod |= EAlt; // ipeDebug("Canvas::key(%x, %x) %x", wParam, lParam, mod); String t; t.append(char(wParam)); iTool->key(t, mod); } void Canvas::button(int button, bool down, int mod, Vector v) { POINT p; p.x = int(v.x); p.y = int(v.y); ClientToScreen(hwnd, &p); iGlobalPos = Vector(p.x, p.y); computeFifi(v.x, v.y); mod |= iAdditionalModifiers; if (iTool) iTool->mouseButton(button | mod, down); else if (down && iObserver) iObserver->canvasObserverMouseAction(button | mod); } void Canvas::mouseMove(Vector v) { // ipeDebug("Canvas::mouseMove %d %d", xPos, yPos); computeFifi(v.x, v.y); if (iTool) iTool->mouseMove(); if (iObserver) iObserver->canvasObserverPositionChanged(); } void Canvas::setCursor(TCursor cursor, double w, Color *color) { if (cursor == EDotCursor) { // Windows switches to a dot automatically when using the pen, // not implemented } else { // HandCursor, CrossCursor not implemented, // but they are also not used in Ipe now. } } // -------------------------------------------------------------------- void Canvas::updateSize() { RECT rc; GetClientRect(hwnd, &rc); iBWidth = iWidth = rc.right; iBHeight = iHeight = rc.bottom; } void Canvas::wndPaint() { PAINTSTRUCT ps; HDC hdc = BeginPaint(hwnd, &ps); if (!iWidth) updateSize(); refreshSurface(); int x0 = ps.rcPaint.left; int y0 = ps.rcPaint.top; int w = ps.rcPaint.right - x0; int h = ps.rcPaint.bottom - y0; // ipeDebug("wndPaint: %d %d", w, h); HBITMAP bits = CreateCompatibleBitmap(hdc, w, h); HDC bitsDC = CreateCompatibleDC(hdc); SelectObject(bitsDC, bits); cairo_surface_t *surface = cairo_win32_surface_create(bitsDC); cairo_t *cr = cairo_create(surface); cairo_translate(cr, -x0, -y0); cairo_set_source_surface(cr, iSurface, 0.0, 0.0); cairo_paint(cr); if (iFifiVisible) drawFifi(cr); if (iPage) { CairoPainter cp(iCascade, iFonts.get(), cr, iZoom, false); cp.transform(canvasTfm()); cp.pushMatrix(); drawTool(cp); cp.popMatrix(); } cairo_destroy(cr); cairo_surface_destroy(surface); BitBlt(hdc, x0, y0, w, h, bitsDC, 0, 0, SRCCOPY); DeleteDC(bitsDC); DeleteObject(bits); EndPaint(hwnd, &ps); } // -------------------------------------------------------------------- void Canvas::mouseButton(Canvas *canvas, int button, bool down, WPARAM wParam, LPARAM lParam) { if (canvas) { int xPos = GET_X_LPARAM(lParam); int yPos = GET_Y_LPARAM(lParam); int mod = 0; if (wParam & MK_SHIFT) mod |= EShift; if (wParam & MK_CONTROL) mod |= EControl; if (GetKeyState(VK_MENU) < 0) mod |= EAlt; canvas->button(button, down, mod, Vector(xPos, yPos)); } } Vector Canvas::location(HWND hwnd, POINT q, POINT h) { POINT p = q; ScreenToClient(hwnd, &p); return Vector(h.x / iHimetric.x + p.x - q.x, h.y / iHimetric.y + p.y - q.y); } LRESULT Canvas::handlePointerEvent(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { if (message == WM_POINTERCAPTURECHANGED) return 0; // ignore and stop gesture processing UINT32 pointerId = LOWORD(wParam); POINTER_INPUT_TYPE pointerType; if (pGetPointerType && pGetPointerType(pointerId, &pointerType) && pointerType == PT_PEN) { POINTER_PEN_INFO penInfo; if (pGetPointerPenInfo(pointerId, &penInfo)) { // bool incontact = penInfo.pointerInfo.pointerFlags & 0x4; bool firstButton = penInfo.pointerInfo.pointerFlags & 0x10; bool secondButton = penInfo.pointerInfo.pointerFlags & 0x20; int bt = firstButton ? 1 : (secondButton ? 2: 0); if (iHimetric.x == 0.0 || pointerId != iPointerId) { iPointerId = pointerId; iHimetric = Vector(double(penInfo.pointerInfo.ptHimetricLocationRaw.x) / penInfo.pointerInfo.ptPixelLocationRaw.x, double(penInfo.pointerInfo.ptHimetricLocationRaw.y) / penInfo.pointerInfo.ptPixelLocationRaw.y); ipeDebug("pointer hi %g", iHimetric.x); } Vector v = location(hwnd, penInfo.pointerInfo.ptPixelLocationRaw, penInfo.pointerInfo.ptHimetricLocationRaw); UINT32 entriesCount = penInfo.pointerInfo.historyCount; if (message == WM_POINTERDOWN) { button(bt, true, 0, v); } else if (message == WM_POINTERUP) { button(bt, false, 0, v); } else { if (entriesCount > 1) { POINTER_PEN_INFO *pi = new POINTER_PEN_INFO[entriesCount]; if (pGetPointerPenInfoHistory(pointerId, &entriesCount, pi)) { for (int i = entriesCount - 1; i >= 0; --i) { isTransient = (i > 0); mouseMove(location(hwnd, pi[i].pointerInfo.ptPixelLocationRaw, pi[i].pointerInfo.ptHimetricLocationRaw)); } } delete [] pi; } else mouseMove(v); } return 0; } } return DefWindowProc(hwnd, message, wParam, lParam); } LRESULT Canvas::handlePanGesture(DWORD flags, POINTS &p) { Vector v(p.x, -p.y); if (flags & GF_BEGIN) { iGestureStart = v; iGesturePan = pan(); } else { v = v - iGestureStart; setPan(iGesturePan - (1.0/zoom()) * v); update(); } return 0; } LRESULT Canvas::handleZoomGesture(DWORD flags, POINTS &p, ULONG d) { if (flags & GF_BEGIN) { iGestureDist = d; iGestureZoom = zoom(); } else { POINT q = { p.x, p.y }; ScreenToClient(hwnd, &q); Vector origin = devToUser(Vector(q.x, q.y)); Vector offset = iZoom * (pan() - origin); double nzoom = iGestureZoom * d / iGestureDist; setZoom(nzoom); setPan(origin + (1.0/nzoom) * offset); update(); if (iObserver) // scroll wheel hasn't moved, but update display of ppi iObserver->canvasObserverWheelMoved(0, 0, 0); } return 0; } LRESULT CALLBACK Canvas::wndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { Canvas *canvas = (Canvas *) GetWindowLongPtr(hwnd, GWLP_USERDATA); switch (message) { case WM_CREATE: { assert(canvas == nullptr); LPCREATESTRUCT p = (LPCREATESTRUCT) lParam; canvas = (Canvas *) p->lpCreateParams; canvas->hwnd = hwnd; SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR) canvas); } break; case WM_MOUSEACTIVATE: if (canvas) SetFocus(canvas->hwnd); return MA_ACTIVATE; case WM_KEYDOWN: if (lParam & 0x1000000) { // ipeDebug("Extended key: %d", wParam); if (canvas && canvas->iTool && wParam == VK_DELETE) { canvas->key(0x7f, lParam); return 0; } } break; case WM_CHAR: // ipeDebug("WM_CHAR: %d", wParam); if (canvas && canvas->iTool) { canvas->key(wParam, lParam); return 0; } break; case WM_MOUSEWHEEL: // ipeDebug("Mouse wheel %lx %lx", wParam, lParam); if (canvas && canvas->iObserver) canvas->iObserver->canvasObserverWheelMoved (0, GET_WHEEL_DELTA_WPARAM(wParam) / 8.0, ((wParam & MK_CONTROL) ? 2 : 0)); return 0; case WM_MOUSEHWHEEL: // ipeDebug("Mouse horizontal wheel %lx %lx", wParam, lParam); if (canvas && canvas->iObserver) canvas->iObserver->canvasObserverWheelMoved (GET_WHEEL_DELTA_WPARAM(wParam) / 8.0, 0, 0); break; case WM_PAINT: if (canvas) canvas->wndPaint(); return 0; case WM_SIZE: if (canvas) canvas->updateSize(); break; case WM_GESTURE: { if (!pGetGestureInfo || !canvas) break; // GetGestureInfo not available (Windows Vista or older) GESTUREINFO gi = {0}; gi.cbSize = sizeof(gi); BOOL res = pGetGestureInfo((HGESTUREINFO) lParam, &gi); if (!res) break; pCloseGestureInfoHandle((HGESTUREINFO) lParam); if (gi.dwID == GID_PAN) return canvas->handlePanGesture(gi.dwFlags, gi.ptsLocation); if (gi.dwID == GID_ZOOM) return canvas->handleZoomGesture(gi.dwFlags, gi.ptsLocation, gi.ullArguments); break; } case WM_MOUSEMOVE: if (canvas) { int xPos = GET_X_LPARAM(lParam); int yPos = GET_Y_LPARAM(lParam); canvas->mouseMove(Vector(xPos, yPos)); } break; case WM_LBUTTONDOWN: case WM_LBUTTONUP: // ignore touch events here // ipeDebug("extra = %x", GetMessageExtraInfo()); if ((GetMessageExtraInfo() & 0xffffff80) != 0xff515780) mouseButton(canvas, 1, message == WM_LBUTTONDOWN, wParam, lParam); break; case WM_LBUTTONDBLCLK: mouseButton(canvas, 0x81, true, wParam, lParam); break; case WM_RBUTTONDOWN: case WM_RBUTTONUP: mouseButton(canvas, 2, message == WM_RBUTTONDOWN, wParam, lParam); break; case WM_MBUTTONDOWN: case WM_MBUTTONUP: mouseButton(canvas, 4, message == WM_MBUTTONDOWN, wParam, lParam); break; case WM_XBUTTONDOWN: case WM_XBUTTONUP: { int but = (HIWORD(wParam) == XBUTTON2) ? 0x10 : 0x08; mouseButton(canvas, but, message == WM_XBUTTONDOWN, wParam, lParam); break; } case WM_GETMINMAXINFO: { LPMINMAXINFO mm = LPMINMAXINFO(lParam); ipeDebug("Canvas MINMAX %ld %ld", mm->ptMinTrackSize.x, mm->ptMinTrackSize.y); break; } case WM_POINTERDOWN: case WM_POINTERUP: case WM_POINTERUPDATE: case WM_POINTERCAPTURECHANGED: if (canvas && canvas->isInkMode) return canvas->handlePointerEvent(hwnd, message, wParam, lParam); break; case WM_DESTROY: ipeDebug("Windows canvas is destroyed"); delete canvas; break; // don't show in debug output: case WM_SETCURSOR: case WM_NCHITTEST: break; default: // ipeDebug("Canvas wndProc(%d)", message); break; } return DefWindowProc(hwnd, message, wParam, lParam); } // -------------------------------------------------------------------- Canvas::Canvas(HWND parent, HINSTANCE hInstance) : iHimetric(0., 0.) { if (hInstance == nullptr) hInstance = (HINSTANCE) GetWindowLongPtr(parent, GWLP_HINSTANCE); HWND hwnd = (parent == nullptr) ? CreateWindowExW(WS_EX_CLIENTEDGE, className, L"", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, nullptr, nullptr, hInstance, this) : CreateWindowExW(WS_EX_CLIENTEDGE, className, L"", WS_CHILD | WS_VISIBLE, 0, 0, 0, 0, parent, nullptr, hInstance, this); if (hwnd == nullptr) { MessageBoxA(nullptr, "Canvas creation failed!", "Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } assert(GetWindowLongPtr(hwnd, GWLP_USERDATA)); if (pSetGestureConfig) { DWORD panWant = GC_PAN | GC_PAN_WITH_SINGLE_FINGER_VERTICALLY | GC_PAN_WITH_SINGLE_FINGER_HORIZONTALLY | GC_PAN_WITH_GUTTER | GC_PAN_WITH_INERTIA; DWORD panBlock = 0; GESTURECONFIG gestureConfig[] = { { GID_PAN, panWant, panBlock }, { GID_ZOOM, GC_ZOOM, 0}, { GID_TWOFINGERTAP, 0, GC_TWOFINGERTAP } }; pSetGestureConfig(hwnd, 0, 3, gestureConfig, sizeof(GESTURECONFIG)); } isTransient = false; } UINT Canvas::getDpiForWindow(HWND hwnd) { if (pGetDpiForWindow) { UINT nDpi = pGetDpiForWindow(hwnd) * 100 / 96; ipeDebug("Updating DPI to %d", nDpi); return nDpi; } else return 100; } void Canvas::init(HINSTANCE hInstance) { WNDCLASSEX wc; wc.cbSize = sizeof(WNDCLASSEX); wc.style = CS_DBLCLKS; // CS_VREDRAW | CS_HREDRAW; wc.lpfnWndProc = wndProc; wc.cbClsExtra = 0; wc.cbWndExtra = 0; wc.hInstance = hInstance; wc.hCursor = LoadCursor(nullptr, IDC_ARROW); wc.hbrBackground = (HBRUSH) GetStockObject(NULL_BRUSH); wc.lpszMenuName = NULL; // actually child id wc.lpszClassName = className; wc.hIcon = NULL; wc.hIconSm = NULL; if (!RegisterClassExW(&wc)) { MessageBoxA(nullptr, "Canvas control registration failed!", "Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } // Check if GetGestureInfo is available (i.e. at least Windows 7) HMODULE hDll = LoadLibraryA("user32.dll"); if (hDll) { pSetGestureConfig = (LPSetGestureConfig) GetProcAddress(hDll, "SetGestureConfig"); pGetGestureInfo = (LPGetGestureInfo) GetProcAddress(hDll, "GetGestureInfo"); pCloseGestureInfoHandle = (LPCloseGestureInfoHandle) GetProcAddress(hDll, "CloseGestureInfoHandle"); pGetPointerType = (LPGetPointerType) GetProcAddress(hDll, "GetPointerType"); pGetPointerPenInfo = (LPGetPointerPenInfo) GetProcAddress(hDll, "GetPointerPenInfo"); pGetPointerPenInfoHistory = (LPGetPointerPenInfoHistory) GetProcAddress(hDll, "GetPointerPenInfoHistory"); pGetDpiForWindow = (LPGetDpiForWindow) GetProcAddress(hDll, "GetDpiForWindow"); } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipepdfview_win.cpp0000644000175000017500000001316013561570220020520 0ustar otfriedotfried// -------------------------------------------------------------------- // ipe::PdfView for Win // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipepdfview_win.h" #include "ipecairopainter.h" #include #include #include #include using namespace ipe; // -------------------------------------------------------------------- const wchar_t PdfView::className[] = L"ipePdfViewWindowClass"; // -------------------------------------------------------------------- void PdfView::invalidate() { InvalidateRect(hwnd, nullptr, FALSE); } void PdfView::invalidate(int x, int y, int w, int h) { RECT r; r.left = x; r.right = x + w; r.top = y; r.bottom = y + h; InvalidateRect(hwnd, &r, FALSE); } // -------------------------------------------------------------------- void PdfView::updateSize() { RECT rc; GetClientRect(hwnd, &rc); iBWidth = iWidth = rc.right; iBHeight = iHeight = rc.bottom; } void PdfView::wndPaint() { PAINTSTRUCT ps; HDC hdc = BeginPaint(hwnd, &ps); if (!iWidth) updateSize(); refreshSurface(); int x0 = ps.rcPaint.left; int y0 = ps.rcPaint.top; int w = ps.rcPaint.right - x0; int h = ps.rcPaint.bottom - y0; // ipeDebug("wndPaint: %d %d", w, h); HBITMAP bits = CreateCompatibleBitmap(hdc, w, h); HDC bitsDC = CreateCompatibleDC(hdc); SelectObject(bitsDC, bits); cairo_surface_t *surface = cairo_win32_surface_create(bitsDC); cairo_t *cr = cairo_create(surface); cairo_translate(cr, -x0, -y0); cairo_set_source_surface(cr, iSurface, 0.0, 0.0); cairo_paint(cr); cairo_destroy(cr); cairo_surface_destroy(surface); BitBlt(hdc, x0, y0, w, h, bitsDC, 0, 0, SRCCOPY); DeleteDC(bitsDC); DeleteObject(bits); EndPaint(hwnd, &ps); } // -------------------------------------------------------------------- LRESULT CALLBACK PdfView::wndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { PdfView *view = (PdfView *) GetWindowLongPtr(hwnd, GWLP_USERDATA); switch (message) { case WM_CREATE: { assert(view == nullptr); LPCREATESTRUCT p = (LPCREATESTRUCT) lParam; view = (PdfView *) p->lpCreateParams; view->hwnd = hwnd; SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR) view); } break; case WM_PAINT: if (view) view->wndPaint(); return 0; case WM_SIZE: if (view) { view->updateSize(); PostMessage(view->target, 0x8000, 0, 0); } break; case WM_LBUTTONDOWN: if (view) PostMessage(view->target, 0x8000, 0, 1); break; case WM_RBUTTONDOWN: case WM_MBUTTONDOWN: case WM_XBUTTONDOWN: if (view) PostMessage(view->target, 0x8000, 0, 2); break; case WM_CLOSE: return 0; // do NOT allow default procedure to close case WM_DESTROY: ipeDebug("Windows PdfView is destroyed"); delete view; break; // don't show in debug output: case WM_SETCURSOR: case WM_NCHITTEST: break; default: // ipeDebug("PdfView wndProc(%d)", message); break; } return DefWindowProc(hwnd, message, wParam, lParam); } // -------------------------------------------------------------------- PdfView::PdfView(HWND parent, HWND target, HINSTANCE hInstance) : target(target) { if (hInstance == nullptr) hInstance = (HINSTANCE) GetWindowLongPtr(parent, GWLP_HINSTANCE); HWND hwnd = (parent == nullptr) ? CreateWindowExW(WS_EX_CLIENTEDGE, className, L"", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, nullptr, nullptr, hInstance, this) : CreateWindowExW(WS_EX_CLIENTEDGE, className, L"", WS_CHILD | WS_VISIBLE, 0, 0, 0, 0, parent, nullptr, hInstance, this); if (hwnd == nullptr) { MessageBoxA(nullptr, "PdfView creation failed!", "Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } assert(GetWindowLongPtr(hwnd, GWLP_USERDATA)); } void PdfView::init(HINSTANCE hInstance) { WNDCLASSEX wc; wc.cbSize = sizeof(WNDCLASSEX); wc.style = CS_DBLCLKS; // CS_VREDRAW | CS_HREDRAW; wc.lpfnWndProc = wndProc; wc.cbClsExtra = 0; wc.cbWndExtra = 0; wc.hInstance = hInstance; wc.hCursor = LoadCursor(nullptr, IDC_ARROW); wc.hbrBackground = (HBRUSH) GetStockObject(NULL_BRUSH); wc.lpszMenuName = NULL; // actually child id wc.lpszClassName = className; wc.hIcon = NULL; wc.hIconSm = NULL; if (!RegisterClassExW(&wc)) { MessageBoxA(nullptr, "PdfView control registration failed!", "Error!", MB_ICONEXCLAMATION | MB_OK); exit(9); } } // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipepdfview_cocoa.cpp0000644000175000017500000000776113561570220021021 0ustar otfriedotfried/* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ // -------------------------------------------------------------------- // ipe::PdfView for Cocoa // -------------------------------------------------------------------- #include "ipepdfview_cocoa.h" #include "ipecairopainter.h" #include #include #include using namespace ipe; // -------------------------------------------------------------------- PdfView::PdfView(IpePdfView *view) { iView = view; } PdfView::~PdfView() { // nothing } void PdfView::invalidate() { NSSize s = [iView bounds].size; iWidth = s.width; iHeight = s.height; [iView setNeedsDisplayInRect:[iView bounds]]; } void PdfView::invalidate(int x, int y, int w, int h) { NSRect rect; rect.origin.x = x; rect.origin.y = iHeight - 1 - y - h; rect.size.width = w; rect.size.height = h; [iView setNeedsDisplayInRect:rect]; } void PdfView::drawRect(NSRect rect) { NSSize s = [iView bounds].size; NSSize sb = [iView convertSizeToBacking:s]; iWidth = s.width; iHeight = s.height; iBWidth = sb.width; iBHeight = sb.height; if (![iView inLiveResize]) refreshSurface(); CGContextRef myContext = [[NSGraphicsContext currentContext] CGContext]; CGContextTranslateCTM(myContext, 0.0, iHeight); CGContextScaleCTM(myContext, 1.0, -1.0); cairo_surface_t *surface = cairo_quartz_surface_create_for_cg_context(myContext, iWidth, iHeight); cairo_t *cr = cairo_create(surface); if (iSurface) { cairo_set_source_surface(cr, iSurface, 0.0, 0.0); int w = cairo_image_surface_get_width(iSurface); int h = cairo_image_surface_get_height(iSurface); if (iWidth != w || iHeight != h) { cairo_matrix_t matrix; cairo_matrix_init_scale(&matrix, w / iWidth, h / iHeight); cairo_pattern_set_matrix(cairo_get_source(cr), &matrix); } cairo_paint(cr); } cairo_destroy(cr); cairo_surface_finish(surface); cairo_surface_destroy(surface); } // -------------------------------------------------------------------- @implementation IpePdfView - (instancetype) initWithFrame:(NSRect) rect { if ([super initWithFrame:rect]) _pdfView = new PdfView(self); return self; } - (BOOL) acceptsFirstResponder { return YES; } - (BOOL) isOpaque { return YES; } - (void) drawRect:(NSRect) rect { self.pdfView->drawRect(rect); } - (void) mouseDown:(NSEvent *) event { id obj = self.window.delegate; if ([obj respondsToSelector:@selector(pdfViewMouseButton:)]) { [obj performSelector:@selector(pdfViewMouseButton:) withObject:event]; } } - (void) rightMouseDown:(NSEvent *) event { [self mouseDown:event]; } - (void) otherMouseDown:(NSEvent *) event { [self mouseDown:event]; } - (void) keyDown:(NSEvent *) event { [super keyDown:event]; } - (void) dealloc { // TODO: Is this actually called? NSLog(@"IpePdfView:dealloc"); delete self.pdfView; } @end // -------------------------------------------------------------------- ipe-7.2.13/src/ipecanvas/ipecanvas.h0000644000175000017500000001465113561570220017125 0ustar otfriedotfried// -*- C++ -*- // -------------------------------------------------------------------- // ipe::Canvas // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef IPECANVAS_H #define IPECANVAS_H #include "ipelib.h" // -------------------------------------------------------------------- // Avoid including cairo.h typedef struct _cairo cairo_t; typedef struct _cairo_surface cairo_surface_t; // -------------------------------------------------------------------- namespace ipe { class Fonts; class Tool; class PdfResources; // -------------------------------------------------------------------- class CanvasObserver { public: virtual ~CanvasObserver(); // kind = 0: precise pan, 1: osx 'imprecise' pan, 2: zoom virtual void canvasObserverWheelMoved(double xDegrees, double yDegrees, int kind); virtual void canvasObserverMouseAction(int button); virtual void canvasObserverPositionChanged(); virtual void canvasObserverToolChanged(bool hasTool); virtual void canvasObserverSizeChanged(); }; class CanvasBase { public: //! Keyboard modifiers enum TModifiers { EShift = 0x100, EControl = 0x200, EAlt = 0x400, EMeta = 0x800, ECommand = 0x1000 }; enum TCursor { EStandardCursor, EHandCursor, ECrossCursor, EDotCursor }; /*! In pretty display, no dashed lines are drawn around text objects, and if Latex font data is not available, no text is drawn at all. */ struct Style { Color paperColor; Color primarySelectionColor; Color secondarySelectionColor; bool pretty; bool classicGrid; double thinLine; double thickLine; int thinStep; int thickStep; bool paperClip; bool numberPages; }; virtual ~CanvasBase(); void setPage(const Page *page, int pno, int view, const Cascade *sheet); void setResources(const PdfResources *resources); //! Return current pan. inline Vector pan() const { return iPan; } //! Return current zoom. inline double zoom() const { return iZoom; } //! Return current style sheet cascade. inline const Cascade *cascade() const { return iCascade; } //! Return center of canvas. inline Vector center() const {return 0.5 * Vector(iWidth, iHeight); } //! Return last mouse position (snapped!) in user coordinates. inline Vector pos() const { return iMousePos; } //! Return last unsnapped mouse position in user coordinates. inline Vector unsnappedPos() const { return iUnsnappedMousePos; } //! Return global mouse position of last mouse press/release. inline Vector globalPos() const { return iGlobalPos; } Vector simpleSnapPos() const; //! Return current snapping information. inline const Snap &snap() const { return iSnap; } //! Set ink mode. inline void setInkMode(bool ink) { isInkMode = ink; } //! Return current additional modifiers. inline int additionalModifiers() const { return iAdditionalModifiers; } void setAdditionalModifiers(int mod); Vector devToUser(const Vector &arg) const; Vector userToDev(const Vector &arg) const; void setCanvasStyle(const Style &style); //! Return canvas style Style canvasStyle() const { return iStyle; } void setPan(const Vector &v); void setZoom(double zoom); void setSnap(const Snap &s); void setDimmed(bool dimmed); void setAutoOrigin(const Vector &v); Matrix canvasTfm() const; void setObserver(CanvasObserver *observer); void setFifiVisible(bool visible); void setSelectionVisible(bool visible); void setTool(Tool *tool); void finishTool(); Tool *tool() { return iTool; } void update(); void updateTool(); int canvasWidth() const { return iWidth; } int canvasHeight() const { return iHeight; } virtual void setCursor(TCursor cursor, double w = 1.0, Color *color = nullptr) = 0; static int selectPageOrView(Document *doc, int page = -1, int startIndex = 0, int pageWidth = 240, int width = 600, int height = 480); virtual void invalidate(int x, int y, int w, int h) = 0; protected: CanvasBase(); void drawPaper(cairo_t *cc); void drawFrame(cairo_t *cc); void drawAxes(cairo_t *cc); void drawGrid(cairo_t *cc); void drawObjects(cairo_t *cc); void drawTool(Painter &painter); void snapToPaperAndFrame(); void refreshSurface(); void computeFifi(double x, double y); void drawFifi(cairo_t *cr); virtual void invalidate() = 0; protected: CanvasObserver *iObserver; Tool *iTool; const Page *iPage; int iPageNumber; int iView; const Cascade *iCascade; Style iStyle; Vector iPan; double iZoom; Snap iSnap; bool iDimmed; bool iAutoSnap; Vector iAutoOrigin; int iAdditionalModifiers; bool isInkMode; bool iRepaintObjects; double iWidth, iHeight; double iBWidth, iBHeight; // size of backing store cairo_surface_t *iSurface; Vector iUnsnappedMousePos; Vector iMousePos; Vector iGlobalPos; Vector iOldFifi; // last fifi position that has been drawn bool iFifiVisible; Snap::TSnapModes iFifiMode; bool iSelectionVisible; const PdfResources *iResources; std::unique_ptr iFonts; }; } // namespace // -------------------------------------------------------------------- #endif ipe-7.2.13/src/Makefile0000644000175000017500000000226313561570220014466 0ustar otfriedotfried# -------------------------------------------------------------------- # Makefile for building all components of Ipe # -------------------------------------------------------------------- GOAL ?= all ifdef IPECROSS IPEQVORONOI = 1 endif subdirs = \ ipelib \ ipelets/lua \ ipetoipe \ ipe6upgrade \ ipeextract \ ipescript \ ipecairo \ iperender \ ipecanvas \ ipelua \ ipeui \ ipe \ ipepresenter \ ipecurl ifdef IPEQVORONOI subdirs += ipelets/qvoronoi endif .PHONY: all $(subdirs) all: $(subdirs) ipetoipe: ipelib ipelets/kgon: ipelib ipelets/qvoronoi: ipelib ipe6upgrade: ipelib ipeextract: ipelib ipecairo: ipelib iperender: ipelib ipecairo ipecanvas: ipelib ipecairo ipeview: ipecanvas ipelua: ipelib ipescript: ipelib ipelua ipe: ipecanvas ipelua ipepresenter: ipecanvas ipecurl: ipelib $(subdirs): $(MAKE) --directory=$@ $(GOAL) .PHONY: clean install clean: $(MAKE) GOAL=clean install: all $(MAKE) GOAL=install app: all $(MAKE) --directory=ipe app $(MAKE) --directory=ipe/icons app $(MAKE) --directory=ipelets/lua app $(MAKE) --directory=ipelets/qvoronoi app $(MAKE) --directory=ipepresenter app # -------------------------------------------------------------------- ipe-7.2.13/src/ipescript/0000755000175000017500000000000013561570220015025 5ustar otfriedotfriedipe-7.2.13/src/ipescript/ipescript.cpp0000644000175000017500000001235113561570220017535 0ustar otfriedotfried// -------------------------------------------------------------------- // ipescript.cpp // -------------------------------------------------------------------- /* This file is part of the extensible drawing editor Ipe. Copyright (c) 1993-2019 Otfried Cheong Ipe is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. As a special exception, you have permission to link Ipe with the CGAL library and distribute executables, as long as you follow the requirements of the Gnu General Public License in regard to all of the software in the executable aside from CGAL. Ipe is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Ipe; if not, you can find it at "http://www.gnu.org/copyleft/gpl.html", or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ipebase.h" #include "ipelua.h" #include #include using namespace ipe; using namespace ipelua; #ifdef WIN32 #define IPEPATHSEP (';') #else #define IPEPATHSEP (':') #endif // -------------------------------------------------------------------- static int traceback (lua_State *L) { if (!lua_isstring(L, 1)) /* 'message' not a string? */ return 1; /* keep it intact */ lua_rawgeti(L, LUA_REGISTRYINDEX, LUA_RIDX_GLOBALS); lua_getfield(L, -1, "debug"); if (!lua_istable(L, -1)) { lua_pop(L, 2); return 1; } lua_getfield(L, -1, "traceback"); if (!lua_isfunction(L, -1)) { lua_pop(L, 3); return 1; } lua_pushvalue(L, 1); // pass error message lua_pushinteger(L, 2); // skip this function and traceback luacall(L, 2, 1); // call debug.traceback return 1; } static void setup_config(lua_State *L, const char *var, const char *conf) { #ifdef IPEBUNDLE push_string(L, Platform::ipeDir(conf)); #else lua_pushstring(L, conf); #endif lua_setfield(L, -2, var); } // -------------------------------------------------------------------- static lua_State *setup_lua() { lua_State *L = luaL_newstate(); luaL_openlibs(L); luaopen_ipe(L); return L; } static void setup_globals(lua_State *L) { lua_getglobal(L, "package"); const char *pscripts = getenv("IPESCRIPTS"); if (pscripts) { String scripts(pscripts); String s; int i = 0; while (i < scripts.size()) { int j = i; while (i < scripts.size() && scripts[i] != IPEPATHSEP) i += 1; String d = scripts.substr(j, i-j); if (d == "_") #ifdef IPEBUNDLE d = Platform::ipeDir("scripts", nullptr); #else d = IPESCRIPTDIR; #endif d += "/?.lua"; if (!s.empty()) s += ';'; s += d; i += 1; } ipeDebug("package.path = %s", s.z()); lua_pushstring(L, s.z()); } else { String s = "./?.lua;"; #ifndef WIN32 const char *home = getenv("HOME"); if (home) { s += home; s += "/.ipe/scripts/?.lua;"; #ifdef __APPLE__ s += home; s += "/Library/Ipe/Scripts/?.lua;"; #endif } #endif #ifdef IPEBUNDLE s += Platform::ipeDir("scripts", "?.lua"); #else s += IPESCRIPTDIR "/?.lua"; #endif ipeDebug("package.path = %s", s.z()); lua_pushstring(L, s.z()); } lua_setfield(L, -2, "path"); lua_newtable(L); // config table #if defined(WIN32) lua_pushliteral(L, "win"); #elif defined(__APPLE__) lua_pushliteral(L, "apple"); #else lua_pushliteral(L, "unix"); #endif lua_setfield(L, -2, "platform"); #ifdef IPEBUNDLE setup_config(L, "system_styles", "styles"); #else setup_config(L, "system_styles", IPESTYLEDIR); #endif push_string(L, Platform::latexDirectory()); lua_setfield(L, -2, "latexdir"); lua_pushfstring(L, "Ipe %d.%d.%d", IPELIB_VERSION / 10000, (IPELIB_VERSION / 100) % 100, IPELIB_VERSION % 100); lua_setfield(L, -2, "version"); lua_setglobal(L, "config"); } // -------------------------------------------------------------------- static void usage() { fprintf(stderr, "Usage: ipescript
Ipelib
Here is a list of all class members with links to the classes they belong to:

- w -


ipe-7.2.13/build/doc/classipe_1_1_transform_tool-members.html0000644000175000017500000002473713561570220024026 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::TransformTool Member List

This is the complete list of members for ipe::TransformTool, including all inherited members.

compute(const Vector &v)ipe::TransformToolprotected
draw(Painter &painter) constipe::TransformToolvirtual
ERotate enum valueipe::TransformTool
EScale enum valueipe::TransformTool
EShear enum valueipe::TransformTool
EStretch enum valueipe::TransformTool
ETranslate enum valueipe::TransformTool
iCanvasipe::Toolprotected
iDiripe::TransformToolprotected
iMouseDownipe::TransformToolprotected
iOnlyHorizontalipe::TransformToolprotected
iOnlyVerticalipe::TransformToolprotected
iOriginipe::TransformToolprotected
iPageipe::TransformToolprotected
isValid() constipe::TransformTool
iTransformipe::TransformToolprotected
iTypeipe::TransformToolprotected
iValidipe::TransformToolprotected
iViewipe::TransformToolprotected
iWithShiftipe::TransformToolprotected
key(String text, int modifiers)ipe::Toolvirtual
mouseButton(int button, bool press)ipe::TransformToolvirtual
mouseMove()ipe::TransformToolvirtual
report()ipe::TransformToolvirtual
snapVtx(const Vector &mouse, Vector &pos, double &bound, bool cp) constipe::Toolvirtual
Tool(CanvasBase *canvas)ipe::Toolprotected
TransformTool(CanvasBase *canvas, Page *page, int view, TType type, bool withShift)ipe::TransformTool
TType enum nameipe::TransformTool
~Tool()ipe::Toolvirtual

ipe-7.2.13/build/doc/ipe.dtd0000644000175000017500000001410613561570220015354 0ustar otfriedotfried ipe-7.2.13/build/doc/classipe_1_1_curve-members.html0000644000175000017500000002207713561570220022075 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Curve Member List

This is the complete list of members for ipe::Curve, including all inherited members.

addToBBox(Rect &box, const Matrix &m, bool cp) constipe::Curvevirtual
appendArc(const Matrix &m, const Vector &v0, const Vector &v1)ipe::Curve
appendOldSpline(const std::vector< Vector > &v)ipe::Curveinline
appendSegment(const Vector &v0, const Vector &v1)ipe::Curve
appendSpline(const std::vector< Vector > &v)ipe::Curveinline
asClosedSpline() constipe::SubPathvirtual
asCurve() constipe::Curvevirtual
asEllipse() constipe::SubPathvirtual
closed() constipe::Curveinlinevirtual
closingSegment(Vector u[2]) constipe::Curve
countSegments() constipe::Curveinline
Curve()ipe::Curve
distance(const Vector &v, const Matrix &m, double bound) constipe::Curvevirtual
draw(Painter &painter) constipe::Curvevirtual
EClosedSpline enum valueipe::SubPath
ECurve enum valueipe::SubPath
EEllipse enum valueipe::SubPath
save(Stream &stream) constipe::Curvevirtual
segment(int i) constipe::Curve
setClosed(bool closed)ipe::Curve
snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Curvevirtual
snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) constipe::Curvevirtual
type() constipe::Curvevirtual
Type enum nameipe::SubPath
~SubPath()=0ipe::SubPathpure virtual

ipe-7.2.13/build/doc/functions_0x7e.html0000644000175000017500000001441413561570220017645 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- ~ -


ipe-7.2.13/build/doc/structipe_1_1_pdf_resources_1_1_s_page_number.html0000644000175000017500000001256213561570220025727 0ustar otfriedotfried Ipelib: ipe::PdfResources::SPageNumber Struct Reference
Ipelib
ipe::PdfResources::SPageNumber Struct Reference

#include <iperesources.h>

Public Attributes

int page
 
int view
 
std::unique_ptr< Texttext
 

Member Data Documentation

◆ page

int ipe::PdfResources::SPageNumber::page

◆ view

int ipe::PdfResources::SPageNumber::view

◆ text

std::unique_ptr<Text> ipe::PdfResources::SPageNumber::text

The documentation for this struct was generated from the following file:
  • iperesources.h

ipe-7.2.13/build/doc/manual_55.html0000644000175000017500000000564613561570220016567 0ustar otfriedotfried Ipe Manual -- 11.4 Ipeextract: extract XML stream from Ipe file
11.5 Ipe6upgrade: convert Ipe 6 files to Ipe 7 file format11 The command line programs11.3 Iperender: exporting to a bitmap, EPS, or SVG11.4 Ipeextract: extract XML stream from Ipe file

11.4 Ipeextract: extract XML stream from Ipe file

Ipeextract extracts the XML stream from an PDF or EPS file made by Ipe 6 or 7 and saves it in a file. It will work even if Ipe cannot actually parse the file, so you can use this tool to debug problems where Ipe fails to open your document.

ipeextract infile [ outfile ]
If not provided, the outfile is guessed by appending "xml" to the infile's basename.
ipe-7.2.13/build/doc/fontbbox.svg0000644000175000017500000002244713561570220016453 0ustar otfriedotfried ipe-7.2.13/build/doc/dir_7b54d492694b293bf8b54c70d2fe7f56.html0000644000175000017500000000644613561570220022163 0ustar otfriedotfried Ipelib: ipecairo Directory Reference
Ipelib
ipecairo Directory Reference

Files

file  ipecairopainter.cpp
 
file  ipecairopainter.h
 
file  ipefonts.cpp
 
file  ipefonts.h
 
file  ipethumbs.cpp
 
file  ipethumbs.h
 

ipe-7.2.13/build/doc/classipe_1_1_canvas_base.html0000644000175000017500000035657113561570220021577 0ustar otfriedotfried Ipelib: ipe::CanvasBase Class Reference
Ipelib

#include <ipecanvas.h>

Inherited by Canvas, ipe::Canvas, ipe::Canvas, and ipe::Canvas.

Classes

struct  Style
 

Public Types

enum  TModifiers {
  EShift = 0x100, EControl = 0x200, EAlt = 0x400, EMeta = 0x800,
  ECommand = 0x1000
}
 
enum  TCursor { EStandardCursor, EHandCursor, ECrossCursor, EDotCursor }
 

Public Member Functions

virtual ~CanvasBase ()
 
void setPage (const Page *page, int pno, int view, const Cascade *sheet)
 
void setResources (const PdfResources *resources)
 
Vector pan () const
 
double zoom () const
 
const Cascadecascade () const
 
Vector center () const
 
Vector pos () const
 
Vector unsnappedPos () const
 
Vector globalPos () const
 
Vector simpleSnapPos () const
 
const Snapsnap () const
 
void setInkMode (bool ink)
 
int additionalModifiers () const
 
void setAdditionalModifiers (int mod)
 
Vector devToUser (const Vector &arg) const
 
Vector userToDev (const Vector &arg) const
 
void setCanvasStyle (const Style &style)
 
Style canvasStyle () const
 
void setPan (const Vector &v)
 
void setZoom (double zoom)
 
void setSnap (const Snap &s)
 
void setDimmed (bool dimmed)
 
void setAutoOrigin (const Vector &v)
 
Matrix canvasTfm () const
 
void setObserver (CanvasObserver *observer)
 
void setFifiVisible (bool visible)
 
void setSelectionVisible (bool visible)
 
void setTool (Tool *tool)
 
void finishTool ()
 
Tooltool ()
 
void update ()
 
void updateTool ()
 
int canvasWidth () const
 
int canvasHeight () const
 
virtual void setCursor (TCursor cursor, double w=1.0, Color *color=nullptr)=0
 
virtual void invalidate (int x, int y, int w, int h)=0
 

Static Public Member Functions

static int selectPageOrView (Document *doc, int page=-1, int startIndex=0, int pageWidth=240, int width=600, int height=480)
 

Protected Member Functions

 CanvasBase ()
 
void drawPaper (cairo_t *cc)
 
void drawFrame (cairo_t *cc)
 
void drawAxes (cairo_t *cc)
 
void drawGrid (cairo_t *cc)
 
void drawObjects (cairo_t *cc)
 
void drawTool (Painter &painter)
 
void snapToPaperAndFrame ()
 
void refreshSurface ()
 
void computeFifi (double x, double y)
 
void drawFifi (cairo_t *cr)
 
virtual void invalidate ()=0
 

Protected Attributes

CanvasObserveriObserver
 
TooliTool
 
const PageiPage
 
int iPageNumber
 
int iView
 
const CascadeiCascade
 
Style iStyle
 
Vector iPan
 
double iZoom
 
Snap iSnap
 
bool iDimmed
 
bool iAutoSnap
 
Vector iAutoOrigin
 
int iAdditionalModifiers
 
bool isInkMode
 
bool iRepaintObjects
 
double iWidth
 
double iHeight
 
double iBWidth
 
double iBHeight
 
cairo_surface_t * iSurface
 
Vector iUnsnappedMousePos
 
Vector iMousePos
 
Vector iGlobalPos
 
Vector iOldFifi
 
bool iFifiVisible
 
Snap::TSnapModes iFifiMode
 
bool iSelectionVisible
 
const PdfResourcesiResources
 
std::unique_ptr< FontsiFonts
 

Member Enumeration Documentation

◆ TModifiers

Keyboard modifiers.

Enumerator
EShift 
EControl 
EAlt 
EMeta 
ECommand 

◆ TCursor

Enumerator
EStandardCursor 
EHandCursor 
ECrossCursor 
EDotCursor 

Constructor & Destructor Documentation

◆ ~CanvasBase()

CanvasBase::~CanvasBase ( )
virtual

destructor.

◆ CanvasBase()

CanvasBase::CanvasBase ( )
protected

Construct a new canvas.

Referenced by ipe::CanvasObserver::canvasObserverSizeChanged().

Member Function Documentation

◆ setPage()

void CanvasBase::setPage ( const Page page,
int  pno,
int  view,
const Cascade sheet 
)

Set the page to be displayed.

Doesn't take ownership of any argument. The page number pno is only needed if page numbering is turned on.

◆ setResources()

void CanvasBase::setResources ( const PdfResources resources)

set information about Latex fonts (from ipe::Document)

◆ pan()

Vector ipe::CanvasBase::pan ( ) const
inline

Return current pan.

Referenced by Canvas::magnify(), and ipe::PanTool::mouseButton().

◆ zoom()

double ipe::CanvasBase::zoom ( ) const
inline

◆ cascade()

const Cascade* ipe::CanvasBase::cascade ( ) const
inline

Return current style sheet cascade.

Referenced by ipe::PanTool::draw().

◆ center()

Vector ipe::CanvasBase::center ( ) const
inline

Return center of canvas.

◆ pos()

Vector ipe::CanvasBase::pos ( ) const
inline

Return last mouse position (snapped!) in user coordinates.

Referenced by ipe::TransformTool::mouseButton(), ipe::TransformTool::mouseMove(), and ipe::TransformTool::TransformTool().

◆ unsnappedPos()

Vector ipe::CanvasBase::unsnappedPos ( ) const
inline

◆ globalPos()

Vector ipe::CanvasBase::globalPos ( ) const
inline

Return global mouse position of last mouse press/release.

Referenced by ipe::Canvas::tabletEvent().

◆ simpleSnapPos()

Vector CanvasBase::simpleSnapPos ( ) const

Return snapped mouse position without angular snapping.

◆ snap()

const Snap& ipe::CanvasBase::snap ( ) const
inline

Return current snapping information.

Referenced by ipe::TransformTool::TransformTool().

◆ setInkMode()

void ipe::CanvasBase::setInkMode ( bool  ink)
inline

Set ink mode.

◆ additionalModifiers()

int ipe::CanvasBase::additionalModifiers ( ) const
inline

Return current additional modifiers.

◆ setAdditionalModifiers()

void CanvasBase::setAdditionalModifiers ( int  mod)

Set additional modifiers.

These modifier bits are passed to the Tool when a key is pressed or a drawing action is performed in addition to the actual keyboard modifiers.

◆ devToUser()

Vector CanvasBase::devToUser ( const Vector arg) const

Convert canvas (device) coordinates to user coordinates.

References ipe::Vector::x, and ipe::Vector::y.

Referenced by Canvas::magnify().

◆ userToDev()

Vector CanvasBase::userToDev ( const Vector arg) const

Convert user coordinates to canvas (device) coordinates.

References ipe::Vector::x, and ipe::Vector::y.

Referenced by ipe::Canvas::drawFifi().

◆ setCanvasStyle()

void CanvasBase::setCanvasStyle ( const Style style)

Set style of canvas drawing.

Includes paper color, pretty text, and grid.

◆ canvasStyle()

Style ipe::CanvasBase::canvasStyle ( ) const
inline

Return canvas style.

◆ setPan()

void CanvasBase::setPan ( const Vector v)

Set current pan position.

The pan position is the user coordinate that is displayed at the very center of the canvas.

Referenced by Canvas::magnify(), and ipe::PanTool::mouseButton().

◆ setZoom()

void CanvasBase::setZoom ( double  zoom)

Set current zoom factor.

The zoom factor maps user coordinates to screen pixel coordinates.

Referenced by Canvas::magnify().

◆ setSnap()

void CanvasBase::setSnap ( const Snap s)

Set the snapping information.

◆ setDimmed()

void CanvasBase::setDimmed ( bool  dimmed)

Dim whole canvas, except for the Tool.

This mode will be reset when the Tool finishes.

◆ setAutoOrigin()

void CanvasBase::setAutoOrigin ( const Vector v)

Enable automatic angular snapping with this origin.

Referenced by ipe::TransformTool::TransformTool().

◆ canvasTfm()

Matrix CanvasBase::canvasTfm ( ) const

Matrix mapping user coordinates to canvas coordinates.

Referenced by Canvas::drawRect(), and ipe::Canvas::paintEvent().

◆ setObserver()

void CanvasBase::setObserver ( CanvasObserver observer)

Set an observer.

Use 0 to delete current observer.

◆ setFifiVisible()

void CanvasBase::setFifiVisible ( bool  visible)

Set whether Fifi should be shown.

Fifi will only be shown if a snapping mode is active.

◆ setSelectionVisible()

void CanvasBase::setSelectionVisible ( bool  visible)

Set whether selection should be shown when there is no tool.

◆ setTool()

void CanvasBase::setTool ( Tool tool)

Set a new tool.

Calls canvasObserverToolChanged().

◆ finishTool()

◆ tool()

Tool* ipe::CanvasBase::tool ( )
inline

◆ update()

void CanvasBase::update ( )

Mark for update with redrawing of objects.

Referenced by Canvas::magnify().

◆ updateTool()

void CanvasBase::updateTool ( )

Mark for update with redrawing of tool only.

Referenced by ipe::SelectTool::key(), ipe::PanTool::mouseMove(), ipe::SelectTool::mouseMove(), and ipe::TransformTool::mouseMove().

◆ canvasWidth()

int ipe::CanvasBase::canvasWidth ( ) const
inline

◆ canvasHeight()

int ipe::CanvasBase::canvasHeight ( ) const
inline

◆ setCursor()

virtual void ipe::CanvasBase::setCursor ( TCursor  cursor,
double  w = 1.0,
Color color = nullptr 
)
pure virtual

◆ selectPageOrView()

int CanvasBase::selectPageOrView ( Document doc,
int  page = -1,
int  startIndex = 0,
int  pageWidth = 240,
int  width = 600,
int  height = 480 
)
static

Show dialog to select a page or a view.

If page is negative (the default), shows thumbnails of all pages of the document in a dialog. If the user selects a page, the page number is returned. If the dialog is canceled, -1 is returned.

If page is non-negative, all views of this page are shown, and the selected view number is returned.

itemWidth is the width of the page thumbnails (the height is computed automatically).

If page is negative (the default), shows thumbnails of all pages of the document in a dialog. If the user selects a page, the page number is returned. If the dialog is canceled, -1 is returned.

If page is non-negative, all views of this page are shown, and the selected view number is returned.

References ipe::Thumbnail::height(), and ipe::Thumbnail::width().

Referenced by ipe::PageSelector::fill().

◆ invalidate() [1/2]

virtual void ipe::CanvasBase::invalidate ( int  x,
int  y,
int  w,
int  h 
)
pure virtual

Implemented in ipe::Canvas.

◆ drawPaper()

void CanvasBase::drawPaper ( cairo_t *  cc)
protected

◆ drawFrame()

void CanvasBase::drawFrame ( cairo_t *  cc)
protected

◆ drawAxes()

void CanvasBase::drawAxes ( cairo_t *  cc)
protected

References ipe::Vector::x, and ipe::Vector::y.

◆ drawGrid()

void CanvasBase::drawGrid ( cairo_t *  cc)
protected

◆ drawObjects()

◆ drawTool()

void CanvasBase::drawTool ( Painter painter)
protected

Draw the current canvas tool.

If no tool is set, it draws the selected objects.

References ipe::EPrimarySelected, ipe::ESecondarySelected, ipe::Painter::setPen(), and ipe::Painter::setStroke().

Referenced by Canvas::drawRect(), and ipe::Canvas::paintEvent().

◆ snapToPaperAndFrame()

◆ refreshSurface()

void CanvasBase::refreshSurface ( )
protected

◆ computeFifi()

void CanvasBase::computeFifi ( double  x,
double  y 
)
protected

Stores the mouse position in iUnsnappedMousePos, computes Fifi if snapping is enabled, and stores snapped position in iMousePos.

References ipe::Snap::ESnapAuto, ipe::Snap::ESnapNone, ipe::Vector::x, and ipe::Vector::y.

Referenced by Canvas::drawRect(), ipe::Canvas::mouseButton(), Canvas::mouseMove(), ipe::Canvas::mouseMoveEvent(), and ipe::Canvas::tabletEvent().

◆ drawFifi()

◆ invalidate() [2/2]

virtual void ipe::CanvasBase::invalidate ( )
protectedpure virtual

Implemented in ipe::Canvas.

Member Data Documentation

◆ iObserver

◆ iTool

◆ iPage

const Page* ipe::CanvasBase::iPage
protected

◆ iPageNumber

int ipe::CanvasBase::iPageNumber
protected

◆ iView

int ipe::CanvasBase::iView
protected

◆ iCascade

const Cascade* ipe::CanvasBase::iCascade
protected

◆ iStyle

Style ipe::CanvasBase::iStyle
protected

◆ iPan

Vector ipe::CanvasBase::iPan
protected

◆ iZoom

double ipe::CanvasBase::iZoom
protected

◆ iSnap

Snap ipe::CanvasBase::iSnap
protected

◆ iDimmed

bool ipe::CanvasBase::iDimmed
protected

◆ iAutoSnap

bool ipe::CanvasBase::iAutoSnap
protected

◆ iAutoOrigin

Vector ipe::CanvasBase::iAutoOrigin
protected

◆ iAdditionalModifiers

int ipe::CanvasBase::iAdditionalModifiers
protected

◆ isInkMode

bool ipe::CanvasBase::isInkMode
protected

◆ iRepaintObjects

bool ipe::CanvasBase::iRepaintObjects
protected

Referenced by ipe::Canvas::~Canvas().

◆ iWidth

double ipe::CanvasBase::iWidth
protected

◆ iHeight

double ipe::CanvasBase::iHeight
protected

◆ iBWidth

double ipe::CanvasBase::iBWidth
protected

◆ iBHeight

double ipe::CanvasBase::iBHeight
protected

◆ iSurface

cairo_surface_t* ipe::CanvasBase::iSurface
protected

◆ iUnsnappedMousePos

Vector ipe::CanvasBase::iUnsnappedMousePos
protected

◆ iMousePos

Vector ipe::CanvasBase::iMousePos
protected

Referenced by ipe::Canvas::drawFifi().

◆ iGlobalPos

Vector ipe::CanvasBase::iGlobalPos
protected

◆ iOldFifi

Vector ipe::CanvasBase::iOldFifi
protected

Referenced by ipe::Canvas::drawFifi().

◆ iFifiVisible

bool ipe::CanvasBase::iFifiVisible
protected

◆ iFifiMode

Snap::TSnapModes ipe::CanvasBase::iFifiMode
protected

Referenced by ipe::Canvas::drawFifi().

◆ iSelectionVisible

bool ipe::CanvasBase::iSelectionVisible
protected

◆ iResources

const PdfResources* ipe::CanvasBase::iResources
protected

◆ iFonts

std::unique_ptr<Fonts> ipe::CanvasBase::iFonts
protected

Referenced by Canvas::drawRect().


The documentation for this class was generated from the following files:
  • ipecanvas.h
  • ipecanvas.cpp
  • ipeselector_cocoa.cpp
  • ipeselector_gtk.cpp
  • ipeselector_qt.cpp
  • ipeselector_win.cpp

ipe-7.2.13/build/doc/manual_28.html0000644000175000017500000000645713561570220016570 0ustar otfriedotfried Ipe Manual -- 7 Presentations
8 Advanced topicsTop6 Stylesheets7 Presentations

7 Presentations

An Ipe presentation is an Ipe PDF document that is presented using, for instance, Acrobat Reader and a video projector. Ipe has a number of features that make it easier to make such presentations.

The Windows and Linux versions of Ipe come with the presentation tool IpePresenter. It shows the current slide in one window (which you can make full screen on the external display), while showing the current slide, the next slide, notes for the current page, as well as a timer on your own display. IpePresenter not only works for Ipe presentations, but also for presentations made with beamer. It easily fits on and runs from a USB-stick, and does not require Latex on the computer where you give the presentation.

ipe-7.2.13/build/doc/classipe_1_1_stream-members.html0000644000175000017500000001267213561570220022244 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Stream Member List

This is the complete list of members for ipe::Stream, including all inherited members.

close()ipe::Streamvirtual
operator<<(char ch)ipe::Streaminline
operator<<(const String &s)ipe::Streaminline
operator<<(const char *s)ipe::Streaminline
operator<<(int i)ipe::Stream
operator<<(double d)ipe::Stream
putChar(char ch)=0ipe::Streampure virtual
putCString(const char *s)ipe::Streamvirtual
putHexByte(char b)ipe::Stream
putRaw(const char *data, int size)ipe::Streamvirtual
putString(String s)ipe::Streamvirtual
putXmlString(String s)ipe::Stream
~Stream()ipe::Streamvirtual

ipe-7.2.13/build/doc/classipe_1_1_bezier-members.html0000644000175000017500000001615513561570220022231 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Bezier Member List

This is the complete list of members for ipe::Bezier, including all inherited members.

approximate(double precision, std::vector< Vector > &result) constipe::Bezier
bbox() constipe::Bezier
Bezier()ipe::Bezierinline
Bezier(const Vector &p0, const Vector &p1, const Vector &p2, const Vector &p3)ipe::Bezierinline
closedSpline(int n, const Vector *v, std::vector< Bezier > &result)ipe::Bezierstatic
distance(const Vector &v, double bound)ipe::Bezier
intersect(const Line &l, std::vector< Vector > &result) constipe::Bezier
intersect(const Segment &l, std::vector< Vector > &result) constipe::Bezier
intersect(const Bezier &b, std::vector< Vector > &result) constipe::Bezier
iVipe::Bezier
oldSpline(int n, const Vector *v, std::vector< Bezier > &result)ipe::Bezierstatic
point(double t) constipe::Bezier
quadBezier(const Vector &p0, const Vector &p1, const Vector &p2)ipe::Bezierstatic
snap(const Vector &v, double &t, Vector &pos, double &bound) constipe::Bezier
spline(int n, const Vector *v, std::vector< Bezier > &result)ipe::Bezierstatic
straight(double precision) constipe::Bezier
subdivide(Bezier &l, Bezier &r) constipe::Bezier
tangent(double t) constipe::Bezier

ipe-7.2.13/build/doc/dir_91a90e6e897462a7bb8a7a0fc103953b.html0000644000175000017500000002055513561570220022137 0ustar otfriedotfried Ipelib: ipecanvas Directory Reference
Ipelib
ipecanvas Directory Reference

Files

file  ipecanvas.cpp
 
file  ipecanvas.h
 
file  ipecanvas_cocoa.cpp
 
file  ipecanvas_cocoa.h
 
file  ipecanvas_gtk.cpp
 
file  ipecanvas_gtk.h
 
file  ipecanvas_qt.cpp
 
file  ipecanvas_qt.h
 
file  ipecanvas_win.cpp
 
file  ipecanvas_win.h
 
file  ipepdfview.cpp
 
file  ipepdfview.h
 
file  ipepdfview_cocoa.cpp
 
file  ipepdfview_cocoa.h
 
file  ipepdfview_qt.cpp
 
file  ipepdfview_qt.h
 
file  ipepdfview_win.cpp
 
file  ipepdfview_win.h
 
file  ipeselector_cocoa.cpp
 
file  ipeselector_cocoa.h
 
file  ipeselector_gtk.cpp
 
file  ipeselector_qt.cpp
 
file  ipeselector_qt.h
 
file  ipeselector_win.cpp
 
file  ipetool.cpp
 
file  ipetool.h
 

ipe-7.2.13/build/doc/classipe_1_1_sub_path.html0000644000175000017500000006650713561570220021134 0ustar otfriedotfried Ipelib: ipe::SubPath Class Reference
Ipelib
ipe::SubPath Class Referenceabstract

#include <ipeshape.h>

Inherited by ipe::ClosedSpline, ipe::Curve, and ipe::Ellipse.

Public Types

enum  Type { ECurve, EEllipse, EClosedSpline }
 

Public Member Functions

virtual ~SubPath ()=0
 
virtual Type type () const =0
 
virtual bool closed () const
 
virtual const EllipseasEllipse () const
 
virtual const ClosedSplineasClosedSpline () const
 
virtual const CurveasCurve () const
 
virtual void save (Stream &stream) const =0
 
virtual void draw (Painter &painter) const =0
 
virtual void addToBBox (Rect &box, const Matrix &m, bool cp) const =0
 
virtual double distance (const Vector &v, const Matrix &m, double bound) const =0
 
virtual void snapVtx (const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) const =0
 
virtual void snapBnd (const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const =0
 

Detailed Description

A subpath of a Path.

A subpath is either open, or closed. There are two special kinds of closed subpaths, namely ellipses and closed B-splines.

Member Enumeration Documentation

◆ Type

The subpath types.

Enumerator
ECurve 
EEllipse 
EClosedSpline 

Constructor & Destructor Documentation

◆ ~SubPath()

SubPath::~SubPath ( )
pure virtual

Implementation of pure virtual destructor.

Referenced by ipe::Curve::closingSegment().

Member Function Documentation

◆ type()

virtual Type ipe::SubPath::type ( ) const
pure virtual

Return type of this subpath.

Implemented in ipe::Curve, ipe::ClosedSpline, and ipe::Ellipse.

Referenced by ipe::Shape::isSegment().

◆ closed()

bool SubPath::closed ( ) const
virtual

Is this subpath closed?

Default implementation returns true.

Reimplemented in ipe::Curve.

Referenced by ipe::Path::clone(), and ipe::Shape::isSegment().

◆ asEllipse()

const Ellipse * SubPath::asEllipse ( ) const
virtual

Return this object as an Ellipse, or nullptr if it's not an ellipse.

Reimplemented in ipe::Ellipse.

◆ asClosedSpline()

const ClosedSpline * SubPath::asClosedSpline ( ) const
virtual

Return this object as an ClosedSpline, or nullptr if it's not a closed spline.

Reimplemented in ipe::ClosedSpline.

◆ asCurve()

const Curve * SubPath::asCurve ( ) const
virtual

Return this object as an Curve, or else nullptr.

Reimplemented in ipe::Curve.

Referenced by ipe::Path::clone(), ipe::Path::draw(), and ipe::Shape::isSegment().

◆ save()

virtual void ipe::SubPath::save ( Stream stream) const
pure virtual

Save subpath to XML stream.

Implemented in ipe::Curve, ipe::ClosedSpline, and ipe::Ellipse.

◆ draw()

virtual void ipe::SubPath::draw ( Painter painter) const
pure virtual

Draw subpath (does not call drawPath()).

Implemented in ipe::Curve, ipe::ClosedSpline, and ipe::Ellipse.

◆ addToBBox()

virtual void ipe::SubPath::addToBBox ( Rect box,
const Matrix m,
bool  cp 
) const
pure virtual

Add subpath to box.

Implemented in ipe::Curve, ipe::ClosedSpline, and ipe::Ellipse.

◆ distance()

virtual double ipe::SubPath::distance ( const Vector v,
const Matrix m,
double  bound 
) const
pure virtual

Return distance from v to subpath transformed by m.

Implemented in ipe::Curve, ipe::ClosedSpline, and ipe::Ellipse.

◆ snapVtx()

virtual void ipe::SubPath::snapVtx ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound,
bool  cp 
) const
pure virtual

Snap to vertex.

Implemented in ipe::Curve, ipe::ClosedSpline, and ipe::Ellipse.

◆ snapBnd()

virtual void ipe::SubPath::snapBnd ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound 
) const
pure virtual

Snap to boundary of subpath.

Implemented in ipe::Curve, ipe::ClosedSpline, and ipe::Ellipse.


The documentation for this class was generated from the following files:
  • ipeshape.h
  • ipeshape.cpp

ipe-7.2.13/build/doc/namespacemembers_func.html0000644000175000017500000000411313561570220021307 0ustar otfriedotfried Ipelib: Namespace Members
Ipelib
 

ipe-7.2.13/build/doc/manual_41.html0000644000175000017500000001405713561570220016556 0ustar otfriedotfried Ipe Manual -- 8.7 Environment variables
8.8 Ipe on a USB-stick8 Advanced topics8.6 Customizing Ipe8.7 Environment variables

8.7 Environment variables

Ipe, ipetoipe, iperender, and ipescript respect the following environment variables:

IPELATEXDIR
the directory where Ipe runs Latex.
IPELATEXPATH
the directory that contains the pdflatex, xelatex, and lualatex commands. If not set, Ipe assumes the commands are on your path.
IPEDEBUG
set to 1 for debugging output.
IPEANCIENTPDFTEX
set this variable to use Pdftex versions older than 1.40.
IPETEXFORMAT
if set, Ipe will not call pdflatex but pdftex requesting the pdflatex format (and similarly for xetex and luatex). This is needed to use cygwin's latex.

The Ipe program uses several additional environment variables:

EDITOR
external editor to use for editing text objects.
IPESTYLES
a list of directories, separated by semicolons on Windows and colons otherwise, where Ipe looks for stylesheets, for instance for the standard stylesheet basic.isy. You can write _ (a single underscore) for the system-wide stylesheet directory. If this variable is not set, the default consists of the system-wide stylesheet directory, plus ~/.ipe/styles on Unix, plus ~/Library/Ipe/Styles on OS X.
IPELETPATH
a list of directories, separated by semicolons on Windows and colons otherwise, containing ipelets. You can write _ (a single underscore) for the system-wide ipelet directory. If this variable is not set, the default consists of the system-wide ipelet directory, plus ~/.ipe/ipelets on Unix, plus ~/Library/Ipe/Ipelets on OS X.
IPEICONDIR
directory containing icons for the Ipe user interface.
IPEDOCDIR
directory containing Ipe documentation.
IPELUAPATH
path for searching for Ipe Lua code.

The ipescript program uses the following environment variable:

IPESCRIPTS
a list of directories, separated by semicolons on Windows and colons otherwise, where ipescript looks for scripts. You can write _ (a single underscore) for the system-wide script directory. If this variable is not set, the default consists of the current directory and the system-wide script directory, plus ~/.ipe/scripts on Unix, plus ~/Library/Ipe/Scripts on OS X.

ipe.conf

Ipe allows you to set environment variables by writing the definitions in a file ipe.conf. On Windows, the file has to be in the top level of the Ipe directory (the same place that contains the readme.txt and gpl.txt files), on Linux and OSX it is simply .ipe/ipe.conf in your home directory. Each line of the file contains a setting for one environment variable, for instance like this:

IPEDEBUG=1
IPELATEXDIR=C:\latexrun
ipe-7.2.13/build/doc/classipe_1_1_ellipse-members.html0000644000175000017500000001625313561570220022405 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Ellipse Member List

This is the complete list of members for ipe::Ellipse, including all inherited members.

addToBBox(Rect &box, const Matrix &m, bool cp) constipe::Ellipsevirtual
asClosedSpline() constipe::SubPathvirtual
asCurve() constipe::SubPathvirtual
asEllipse() constipe::Ellipsevirtual
closed() constipe::SubPathvirtual
distance(const Vector &v, const Matrix &m, double bound) constipe::Ellipsevirtual
draw(Painter &painter) constipe::Ellipsevirtual
EClosedSpline enum valueipe::SubPath
ECurve enum valueipe::SubPath
EEllipse enum valueipe::SubPath
Ellipse(const Matrix &m)ipe::Ellipse
matrix() constipe::Ellipseinline
save(Stream &stream) constipe::Ellipsevirtual
snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Ellipsevirtual
snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) constipe::Ellipsevirtual
type() constipe::Ellipsevirtual
Type enum nameipe::SubPath
~SubPath()=0ipe::SubPathpure virtual

ipe-7.2.13/build/doc/classipe_1_1_file_stream-members.html0000644000175000017500000001407013561570220023235 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::FileStream Member List

This is the complete list of members for ipe::FileStream, including all inherited members.

close()ipe::Streamvirtual
FileStream(std::FILE *file)ipe::FileStream
operator<<(char ch)ipe::Streaminline
operator<<(const String &s)ipe::Streaminline
operator<<(const char *s)ipe::Streaminline
operator<<(int i)ipe::Stream
operator<<(double d)ipe::Stream
putChar(char ch)ipe::FileStreamvirtual
putCString(const char *s)ipe::FileStreamvirtual
putHexByte(char b)ipe::Stream
putRaw(const char *data, int size)ipe::FileStreamvirtual
putString(String s)ipe::FileStreamvirtual
putXmlString(String s)ipe::Stream
tell() constipe::FileStreamvirtual
~Stream()ipe::Streamvirtual

ipe-7.2.13/build/doc/classipe_1_1_a85_source.html0000644000175000017500000001377713561570220021305 0ustar otfriedotfried Ipelib: ipe::A85Source Class Reference
Ipelib

#include <ipeutils.h>

Inherits ipe::DataSource.

Public Member Functions

 A85Source (DataSource &source)
 
virtual int getChar ()
 
- Public Member Functions inherited from ipe::DataSource
virtual ~DataSource ()=0
 

Detailed Description

Filter source adding ASCII85 decoding.

Constructor & Destructor Documentation

◆ A85Source()

A85Source::A85Source ( DataSource source)

Member Function Documentation

◆ getChar()

int A85Source::getChar ( )
virtual

Get one more character, or EOF.

Implements ipe::DataSource.

References ipe::DataSource::getChar().

Referenced by ipe::Document::formatFromFilename().


The documentation for this class was generated from the following files:
  • ipeutils.h
  • ipeutils.cpp

ipe-7.2.13/build/doc/classipe_1_1_pdf_array-members.html0000644000175000017500000001470013561570220022712 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PdfArray Member List

This is the complete list of members for ipe::PdfArray, including all inherited members.

append(const PdfObj *)ipe::PdfArray
array() const noexceptipe::PdfArrayvirtual
boolean() const noexceptipe::PdfObjvirtual
count() const noexceptipe::PdfArrayinline
dict() const noexceptipe::PdfObjvirtual
name() const noexceptipe::PdfObjvirtual
null() const noexceptipe::PdfObjvirtual
number() const noexceptipe::PdfObjvirtual
obj(int index, const PdfFile *file) const noexceptipe::PdfArray
PdfArray()ipe::PdfArrayinlineexplicit
ref() const noexceptipe::PdfObjvirtual
repr() const noexceptipe::PdfObj
string() const noexceptipe::PdfObjvirtual
write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexceptipe::PdfArrayvirtual
~PdfArray()ipe::PdfArray
~PdfObj()=0ipe::PdfObjpure virtual

ipe-7.2.13/build/doc/classipe_1_1_document.html0000644000175000017500000023375613561570220021147 0ustar otfriedotfried Ipelib: ipe::Document Class Reference
Ipelib

#include <ipedoc.h>

Classes

struct  SProperties
 

Public Types

enum  LoadErrors { EVersionTooOld = -1, EVersionTooRecent = -2, EFileOpenError = -3, ENotAnIpeFile = -4 }
 
enum  {
  ErrNone, ErrNoText, ErrNoDir, ErrWritingSource,
  ErrOldPdfLatex, ErrRunLatex, ErrLatex, ErrLatexOutput
}
 

Public Member Functions

 Document ()
 
 Document (const Document &rhs)
 
Documentoperator= (const Document &rhs)=delete
 
 ~Document ()
 
bool save (TellStream &stream, FileFormat format, uint32_t flags) const
 
bool save (const char *fname, FileFormat format, uint32_t flags) const
 
bool exportPages (const char *fname, uint32_t flags, int fromPage, int toPage) const
 
bool exportView (const char *fname, FileFormat format, uint32_t flags, int pno, int vno) const
 
void saveAsXml (Stream &stream, bool usePdfBitmaps=false) const
 
int countPages () const
 
int countTotalViews () const
 
const Pagepage (int no) const
 
Pagepage (int no)
 
int findPage (String nameOrNumber) const
 
Pageset (int no, Page *page)
 
void insert (int no, Page *page)
 
void push_back (Page *page)
 
Pageremove (int no)
 
SProperties properties () const
 
void setProperties (const SProperties &info)
 
Cascadecascade ()
 
const Cascadecascade () const
 
CascadereplaceCascade (Cascade *cascade)
 
void setResources (PdfResources *resources)
 
const PdfResourcesresources () const noexcept
 
void findBitmaps (BitmapFinder &bm) const
 
bool checkStyle (AttributeSeq &seq) const
 
int runLatex (String docname, String &logFile)
 
int runLatex (String docname)
 

Static Public Member Functions

static FileFormat fileFormat (DataSource &source)
 
static FileFormat formatFromFilename (String fn)
 
static Documentload (DataSource &source, FileFormat format, int &reason)
 
static Documentload (const char *fname, int &reason)
 
static DocumentloadWithErrorReport (const char *fname)
 

Detailed Description

The model for an Ipe document.

The Document class represents the contents of an Ipe document, and all the methods necessary to load, save, and modify it.

Member Enumeration Documentation

◆ LoadErrors

Errors that can happen while loading documents.

Enumerator
EVersionTooOld 

The version of the file is too old.

EVersionTooRecent 

The file version is newer than this Ipelib.

EFileOpenError 

Error opening the file.

ENotAnIpeFile 

The file was not created by Ipe.

◆ anonymous enum

anonymous enum

Error codes returned by RunLatex.

Enumerator
ErrNone 
ErrNoText 
ErrNoDir 
ErrWritingSource 
ErrOldPdfLatex 
ErrRunLatex 
ErrLatex 
ErrLatexOutput 

Constructor & Destructor Documentation

◆ Document() [1/2]

Document::Document ( )

Construct an empty document for filling by a client.

As constructed, it has no pages, A4 media, and only the standard style sheet.

References ipe::Cascade::insert(), and ipe::StyleSheet::standard().

Referenced by formatFromFilename().

◆ Document() [2/2]

Document::Document ( const Document rhs)

Copy constructor.

References countPages(), ipe::DataSource::getChar(), and page().

◆ ~Document()

Document::~Document ( )

Destructor.

References countPages(), and page().

Member Function Documentation

◆ operator=()

Document& ipe::Document::operator= ( const Document rhs)
delete

◆ fileFormat()

FileFormat Document::fileFormat ( DataSource source)
static

Determine format of file in source.

References ipe::Eps, ipe::Ipe5, ipe::Pdf, ipe::String::substr(), ipe::Unknown, and ipe::Xml.

Referenced by load().

◆ formatFromFilename()

◆ load() [1/2]

Document * Document::load ( DataSource source,
FileFormat  format,
int &  reason 
)
static

Construct a document from an input stream.

Returns 0 if the stream couldn't be parsed, and a reason explaining that in reason. If reason is positive, it is a file (stream) offset where parsing failed. If reason is negative, it is an error code, see Document::LoadErrors.

References ENotAnIpeFile, ipe::Eps, EVersionTooOld, ipe::Ipe5, ipe::Pdf, and ipe::Xml.

Referenced by load(), and loadWithErrorReport().

◆ load() [2/2]

Document * Document::load ( const char *  fname,
int &  reason 
)
static

◆ loadWithErrorReport()

Document * Document::loadWithErrorReport ( const char *  fname)
static

◆ save() [1/2]

◆ save() [2/2]

bool Document::save ( const char *  fname,
FileFormat  format,
uint32_t  flags 
) const

References ipe::Platform::fopen(), and save().

◆ exportPages()

bool Document::exportPages ( const char *  fname,
uint32_t  flags,
int  fromPage,
int  toPage 
) const

◆ exportView()

bool Document::exportView ( const char *  fname,
FileFormat  format,
uint32_t  flags,
int  pno,
int  vno 
) const

◆ saveAsXml()

void Document::saveAsXml ( Stream stream,
bool  usePdfBitmaps = false 
) const

◆ countPages()

int ipe::Document::countPages ( ) const
inline

◆ countTotalViews()

int Document::countTotalViews ( ) const

Return total number of views in all pages.

References countPages(), ipe::Page::countViews(), and page().

◆ page() [1/2]

const Page* ipe::Document::page ( int  no) const
inline

Return page (const version).

The first page is no 0.

Referenced by checkStyle(), countTotalViews(), Document(), ipe::PageSelector::fill(), findBitmaps(), findPage(), insert(), runLatex(), saveAsXml(), set(), and ~Document().

◆ page() [2/2]

Page* ipe::Document::page ( int  no)
inline

Return page.

The first page is no 0.

◆ findPage()

int Document::findPage ( String  s) const

Return page index given a section title or page number.

Input page numbers are 1-based strings. Returns -1 if page not found.

References countPages(), ipe::String::empty(), ipe::Lex::getInt(), page(), and ipe::Page::section().

◆ set()

Page * Document::set ( int  no,
Page page 
)

Replace page.

Returns the original page.

References page().

◆ insert()

void Document::insert ( int  no,
Page page 
)

Insert a new page.

The page is inserted at index no.

References page().

◆ push_back()

void Document::push_back ( Page page)

Append a new page.

Referenced by ipe::ImlParser::parseDocument().

◆ remove()

Page * Document::remove ( int  no)

Remove a page.

Returns the page that has been removed.

◆ properties()

SProperties ipe::Document::properties ( ) const
inline

Return document properties.

Referenced by ipe::ImlParser::parseDocument(), and runLatex().

◆ setProperties()

void Document::setProperties ( const SProperties info)

Set document properties.

Referenced by ipe::ImlParser::parseDocument().

◆ cascade() [1/2]

Cascade* ipe::Document::cascade ( )
inline

◆ cascade() [2/2]

const Cascade* ipe::Document::cascade ( ) const
inline

Return stylesheet cascade (const version).

◆ replaceCascade()

Cascade * Document::replaceCascade ( Cascade sheets)

Replace the entire style sheet cascade.

Takes ownership of cascade, and returns the original cascade.

◆ setResources()

void Document::setResources ( PdfResources resources)

Update the PDF resources (after running latex).

Takes ownership.

References ipe::ImlParser::parseStyleSheet(), and resources().

Referenced by runLatex().

◆ resources()

const PdfResources* ipe::Document::resources ( ) const
inlinenoexcept

Return the current PDF resources.

Referenced by setResources(), and ipe::Thumbnail::Thumbnail().

◆ findBitmaps()

void Document::findBitmaps ( BitmapFinder bm) const

Create a list of all bitmaps in the document.

References ipe::Object::accept(), countPages(), ipe::ESymbol, ipe::BitmapFinder::iBitmaps, ipe::Symbol::iObject, page(), and ipe::BitmapFinder::scanPage().

Referenced by saveAsXml().

◆ checkStyle()

bool Document::checkStyle ( AttributeSeq seq) const

Check all symbolic attributes in the document.

This function verifies that all symbolic attributes in the document are defined in the style sheet. It appends to seq all symbolic attributes (in no particular order, but without duplicates) that are NOT defined.

Returns true if there are no undefined symbolic attributes in the document.

References cascade(), ipe::Object::checkStyle(), ipe::Page::count(), countPages(), ipe::Page::object(), and page().

◆ runLatex() [1/2]

◆ runLatex() [2/2]

int Document::runLatex ( String  docname)

Run Pdflatex (suitable for console applications)

Success/error is reported on stderr.

References ErrLatex, ErrLatexOutput, ErrNoDir, ErrNone, ErrNoText, ErrOldPdfLatex, ErrRunLatex, ErrWritingSource, and runLatex().


The documentation for this class was generated from the following files:
  • ipedoc.h
  • ipedoc.cpp

ipe-7.2.13/build/doc/intersection.svg0000644000175000017500000007167013561570220017342 0ustar otfriedotfried ipe-7.2.13/build/doc/snaplines.svg0000644000175000017500000001452513561570220016624 0ustar otfriedotfried ipe-7.2.13/build/doc/manual_9.html0000644000175000017500000000527113561570220016500 0ustar otfriedotfried Ipe Manual -- 3.6 Transparency
3.7 Symbolic and absolute attributes3 General Concepts3.5 Pen, dash style, arrows, and tiling patterns3.6 Transparency

3.6 Transparency

Ipe supports a simple model of transparency. You can set the opacity of path objects and text objects: an opacity of 1.0 means a fully opaque object, while 0.5 would mean that the object is half-transparent. All opacity values you wish to use in a document must be defined in its stylesheet.

ipe-7.2.13/build/doc/classipe_1_1_segment-members.html0000644000175000017500000001170013561570220022402 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Segment Member List

This is the complete list of members for ipe::Segment, including all inherited members.

distance(const Vector &v, double bound) constipe::Segment
distance(const Vector &v) constipe::Segment
intersects(const Segment &seg, Vector &pt) constipe::Segment
intersects(const Line &l, Vector &pt) constipe::Segment
iPipe::Segment
iQipe::Segment
line() constipe::Segmentinline
project(const Vector &v, Vector &projection) constipe::Segment
Segment()ipe::Segmentinline
Segment(const Vector &p, const Vector &q)ipe::Segmentinlineexplicit
snap(const Vector &mouse, Vector &pos, double &bound) constipe::Segment

ipe-7.2.13/build/doc/manual_30.html0000644000175000017500000001257613561570220016560 0ustar otfriedotfried Ipe Manual -- 7.2 Views
7.3 Bookmarks7 Presentations7.1 Presentation stylesheets7.2 Views

7.2 Views

When making a PDF presentation with Acrobat Reader, one would often like to present a page incrementally. For instance, I would first like to show a polygon, then add its triangulation, and finally color the vertices. Views make it possible to do this nicely.

An Ipe document consists of several pages, each of which can consist of an arbitrary number of views. When saving as PDF, each view generates a separate PDF page (if you only look at the result in, say, Acrobat reader, you cannot tell whether two pages are actually two views of the same Ipe page or two different Ipe pages).

An Ipe page consists of a number of objects, a number of layers, and a number of views. Each object belongs to exactly one layer. A layer can be shown by any number of views—a view is really just a list of layers to be presented. In addition, a view keeps a record of the current active layer—this makes it easy to move around your views and edit them. Finally, views can specify a graphic effect to be used by the PDF viewer when proceeding to the following PDF page.

To return to our polygon triangulation example, let's create an empty page. We draw a polygon into the default layer "alpha." Now use the New layer, new view function (in the Views menu), and draw the triangulation into the new layer "beta." Note that the function not only created a new layer, but also a second view showing both "alpha" and "beta". Try moving back and forth between the two views (using the PageUp and PageDown keys). You'll see changes in the layer list on the left: in view 1, layer "alpha" is selected and active, in view 2, both layers are selected and "beta" is active. Create a third layer and view, and mark the vertices.

Save in PDF format, and voila, you have a lovely little presentation. The result is available here.

In presentations, one often has slides with mostly text. The textbox object is convenient for this, as one doesn't need to use the mouse to create it. To create a slide where several text items appear one by one, one only needs to press F10 to create a textbox, then Shift+Ctrl+I to make a new view, F10 again for the next textbox, and so on. Finally, one moves the textboxes vertically for the most pleasing effect (Shift+Alt+Left Mouse does a constrained vertical translation, or Shift+Left Mouse in Translate mode).

Note that all views of a page receive the same bounding box, containing all objects visible on some view, plus all objects in a layer named "BBOX" (even if that layer is not visible). This can be used to force a larger bounding box without adding a white rectangle or the like.

If you need independent bounding boxes for each view, create a layer named "VIEWBBOX". Any view in which this layer is visible will receive a bounding box computed for the objects visible in this view only.

ipe-7.2.13/build/doc/classipe_1_1_pdf_obj-members.html0000644000175000017500000001207013561570220022344 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PdfObj Member List

This is the complete list of members for ipe::PdfObj, including all inherited members.

array() const noexceptipe::PdfObjvirtual
boolean() const noexceptipe::PdfObjvirtual
dict() const noexceptipe::PdfObjvirtual
name() const noexceptipe::PdfObjvirtual
null() const noexceptipe::PdfObjvirtual
number() const noexceptipe::PdfObjvirtual
ref() const noexceptipe::PdfObjvirtual
repr() const noexceptipe::PdfObj
string() const noexceptipe::PdfObjvirtual
write(Stream &stream, const PdfRenumber *renumber=nullptr, bool inflate=false) const noexcept=0ipe::PdfObjpure virtual
~PdfObj()=0ipe::PdfObjpure virtual

ipe-7.2.13/build/doc/classipe_1_1_all_attributes.html0000644000175000017500000010133713561570220022334 0ustar otfriedotfried Ipelib: ipe::AllAttributes Class Reference
Ipelib

#include <ipeattributes.h>

Public Member Functions

 AllAttributes ()
 

Public Attributes

TPathMode iPathMode
 
Attribute iStroke
 
Attribute iFill
 
Attribute iDashStyle
 
Attribute iPen
 
bool iFArrow
 
bool iRArrow
 
Attribute iFArrowShape
 
Attribute iRArrowShape
 
Attribute iFArrowSize
 
Attribute iRArrowSize
 
Attribute iSymbolSize
 
Attribute iTextSize
 
THorizontalAlignment iHorizontalAlignment
 
TVerticalAlignment iVerticalAlignment
 
Attribute iTextStyle
 
Attribute iLabelStyle
 
TPinned iPinned
 
bool iTransformableText
 
TTransformations iTransformations
 
TLineJoin iLineJoin
 
TLineCap iLineCap
 
TFillRule iFillRule
 
Attribute iOpacity
 
Attribute iStrokeOpacity
 
Attribute iTiling
 
Attribute iGradient
 
Attribute iMarkShape
 

Detailed Description

Collection of all object attributes.

Constructor & Destructor Documentation

◆ AllAttributes()

AllAttributes::AllAttributes ( )

Constructor sets default values.

Referenced by ipe::Attribute::normal().

Member Data Documentation

◆ iPathMode

TPathMode ipe::AllAttributes::iPathMode

Should we stroke and/or fill?

◆ iStroke

Attribute ipe::AllAttributes::iStroke

Stroke color.

Referenced by ipe::Latex::addPageNumber(), and ipe::Text::Text().

◆ iFill

Attribute ipe::AllAttributes::iFill

Fill color.

◆ iDashStyle

Attribute ipe::AllAttributes::iDashStyle

Dash style.

◆ iPen

Attribute ipe::AllAttributes::iPen

Pen (that is, line width).

◆ iFArrow

bool ipe::AllAttributes::iFArrow

Arrow forward?

◆ iRArrow

bool ipe::AllAttributes::iRArrow

Reverse arrow?

◆ iFArrowShape

Attribute ipe::AllAttributes::iFArrowShape

Shape of forward arrows.

◆ iRArrowShape

Attribute ipe::AllAttributes::iRArrowShape

Shape of reverse arrows.

◆ iFArrowSize

Attribute ipe::AllAttributes::iFArrowSize

Forward arrow size.

◆ iRArrowSize

Attribute ipe::AllAttributes::iRArrowSize

Reverse arrow size.

◆ iSymbolSize

Attribute ipe::AllAttributes::iSymbolSize

Symbol size.

◆ iTextSize

Attribute ipe::AllAttributes::iTextSize

Text size. Horizontal alignment of label objects.

Referenced by ipe::Latex::addPageNumber(), and ipe::Text::Text().

◆ iHorizontalAlignment

THorizontalAlignment ipe::AllAttributes::iHorizontalAlignment

◆ iVerticalAlignment

TVerticalAlignment ipe::AllAttributes::iVerticalAlignment

Vertical alignment of label objects.

Referenced by ipe::Latex::addPageNumber(), and ipe::Text::Text().

◆ iTextStyle

Attribute ipe::AllAttributes::iTextStyle

Text style for minipages.

Referenced by ipe::Text::Text().

◆ iLabelStyle

Attribute ipe::AllAttributes::iLabelStyle

Text style for labels.

Referenced by ipe::Text::Text().

◆ iPinned

TPinned ipe::AllAttributes::iPinned

Pinned status. Should newly created text be transformable?

Referenced by ipe::Object::Object().

◆ iTransformableText

bool ipe::AllAttributes::iTransformableText

If this is false, newly created text will only allow translations. Otherwise, the value of iTranslations is used (as for other objects).

Referenced by ipe::Text::Text().

◆ iTransformations

TTransformations ipe::AllAttributes::iTransformations

Allowed transformations.

Referenced by ipe::Object::Object().

◆ iLineJoin

TLineJoin ipe::AllAttributes::iLineJoin

Line join style.

◆ iLineCap

TLineCap ipe::AllAttributes::iLineCap

Line cap style.

◆ iFillRule

TFillRule ipe::AllAttributes::iFillRule

Shape fill rule.

◆ iOpacity

Attribute ipe::AllAttributes::iOpacity

Opacity.

Referenced by ipe::Text::Text().

◆ iStrokeOpacity

Attribute ipe::AllAttributes::iStrokeOpacity

Stroke opacity.

◆ iTiling

Attribute ipe::AllAttributes::iTiling

Tiling pattern.

◆ iGradient

Attribute ipe::AllAttributes::iGradient

Gradient pattern.

◆ iMarkShape

Attribute ipe::AllAttributes::iMarkShape

Shape of Mark to create.


The documentation for this class was generated from the following files:
  • ipeattributes.h
  • ipeattributes.cpp

ipe-7.2.13/build/doc/classipe_1_1_inflate_source-members.html0000644000175000017500000000612713561570220023751 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::InflateSource Member List

This is the complete list of members for ipe::InflateSource, including all inherited members.

getChar()ipe::InflateSourcevirtual
InflateSource(DataSource &source)ipe::InflateSource
~DataSource()=0ipe::DataSourcepure virtual
~InflateSource()ipe::InflateSourcevirtual

ipe-7.2.13/build/doc/tabs.css0000644000175000017500000002077213561570220015553 0ustar otfriedotfried.sm{position:relative;z-index:9999}.sm,.sm ul,.sm li{display:block;list-style:none;margin:0;padding:0;line-height:normal;direction:ltr;text-align:left;-webkit-tap-highlight-color:transparent}.sm-rtl,.sm-rtl ul,.sm-rtl li{direction:rtl;text-align:right}.sm>li>h1,.sm>li>h2,.sm>li>h3,.sm>li>h4,.sm>li>h5,.sm>li>h6{margin:0;padding:0}.sm ul{display:none}.sm li,.sm a{position:relative}.sm a{display:block}.sm a.disabled{cursor:not-allowed}.sm:after{content:"\00a0";display:block;height:0;font:0px/0 serif;clear:both;visibility:hidden;overflow:hidden}.sm,.sm *,.sm *:before,.sm *:after{-moz-box-sizing:border-box;-webkit-box-sizing:border-box;box-sizing:border-box}.sm-dox{background-image:url("tab_b.png")}.sm-dox a,.sm-dox a:focus,.sm-dox a:hover,.sm-dox a:active{padding:0px 12px;padding-right:43px;font-family:"Lucida Grande","Geneva","Helvetica",Arial,sans-serif;font-size:13px;font-weight:bold;line-height:36px;text-decoration:none;text-shadow:0px 1px 1px rgba(255,255,255,0.9);color:#283A5D;outline:none}.sm-dox a:hover{background-image:url("tab_a.png");background-repeat:repeat-x;color:#fff;text-shadow:0px 1px 1px #000}.sm-dox a.current{color:#D23600}.sm-dox a.disabled{color:#bbb}.sm-dox a span.sub-arrow{position:absolute;top:50%;margin-top:-14px;left:auto;right:3px;width:28px;height:28px;overflow:hidden;font:bold 12px/28px monospace !important;text-align:center;text-shadow:none;background:rgba(255,255,255,0.5);border-radius:5px}.sm-dox a.highlighted span.sub-arrow:before{display:block;content:'-'}.sm-dox>li:first-child>a,.sm-dox>li:first-child>:not(ul) a{border-radius:5px 5px 0 0}.sm-dox>li:last-child>a,.sm-dox>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul,.sm-dox>li:last-child>ul>li:last-child>a,.sm-dox>li:last-child>ul>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul>li:last-child>ul,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul{border-radius:0 0 5px 5px}.sm-dox>li:last-child>a.highlighted,.sm-dox>li:last-child>*:not(ul) a.highlighted,.sm-dox>li:last-child>ul>li:last-child>a.highlighted,.sm-dox>li:last-child>ul>li:last-child>*:not(ul) a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a.highlighted{border-radius:0}.sm-dox ul{background:rgba(162,162,162,0.1)}.sm-dox ul a,.sm-dox ul a:focus,.sm-dox ul a:hover,.sm-dox ul a:active{font-size:12px;border-left:8px solid transparent;line-height:36px;text-shadow:none;background-color:white;background-image:none}.sm-dox ul a:hover{background-image:url("tab_a.png");background-repeat:repeat-x;color:#fff;text-shadow:0px 1px 1px #000}.sm-dox ul ul a,.sm-dox ul ul a:hover,.sm-dox ul ul a:focus,.sm-dox ul ul a:active{border-left:16px solid transparent}.sm-dox ul ul ul a,.sm-dox ul ul ul a:hover,.sm-dox ul ul ul a:focus,.sm-dox ul ul ul a:active{border-left:24px solid transparent}.sm-dox ul ul ul ul a,.sm-dox ul ul ul ul a:hover,.sm-dox ul ul ul ul a:focus,.sm-dox ul ul ul ul a:active{border-left:32px solid transparent}.sm-dox ul ul ul ul ul a,.sm-dox ul ul ul ul ul a:hover,.sm-dox ul ul ul ul ul a:focus,.sm-dox ul ul ul ul ul a:active{border-left:40px solid transparent}@media (min-width: 768px){.sm-dox ul{position:absolute;width:12em}.sm-dox li{float:left}.sm-dox.sm-rtl li{float:right}.sm-dox ul li,.sm-dox.sm-rtl ul li,.sm-dox.sm-vertical li{float:none}.sm-dox a{white-space:nowrap}.sm-dox ul a,.sm-dox.sm-vertical a{white-space:normal}.sm-dox .sm-nowrap>li>a,.sm-dox .sm-nowrap>li>:not(ul) a{white-space:nowrap}.sm-dox{padding:0 10px;background-image:url("tab_b.png");line-height:36px}.sm-dox a span.sub-arrow{top:50%;margin-top:-2px;right:12px;width:0;height:0;border-width:4px;border-style:solid dashed dashed dashed;border-color:#283A5D transparent transparent transparent;background:transparent;border-radius:0}.sm-dox a,.sm-dox a:focus,.sm-dox a:active,.sm-dox a:hover,.sm-dox a.highlighted{padding:0px 12px;background-image:url("tab_s.png");background-repeat:no-repeat;background-position:right;border-radius:0 !important}.sm-dox a:hover{background-image:url("tab_a.png");background-repeat:repeat-x;color:#fff;text-shadow:0px 1px 1px #000}.sm-dox a:hover span.sub-arrow{border-color:#fff transparent transparent transparent}.sm-dox a.has-submenu{padding-right:24px}.sm-dox li{border-top:0}.sm-dox>li>ul:before,.sm-dox>li>ul:after{content:'';position:absolute;top:-18px;left:30px;width:0;height:0;overflow:hidden;border-width:9px;border-style:dashed dashed solid dashed;border-color:transparent transparent #bbb transparent}.sm-dox>li>ul:after{top:-16px;left:31px;border-width:8px;border-color:transparent transparent #fff transparent}.sm-dox ul{border:1px solid #bbb;padding:5px 0;background:#fff;border-radius:5px !important;box-shadow:0 5px 9px rgba(0,0,0,0.2)}.sm-dox ul a span.sub-arrow{right:8px;top:50%;margin-top:-5px;border-width:5px;border-color:transparent transparent transparent #555;border-style:dashed dashed dashed solid}.sm-dox ul a,.sm-dox ul a:hover,.sm-dox ul a:focus,.sm-dox ul a:active,.sm-dox ul a.highlighted{color:#555;background-image:none;border:0 !important;color:#555;background-image:none}.sm-dox ul a:hover{background-image:url("tab_a.png");background-repeat:repeat-x;color:#fff;text-shadow:0px 1px 1px #000}.sm-dox ul a:hover span.sub-arrow{border-color:transparent transparent transparent #fff}.sm-dox span.scroll-up,.sm-dox span.scroll-down{position:absolute;display:none;visibility:hidden;overflow:hidden;background:#fff;height:36px}.sm-dox span.scroll-up:hover,.sm-dox span.scroll-down:hover{background:#eee}.sm-dox span.scroll-up:hover span.scroll-up-arrow,.sm-dox span.scroll-up:hover span.scroll-down-arrow{border-color:transparent transparent #D23600 transparent}.sm-dox span.scroll-down:hover span.scroll-down-arrow{border-color:#D23600 transparent transparent transparent}.sm-dox span.scroll-up-arrow,.sm-dox span.scroll-down-arrow{position:absolute;top:0;left:50%;margin-left:-6px;width:0;height:0;overflow:hidden;border-width:6px;border-style:dashed dashed solid dashed;border-color:transparent transparent #555 transparent}.sm-dox span.scroll-down-arrow{top:8px;border-style:solid dashed dashed dashed;border-color:#555 transparent transparent transparent}.sm-dox.sm-rtl a.has-submenu{padding-right:12px;padding-left:24px}.sm-dox.sm-rtl a span.sub-arrow{right:auto;left:12px}.sm-dox.sm-rtl.sm-vertical a.has-submenu{padding:10px 20px}.sm-dox.sm-rtl.sm-vertical a span.sub-arrow{right:auto;left:8px;border-style:dashed solid dashed dashed;border-color:transparent #555 transparent transparent}.sm-dox.sm-rtl>li>ul:before{left:auto;right:30px}.sm-dox.sm-rtl>li>ul:after{left:auto;right:31px}.sm-dox.sm-rtl ul a.has-submenu{padding:10px 20px !important}.sm-dox.sm-rtl ul a span.sub-arrow{right:auto;left:8px;border-style:dashed solid dashed dashed;border-color:transparent #555 transparent transparent}.sm-dox.sm-vertical{padding:10px 0;border-radius:5px}.sm-dox.sm-vertical a{padding:10px 20px}.sm-dox.sm-vertical a:hover,.sm-dox.sm-vertical a:focus,.sm-dox.sm-vertical a:active,.sm-dox.sm-vertical a.highlighted{background:#fff}.sm-dox.sm-vertical a.disabled{background-image:url("tab_b.png")}.sm-dox.sm-vertical a span.sub-arrow{right:8px;top:50%;margin-top:-5px;border-width:5px;border-style:dashed dashed dashed solid;border-color:transparent transparent transparent #555}.sm-dox.sm-vertical>li>ul:before,.sm-dox.sm-vertical>li>ul:after{display:none}.sm-dox.sm-vertical ul a{padding:10px 20px}.sm-dox.sm-vertical ul a:hover,.sm-dox.sm-vertical ul a:focus,.sm-dox.sm-vertical ul a:active,.sm-dox.sm-vertical ul a.highlighted{background:#eee}.sm-dox.sm-vertical ul a.disabled{background:#fff}} ipe-7.2.13/build/doc/structipe_1_1_document_1_1_s_properties.html0000644000175000017500000003647413561570220024622 0ustar otfriedotfried Ipelib: ipe::Document::SProperties Struct Reference
Ipelib
ipe::Document::SProperties Struct Reference

#include <ipedoc.h>

Public Attributes

String iTitle
 
String iAuthor
 
String iSubject
 
String iKeywords
 
String iPreamble
 
LatexType iTexEngine { LatexType::Default }
 
bool iFullScreen { false }
 
bool iNumberPages { false }
 
String iCreated
 
String iModified
 
String iCreator
 

Detailed Description

Properties of a document.

Member Data Documentation

◆ iTitle

String ipe::Document::SProperties::iTitle

◆ iAuthor

String ipe::Document::SProperties::iAuthor

◆ iSubject

String ipe::Document::SProperties::iSubject

◆ iKeywords

String ipe::Document::SProperties::iKeywords

◆ iPreamble

String ipe::Document::SProperties::iPreamble

◆ iTexEngine

LatexType ipe::Document::SProperties::iTexEngine { LatexType::Default }

◆ iFullScreen

bool ipe::Document::SProperties::iFullScreen { false }

◆ iNumberPages

bool ipe::Document::SProperties::iNumberPages { false }

◆ iCreated

String ipe::Document::SProperties::iCreated

Date/time in PDF style "D:20010428191400" format.

Referenced by ipe::PdfWriter::createTrailer(), and ipe::ImlParser::parseDocument().

◆ iModified

String ipe::Document::SProperties::iModified

◆ iCreator

String ipe::Document::SProperties::iCreator

Program that created this document (e.g. "Ipe 7.5").

Referenced by ipe::PdfWriter::createTrailer(), and ipe::ImlParser::parseDocument().


The documentation for this struct was generated from the following file:
  • ipedoc.h

ipe-7.2.13/build/doc/open.png0000644000175000017500000000017313561570220015550 0ustar otfriedotfried‰PNG  IHDR à‘BIDATxíÝÁ €0 Ð׬ՙ\Àº€39—b!©9{|ðI>$#Àß´ý8/¨ÄØzƒ/Ï>2À[ÎgiU,/¬~¼Ï\ Ä9Ù¸IEND®B`‚ipe-7.2.13/build/doc/classipe_1_1_pdf_painter-members.html0000644000175000017500000006101413561570220023236 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PdfPainter Member List

This is the complete list of members for ipe::PdfPainter, including all inherited members.

addClipPath()ipe::Painter
cascade() constipe::Painterinline
closePath()ipe::Painter
curveTo(const Vector &v1, const Vector &v2, const Vector &v3)ipe::Painter
curveTo(const Bezier &bezier)ipe::Painterinline
dashStyle() constipe::Painterinline
dashStyle(std::vector< double > &dashes, double &offset) constipe::Painter
doAddClipPath()ipe::PdfPainterprotectedvirtual
doClosePath()ipe::PdfPainterprotectedvirtual
doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3)ipe::PdfPainterprotectedvirtual
doDrawArc(const Arc &arc)ipe::Painterprotectedvirtual
doDrawBitmap(Bitmap bitmap)ipe::PdfPainterprotectedvirtual
doDrawPath(TPathMode mode)ipe::PdfPainterprotectedvirtual
doDrawSymbol(Attribute symbol)ipe::PdfPainterprotectedvirtual
doDrawText(const Text *text)ipe::PdfPainterprotectedvirtual
doLineTo(const Vector &v)ipe::PdfPainterprotectedvirtual
doMoveTo(const Vector &v)ipe::PdfPainterprotectedvirtual
doNewPath()ipe::PdfPainterprotectedvirtual
doPop()ipe::PdfPainterprotectedvirtual
doPush()ipe::PdfPainterprotectedvirtual
drawArc(const Arc &arc)ipe::Painter
drawArcAsBezier(double alpha)ipe::Painterprotected
drawAttributes()ipe::PdfPainterprotected
drawBitmap(Bitmap bitmap)ipe::Painter
drawColor(Stream &stream, Color color, const char *gray, const char *rgb)ipe::PdfPainterstatic
drawEllipse()ipe::Painter
drawOpacity(bool withStroke)ipe::PdfPainterprotected
drawPath(TPathMode mode)ipe::Painter
drawSymbol(Attribute symbol)ipe::Painter
drawText(const Text *text)ipe::Painter
fill() constipe::Painterinline
fillRule() constipe::Painterinline
gradient() constipe::Painterinline
iActiveStateipe::PdfPainterprotected
iCascadeipe::Painterprotected
iInPathipe::Painterprotected
iMatrixipe::Painterprotected
iStateipe::Painterprotected
iStreamipe::PdfPainterprotected
lineCap() constipe::Painterinline
lineJoin() constipe::Painterinline
lineTo(const Vector &v)ipe::Painter
matrix() constipe::Painterinline
moveTo(const Vector &v)ipe::Painter
newPath()ipe::Painter
opacity() constipe::Painterinline
Painter(const Cascade *style)ipe::Painter
PdfPainter(const Cascade *style, Stream &stream)ipe::PdfPainter
pen() constipe::Painterinline
pop()ipe::Painter
popMatrix()ipe::Painter
push()ipe::Painter
pushMatrix()ipe::Painter
rect(const Rect &re)ipe::Painter
setDashStyle(Attribute dash)ipe::Painter
setFill(Attribute color)ipe::Painter
setFillRule(TFillRule rule)ipe::Painter
setGradient(Attribute grad)ipe::Painter
setLineCap(TLineCap cap)ipe::Painter
setLineJoin(TLineJoin join)ipe::Painter
setOpacity(Attribute opaq)ipe::Painter
setPen(Attribute pen)ipe::Painter
setState(const State &state)ipe::Painter
setStroke(Attribute color)ipe::Painter
setStrokeOpacity(Attribute opaq)ipe::Painter
setSymFill(Attribute color)ipe::Painter
setSymPen(Attribute wid)ipe::Painter
setSymStroke(Attribute color)ipe::Painter
setTiling(Attribute til)ipe::Painter
state() constipe::Painterinline
stroke() constipe::Painterinline
strokeOpacity() constipe::Painterinline
symFill() constipe::Painterinline
symPen() constipe::Painterinline
symStroke() constipe::Painterinline
tiling() constipe::Painterinline
transform(const Matrix &m)ipe::Painter
translate(const Vector &v)ipe::Painter
untransform(TTransformations trans)ipe::Painter
~Painter()ipe::Paintervirtual
~PdfPainter()ipe::PdfPainterinlinevirtual

ipe-7.2.13/build/doc/classipe_1_1_page.html0000644000175000017500000043167313561570220020243 0ustar otfriedotfried Ipelib: ipe::Page Class Reference
Ipelib

#include <ipepage.h>

Public Member Functions

 Page ()
 
void saveAsXml (Stream &stream) const
 
void saveAsIpePage (Stream &stream) const
 
void saveSelection (Stream &stream) const
 
int countLayers () const noexcept
 
String layer (int index) const noexcept
 
bool isLocked (int i) const noexcept
 
bool hasSnapping (int i) const noexcept
 
bool objSnapsInView (int objNo, int view) const noexcept
 
void setLocked (int i, bool flag)
 
void setSnapping (int i, bool flag)
 
void moveLayer (int index, int newIndex)
 
int findLayer (String name) const
 
void addLayer (String name)
 
void addLayer ()
 
void removeLayer (String name)
 
void renameLayer (String oldName, String newName)
 
int countViews () const
 
int countMarkedViews () const
 
Attribute effect (int index) const
 
void setEffect (int index, Attribute sym)
 
String active (int index) const
 
void setActive (int index, String name)
 
String viewName (int index) const noexcept
 
void setViewName (int index, String name) noexcept
 
bool markedView (int index) const
 
void setMarkedView (int index, bool marked)
 
void insertView (int i, String active)
 
void removeView (int i)
 
void clearViews ()
 
int findView (String viewNumberOrName) const
 
bool visible (int view, int layer) const
 
bool objectVisible (int view, int objno) const
 
void setVisible (int view, String layer, bool vis)
 
String title () const
 
void setTitle (String title)
 
String section (int level) const
 
void setSection (int level, bool useTitle, String name)
 
bool sectionUsesTitle (int level) const
 
const TexttitleText () const
 
void applyTitleStyle (const Cascade *sheet)
 
bool marked () const
 
void setMarked (bool marked)
 
String notes () const
 
void setNotes (String notes)
 
int count () const
 
void objectsPerLayer (std::vector< int > &objcounts) const
 
Objectobject (int i)
 
const Objectobject (int i) const
 
TSelect select (int i) const
 
int layerOf (int i) const
 
void setSelect (int i, TSelect sel)
 
void setLayerOf (int i, int layer)
 
Rect pageBBox (const Cascade *sheet) const
 
Rect viewBBox (const Cascade *sheet, int view) const
 
Rect bbox (int i) const
 
void transform (int i, const Matrix &m)
 
double distance (int i, const Vector &v, double bound) const
 
void snapVtx (int i, const Vector &mouse, Vector &pos, double &bound) const
 
void snapCtl (int i, const Vector &mouse, Vector &pos, double &bound) const
 
void snapBnd (int i, const Vector &mouse, Vector &pos, double &bound) const
 
void invalidateBBox (int i) const
 
void insert (int i, TSelect sel, int layer, Object *obj)
 
void append (TSelect sel, int layer, Object *obj)
 
void remove (int i)
 
void replace (int i, Object *obj)
 
bool setAttribute (int i, Property prop, Attribute value)
 
int primarySelection () const
 
bool hasSelection () const
 
void deselectAll ()
 
void ensurePrimarySelection ()
 

Static Public Member Functions

static Pagebasic ()
 

Detailed Description

An Ipe document page.

Its main ingredients are a sequence of Objects (with selection state, layer, and a cached bounding box), a set of Layers, and a sequence of Views.

Each object on a Page belongs to one of the layers of the page. Layers are orthogonal to the back-to-front ordering of objects (in particular, they are not "layered" - the word is a misnomer). The "layer" is really just another attribute of the object.

  • Layers are either editable or locked. Objects in a locked layer cannot be selected, and a locked layer cannot be made active in the UI. This more or less means that the contents of such a layer cannot be modified—but that's a consequence of the UI, Ipelib contains no special handling of locked layers.
  • A layer may have snapping on or off—objects will behave magnetically only if their layer has snapping on.

A Page is presented in a number of views. Each view presents some of the layers of the page. In addition, each view has an active layer (where objects are added when this view is shown in the UI), and possibly a transition effect (Acrobat Reader eye candy).

A Page can be copied and assigned. The operation takes time linear in the number of top-level object on the page.

Constructor & Destructor Documentation

◆ Page()

Page::Page ( )
explicit

The default constructor creates a new empty page.

This page still needs a layer and a view to be usable!

Referenced by basic().

Member Function Documentation

◆ basic()

Page * Page::basic ( )
static

Create a new empty page with standard settings.

This is an empty page with layer 'alpha' and a single view.

References addLayer(), insertView(), Page(), and setVisible().

◆ saveAsXml()

◆ saveAsIpePage()

void Page::saveAsIpePage ( Stream stream) const

Copy whole page with bitmaps as <ipepage> into the stream.

References ipe::BitmapFinder::iBitmaps, saveAsXml(), ipe::Bitmap::saveAsXml(), ipe::BitmapFinder::scanPage(), and ipe::Bitmap::setObjNum().

◆ saveSelection()

void Page::saveSelection ( Stream stream) const

Copy selected objects as <ipeselection> into the stream.

References count(), ipe::BitmapFinder::iBitmaps, ipe::Bitmap::saveAsXml(), select(), and ipe::Bitmap::setObjNum().

◆ countLayers()

int ipe::Page::countLayers ( ) const
inlinenoexcept

◆ layer()

String ipe::Page::layer ( int  index) const
inlinenoexcept

◆ isLocked()

bool ipe::Page::isLocked ( int  i) const
inlinenoexcept

◆ hasSnapping()

bool ipe::Page::hasSnapping ( int  i) const
inlinenoexcept

Does layer i have active snapping?

References addLayer(), findLayer(), moveLayer(), objSnapsInView(), removeLayer(), renameLayer(), setLocked(), and setSnapping().

Referenced by objSnapsInView().

◆ objSnapsInView()

bool Page::objSnapsInView ( int  objNo,
int  view 
) const
noexcept

Snapping occurs if the layer is visible and has snapping enabled.

References hasSnapping(), layer(), layerOf(), and visible().

Referenced by hasSnapping(), and ipe::Snap::simpleSnap().

◆ setLocked()

void Page::setLocked ( int  i,
bool  flag 
)

Set locking of layer i.

Referenced by hasSnapping(), and ipe::ImlParser::parsePage().

◆ setSnapping()

void Page::setSnapping ( int  i,
bool  flag 
)

Set snapping of layer i.

Referenced by hasSnapping().

◆ moveLayer()

void Page::moveLayer ( int  index,
int  newIndex 
)

Moves the position of a layer in the layer list.

References layer().

Referenced by hasSnapping().

◆ findLayer()

int Page::findLayer ( String  name) const

◆ addLayer() [1/2]

void Page::addLayer ( String  name)

Add a new layer.

References countViews().

Referenced by basic(), and ipe::ImlParser::parsePage().

◆ addLayer() [2/2]

void Page::addLayer ( )

Add a new layer with unique name.

References findLayer().

Referenced by hasSnapping().

◆ removeLayer()

void Page::removeLayer ( String  name)

Removes an empty layer from the page.

All objects are adjusted. Panics if there are objects in the deleted layer, of if it is the only layer.

References findLayer().

Referenced by hasSnapping().

◆ renameLayer()

void Page::renameLayer ( String  oldName,
String  newName 
)

Rename a layer.

References findLayer().

Referenced by hasSnapping().

◆ countViews()

◆ countMarkedViews()

int Page::countMarkedViews ( ) const

References count(), countViews(), and markedView().

Referenced by countViews().

◆ effect()

Attribute ipe::Page::effect ( int  index) const
inline

Return effect of view.

References setEffect().

Referenced by ipe::PdfWriter::createPageView(), and saveAsXml().

◆ setEffect()

void Page::setEffect ( int  index,
Attribute  sym 
)

Set effect of view.

Panics if sym is not symbolic.

References ipe::Attribute::isSymbolic().

Referenced by effect(), and ipe::ImlParser::parsePage().

◆ active()

String ipe::Page::active ( int  index) const
inline

Return active layer of view.

References setActive().

Referenced by insertView(), markedView(), and saveAsXml().

◆ setActive()

void Page::setActive ( int  index,
String  name 
)

Set active layer of view.

References findLayer(), and layer().

Referenced by active(), and ipe::ImlParser::parsePage().

◆ viewName()

String ipe::Page::viewName ( int  index) const
inlinenoexcept

Return name of view.

Referenced by ipe::PageSelector::fill(), findView(), and saveAsXml().

◆ setViewName()

void ipe::Page::setViewName ( int  index,
String  name 
)
inlinenoexcept

Set name of view.

Referenced by ipe::ImlParser::parsePage().

◆ markedView()

bool ipe::Page::markedView ( int  index) const
inline

Return if view is marked.

References active(), clearViews(), findView(), insertView(), marked(), removeView(), and setMarkedView().

Referenced by countMarkedViews(), and saveAsXml().

◆ setMarkedView()

void Page::setMarkedView ( int  index,
bool  marked 
)

Set if view is marked.

References marked().

Referenced by markedView(), and ipe::ImlParser::parsePage().

◆ insertView()

void Page::insertView ( int  i,
String  active 
)

Insert a new view at index i.

References active(), and countLayers().

Referenced by basic(), markedView(), and ipe::ImlParser::parsePage().

◆ removeView()

void Page::removeView ( int  i)

Remove the view at index i.

References countLayers().

Referenced by markedView().

◆ clearViews()

void Page::clearViews ( )

Remove all views of this page.

Referenced by markedView().

◆ findView()

int Page::findView ( String  s) const

Return index of view with given number or name.

Input numbers are one-based. Returns -1 if no such view exists.

References countViews(), ipe::String::empty(), ipe::ENotSelected, ipe::Lex::getInt(), and viewName().

Referenced by markedView().

◆ visible()

bool ipe::Page::visible ( int  view,
int  layer 
) const
inline

Is layer visible in view?

References layer().

Referenced by ipe::PdfWriter::createPageView(), objSnapsInView(), pageBBox(), and saveAsXml().

◆ objectVisible()

bool ipe::Page::objectVisible ( int  view,
int  objno 
) const
inline

◆ setVisible()

void Page::setVisible ( int  view,
String  layer,
bool  vis 
)

Set visibility of layer layer in view view.

References findLayer().

Referenced by basic(), objectVisible(), and ipe::ImlParser::parsePage().

◆ title()

String Page::title ( ) const

◆ setTitle()

void Page::setTitle ( String  title)

Set the title of this page.

An empty title is not displayed.

References ipe::Text::setText(), and title().

Referenced by objectVisible(), and ipe::ImlParser::parsePage().

◆ section()

String Page::section ( int  level) const

Return section title at level.

Level 0 is the section, level 1 the subsection.

References title().

Referenced by ipe::Document::findPage(), and objectVisible().

◆ setSection()

void Page::setSection ( int  level,
bool  useTitle,
String  name 
)

Set the section title at level.

Level 0 is the section, level 1 the subsection.

If useTitle is true, then name is ignored, and the section title will be copied from the page title (and further changes to the page title are automatically reflected).

Referenced by objectVisible(), and ipe::ImlParser::parsePage().

◆ sectionUsesTitle()

bool ipe::Page::sectionUsesTitle ( int  level) const
inline

Does this section title reflect the page title?

References applyTitleStyle(), and titleText().

◆ titleText()

const Text * Page::titleText ( ) const

Return Text object representing the title text.

Return 0 if no title is set. Ownership of object remains with Page.

References title().

Referenced by ipe::Latex::scanPage(), sectionUsesTitle(), and ipe::PdfWriter::~PdfWriter().

◆ applyTitleStyle()

◆ marked()

bool ipe::Page::marked ( ) const
inline

Return if page is marked for printing.

References setMarked().

Referenced by markedView(), setMarked(), and setMarkedView().

◆ setMarked()

void Page::setMarked ( bool  marked)

Set if page is marked for printing.

References marked().

Referenced by marked(), and ipe::ImlParser::parsePage().

◆ notes()

String ipe::Page::notes ( ) const
inline

Return notes for this page.

References setNotes().

Referenced by ipe::PdfWriter::createPageView(), and setNotes().

◆ setNotes()

void Page::setNotes ( String  notes)

Set the notes of this page.

References notes().

Referenced by notes(), and ipe::ImlParser::parsePage().

◆ count()

◆ objectsPerLayer()

void Page::objectsPerLayer ( std::vector< int > &  objcounts) const

Return number of objects in each layer.

References countLayers().

Referenced by count().

◆ object() [1/2]

◆ object() [2/2]

const Object* ipe::Page::object ( int  i) const
inline

Return object at index i (const version).

◆ select()

TSelect ipe::Page::select ( int  i) const
inline

◆ layerOf()

int ipe::Page::layerOf ( int  i) const
inline

◆ setSelect()

void ipe::Page::setSelect ( int  i,
TSelect  sel 
)
inline

Set selection status of object at index i.

Referenced by deselectAll(), ensurePrimarySelection(), and ipe::SelectTool::mouseButton().

◆ setLayerOf()

◆ pageBBox()

Rect Page::pageBBox ( const Cascade sheet) const

Returns a precise bounding box for the artwork on the page.

This is meant to be used as the bounding box in PDF output. It is computed by rendering all objects on the page that are visible in at least one view, plus all objects in a layer named "BBOX" (even if that is not visible), using a BBoxPainter.

References ipe::BBoxPainter::bbox(), count(), countLayers(), countViews(), layer(), layerOf(), and visible().

Referenced by ipe::PdfWriter::createPageView(), ipe::Thumbnail::saveRender(), and setLayerOf().

◆ viewBBox()

Rect Page::viewBBox ( const Cascade sheet,
int  view 
) const

Returns a precise bounding box for the artwork in the view.

This is meant to be used as the bounding box in PDF and EPS output. It is computed by rendering all objects in the page using a BBoxPainter.

References ipe::BBoxPainter::bbox(), count(), and objectVisible().

Referenced by ipe::PdfWriter::createPageView(), and setLayerOf().

◆ bbox()

Rect Page::bbox ( int  i) const

Return a bounding box for the object at index i.

This is a bounding box including the control points of the object. If you need a tight bounding box, you'll need to use the Object directly.

The Page caches the box the first time it is computed.

Make sure you call Page::transform instead of Object::setMatrix, as the latter would not invalidate the bounding box.

Referenced by ipe::PdfWriter::createPageView(), distance(), setLayerOf(), snapBnd(), snapCtl(), snapVtx(), and ipe::TransformTool::TransformTool().

◆ transform()

void Page::transform ( int  i,
const Matrix m 
)

Transform the object at index i.

Use this function instead of calling Object::setMatrix directly, as the latter doesn't invalidate the cached bounding box.

References invalidateBBox(), object(), and ipe::Object::setMatrix().

Referenced by setLayerOf().

◆ distance()

double Page::distance ( int  i,
const Vector v,
double  bound 
) const

Return distance between object at index i and v.

But may just return bound if the distance is larger. This function uses the cached bounded box, and is faster than calling Object::distance directly.

References bbox(), ipe::Object::distance(), and object().

Referenced by ipe::SelectTool::SelectTool(), and setLayerOf().

◆ snapVtx()

void Page::snapVtx ( int  i,
const Vector mouse,
Vector pos,
double &  bound 
) const

Compute possible vertex snapping position for object at index i.

Looks only for positions closer than bound. If successful, modifies pos and bound.

References bbox(), object(), and ipe::Object::snapVtx().

Referenced by setLayerOf(), and ipe::Snap::simpleSnap().

◆ snapCtl()

void Page::snapCtl ( int  i,
const Vector mouse,
Vector pos,
double &  bound 
) const

Compute possible control point snapping position for object at index i.

Looks only for positions closer than bound. If successful, modifies pos and bound.

References bbox(), object(), and ipe::Object::snapCtl().

Referenced by setLayerOf(), and ipe::Snap::simpleSnap().

◆ snapBnd()

void Page::snapBnd ( int  i,
const Vector mouse,
Vector pos,
double &  bound 
) const

Compute possible boundary snapping position for object at index i.

Looks only for positions closer than bound. If successful, modifies pos and bound.

References bbox(), object(), and ipe::Object::snapBnd().

Referenced by setLayerOf(), and ipe::Snap::simpleSnap().

◆ invalidateBBox()

void Page::invalidateBBox ( int  i) const

Invalidate the bounding box at index i (the object is somehow changed).

Referenced by replace(), ipe::Latex::scanPage(), setAttribute(), setLayerOf(), and transform().

◆ insert()

void Page::insert ( int  i,
TSelect  select,
int  layer,
Object obj 
)

Insert a new object at index i.

Takes ownership of the object.

References layer(), and select().

Referenced by ipe::ImlParser::parsePage(), and setLayerOf().

◆ append()

void Page::append ( TSelect  select,
int  layer,
Object obj 
)

Append a new object.

Takes ownership of the object.

References layer(), and select().

Referenced by setLayerOf().

◆ remove()

void Page::remove ( int  i)

Remove the object at index i.

◆ replace()

void Page::replace ( int  i,
Object obj 
)

Replace the object at index i.

Takes ownership of obj.

References invalidateBBox().

Referenced by setLayerOf().

◆ setAttribute()

bool Page::setAttribute ( int  i,
Property  prop,
Attribute  value 
)

Set attribute prop of object at index i to value.

This method automatically invalidates the bounding box if a ETextSize property is actually changed.

References ipe::EPropTextSize, ipe::EPropTransformations, invalidateBBox(), object(), and ipe::Object::setAttribute().

Referenced by setLayerOf().

◆ primarySelection()

int Page::primarySelection ( ) const

Return index of primary selection.

Returns -1 if there is no primary selection.

References count(), ipe::EPrimarySelected, and select().

Referenced by ipe::SelectTool::mouseButton(), and setLayerOf().

◆ hasSelection()

bool Page::hasSelection ( ) const

Returns true iff any object on the page is selected.

References count(), and select().

Referenced by ipe::SelectTool::mouseButton(), and setLayerOf().

◆ deselectAll()

void Page::deselectAll ( )

Deselect all objects.

References count(), ipe::ENotSelected, and setSelect().

Referenced by ipe::SelectTool::mouseButton(), and setLayerOf().

◆ ensurePrimarySelection()

void Page::ensurePrimarySelection ( )

If no object is the primary selection, make the topmost secondary selection the primary one.

References count(), ipe::EPrimarySelected, ipe::ESecondarySelected, select(), and setSelect().

Referenced by ipe::SelectTool::mouseButton(), and setLayerOf().


The documentation for this class was generated from the following files:
  • ipepage.h
  • ipepage.cpp

ipe-7.2.13/build/doc/functions_m.html0000644000175000017500000001372013561570220017315 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- m -


ipe-7.2.13/build/doc/classipe_1_1_face-members.html0000644000175000017500000000735713561570220021653 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Face Member List

This is the complete list of members for ipe::Face, including all inherited members.

cairoFont() noexceptipe::Faceinline
Face(const PdfDict *d, const PdfResourceBase *resources) noexceptipe::Face
glyphIndex(int ch) noexceptipe::Face
matches(const PdfDict *d) const noexceptipe::Faceinline
type() const noexceptipe::Faceinline
width(int ch) const noexceptipe::Face
~Face() noexceptipe::Face

ipe-7.2.13/build/doc/namespacemembers_vars.html0000644000175000017500000000416713561570220021340 0ustar otfriedotfried Ipelib: Namespace Members
Ipelib
 
  • FILE_FORMAT : ipe
  • IPE_PI : ipe
  • IPELIB_VERSION : ipe
  • IPESEP : ipe
  • kind_names : ipe
  • OLDEST_FILE_FORMAT : ipe
  • property_names : ipe

ipe-7.2.13/build/doc/group__ipelet.html0000644000175000017500000000626413561570220017633 0ustar otfriedotfried Ipelib: The Ipelet interface
Ipelib
The Ipelet interface

Classes

class  ipe::Ipelet
 
class  ipe::IpeletHelper
 

Detailed Description

Implementation of Ipe plugins.

Ipelets are dynamically loaded plugins for Ipe written in Lua.

The Ipelet class makes it easy for ipelet authors to write ipelets in C++ without using Lua's C API. They only need to provide some boilerplate Lua code to define the labels and functions of the ipelet, and use the Lua function "loadIpelet" to load a DLL containing a C++ class derived from Ipelet. The run() method of this class can then be called from Lua. The C++ code has access to services provided by Ipe through an IpeletHelper object.

Ipelet derived classes are restricted to operate on the current page of the document, and cannot modify the StyleSheet or other properties of the document. If you wish to write an ipelet doing this, you need to work in Lua (or create a C++ library using the Lua C API).


ipe-7.2.13/build/doc/classipe_1_1_ipelet-members.html0000644000175000017500000000543013561570220022225 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Ipelet Member List

This is the complete list of members for ipe::Ipelet, including all inherited members.

ipelibVersion() const =0ipe::Ipeletpure virtual
run(int function, IpeletData *data, IpeletHelper *helper)=0ipe::Ipeletpure virtual
~Ipelet()=0ipe::Ipeletpure virtual

ipe-7.2.13/build/doc/class_canvas-members.html0000644000175000017500000007114213561570220021063 0ustar otfriedotfried Ipelib: Member List
Ipelib
Canvas Member List

This is the complete list of members for Canvas, including all inherited members.

additionalModifiers() constipe::CanvasBaseinline
button(bool press, NSEvent *event)Canvas
Canvas(IpeCanvasView *view)Canvas
CanvasBase()ipe::CanvasBaseprotected
canvasHeight() constipe::CanvasBaseinline
canvasStyle() constipe::CanvasBaseinline
canvasTfm() constipe::CanvasBase
canvasWidth() constipe::CanvasBaseinline
cascade() constipe::CanvasBaseinline
center() constipe::CanvasBaseinline
computeFifi(double x, double y)ipe::CanvasBaseprotected
devToUser(const Vector &arg) constipe::CanvasBase
drawAxes(cairo_t *cc)ipe::CanvasBaseprotected
drawFifi(cairo_t *cr)ipe::CanvasBaseprotected
drawFrame(cairo_t *cc)ipe::CanvasBaseprotected
drawGrid(cairo_t *cc)ipe::CanvasBaseprotected
drawObjects(cairo_t *cc)ipe::CanvasBaseprotected
drawPaper(cairo_t *cc)ipe::CanvasBaseprotected
drawRect(NSRect rect)Canvas
drawTool(Painter &painter)ipe::CanvasBaseprotected
EAlt enum valueipe::CanvasBase
ECommand enum valueipe::CanvasBase
EControl enum valueipe::CanvasBase
ECrossCursor enum valueipe::CanvasBase
EDotCursor enum valueipe::CanvasBase
EHandCursor enum valueipe::CanvasBase
EMeta enum valueipe::CanvasBase
EShift enum valueipe::CanvasBase
EStandardCursor enum valueipe::CanvasBase
finishTool()ipe::CanvasBase
globalPos() constipe::CanvasBaseinline
iAdditionalModifiersipe::CanvasBaseprotected
iAutoOriginipe::CanvasBaseprotected
iAutoSnapipe::CanvasBaseprotected
iBHeightipe::CanvasBaseprotected
iBWidthipe::CanvasBaseprotected
iCascadeipe::CanvasBaseprotected
iDimmedipe::CanvasBaseprotected
iFifiModeipe::CanvasBaseprotected
iFifiVisibleipe::CanvasBaseprotected
iFontsipe::CanvasBaseprotected
iGlobalPosipe::CanvasBaseprotected
iHeightipe::CanvasBaseprotected
iMousePosipe::CanvasBaseprotected
iObserveripe::CanvasBaseprotected
iOldFifiipe::CanvasBaseprotected
iPageipe::CanvasBaseprotected
iPageNumberipe::CanvasBaseprotected
iPanipe::CanvasBaseprotected
iRepaintObjectsipe::CanvasBaseprotected
iResourcesipe::CanvasBaseprotected
iSelectionVisibleipe::CanvasBaseprotected
isInkModeipe::CanvasBaseprotected
iSnapipe::CanvasBaseprotected
iStyleipe::CanvasBaseprotected
iSurfaceipe::CanvasBaseprotected
iToolipe::CanvasBaseprotected
iUnsnappedMousePosipe::CanvasBaseprotected
iWidthipe::CanvasBaseprotected
iZoomipe::CanvasBaseprotected
key(NSEvent *event)Canvas
magnify(NSEvent *event)Canvas
mouseMove(NSEvent *event)Canvas
pan() constipe::CanvasBaseinline
pos() constipe::CanvasBaseinline
refreshSurface()ipe::CanvasBaseprotected
scrollWheel(NSEvent *event)Canvas
selectPageOrView(Document *doc, int page=-1, int startIndex=0, int pageWidth=240, int width=600, int height=480)ipe::CanvasBasestatic
setAdditionalModifiers(int mod)ipe::CanvasBase
setAutoOrigin(const Vector &v)ipe::CanvasBase
setCanvasStyle(const Style &style)ipe::CanvasBase
setDimmed(bool dimmed)ipe::CanvasBase
setFifiVisible(bool visible)ipe::CanvasBase
setInkMode(bool ink)ipe::CanvasBaseinline
setObserver(CanvasObserver *observer)ipe::CanvasBase
setPage(const Page *page, int pno, int view, const Cascade *sheet)ipe::CanvasBase
setPan(const Vector &v)ipe::CanvasBase
setResources(const PdfResources *resources)ipe::CanvasBase
setSelectionVisible(bool visible)ipe::CanvasBase
setSnap(const Snap &s)ipe::CanvasBase
setTool(Tool *tool)ipe::CanvasBase
setZoom(double zoom)ipe::CanvasBase
simpleSnapPos() constipe::CanvasBase
snap() constipe::CanvasBaseinline
snapToPaperAndFrame()ipe::CanvasBaseprotected
TCursor enum nameipe::CanvasBase
TModifiers enum nameipe::CanvasBase
tool()ipe::CanvasBaseinline
unsnappedPos() constipe::CanvasBaseinline
update()ipe::CanvasBase
updateTool()ipe::CanvasBase
userToDev(const Vector &arg) constipe::CanvasBase
view()Canvasinline
zoom() constipe::CanvasBaseinline
~Canvas()Canvasvirtual
~CanvasBase()ipe::CanvasBasevirtual

ipe-7.2.13/build/doc/functions_func_u.html0000644000175000017500000000542713561570220020345 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- u -


ipe-7.2.13/build/doc/classipe_1_1_rect.html0000644000175000017500000013311313561570220020250 0ustar otfriedotfried Ipelib: ipe::Rect Class Reference
Ipelib

#include <ipegeo.h>

Public Member Functions

 Rect ()
 
 Rect (const Vector &c)
 
 Rect (const Vector &c1, const Vector &c2)
 
void clear ()
 
int isEmpty () const
 
double left () const
 
double right () const
 
double bottom () const
 
double top () const
 
Vector topRight () const
 
Vector bottomLeft () const
 
Vector topLeft () const
 
Vector bottomRight () const
 
Vector center () const
 
double width () const
 
double height () const
 
void addPoint (const Vector &rhs)
 
void addRect (const Rect &rhs)
 
void clipTo (const Rect &rhs)
 
bool contains (const Vector &rhs) const
 
bool contains (const Rect &rhs) const
 
bool certainClearance (const Vector &v, double bound) const
 
bool intersects (const Rect &rhs) const
 

Related Functions

(Note that these are not member functions.)

Streamoperator<< (Stream &stream, const Rect &rhs)
 

Detailed Description

Axis-parallel rectangle (which can be empty)

Constructor & Destructor Documentation

◆ Rect() [1/3]

ipe::Rect::Rect ( )
inlineexplicit

Create empty rectangle.

Referenced by ipe::Vector::snap().

◆ Rect() [2/3]

ipe::Rect::Rect ( const Vector c)
inlineexplicit

Create rectangle containing just the point c.

◆ Rect() [3/3]

Rect::Rect ( const Vector c1,
const Vector c2 
)
explicit

Create rectangle containing points c1 and c2.

Member Function Documentation

◆ clear()

void ipe::Rect::clear ( )
inline

Make rectangle empty.

Referenced by ipe::BBoxPainter::doNewPath().

◆ isEmpty()

int ipe::Rect::isEmpty ( ) const
inline

◆ left()

double ipe::Rect::left ( ) const
inline

Return left side.

Referenced by ipe::PdfViewBase::drawPaper().

◆ right()

double ipe::Rect::right ( ) const
inline

Return right side.

◆ bottom()

double ipe::Rect::bottom ( ) const
inline

Return bottom side.

Referenced by ipe::PdfViewBase::drawPaper().

◆ top()

double ipe::Rect::top ( ) const
inline

Return top side.

◆ topRight()

◆ bottomLeft()

◆ topLeft()

◆ bottomRight()

Vector ipe::Rect::bottomRight ( ) const
inline

◆ center()

Vector ipe::Rect::center ( ) const
inline

Return center of rectangle.

Referenced by ipe::Group::draw().

◆ width()

◆ height()

◆ addPoint()

◆ addRect()

void Rect::addRect ( const Rect rhs)

◆ clipTo()

void Rect::clipTo ( const Rect cbox)

Clip rectangle to fit inside cbox.

Does nothing if either rectangle is empty.

References isEmpty(), ipe::Vector::x, and ipe::Vector::y.

Referenced by ipe::Group::addToBBox(), ipe::BBoxPainter::doDrawBitmap(), ipe::BBoxPainter::doDrawPath(), and ipe::BBoxPainter::doDrawText().

◆ contains() [1/2]

bool Rect::contains ( const Vector rhs) const

Does (closed) rectangle contain the point?

References ipe::Vector::x, and ipe::Vector::y.

Referenced by ipe::SelectTool::mouseButton().

◆ contains() [2/2]

bool Rect::contains ( const Rect rhs) const

Does rectangle contain other rectangle?

References isEmpty(), ipe::Vector::x, and ipe::Vector::y.

◆ certainClearance()

bool Rect::certainClearance ( const Vector v,
double  bound 
) const

Returns false if the distance between the box and v is smaller than bound. Often returns true if their distance is larger than bound.

References bottomLeft(), topRight(), ipe::Vector::x, and ipe::Vector::y.

Referenced by ipe::Image::distance(), ipe::Bezier::distance(), and ipe::Bezier::snap().

◆ intersects()

bool Rect::intersects ( const Rect rhs) const

Does rectangle intersect other rectangle?

References isEmpty(), ipe::Vector::x, and ipe::Vector::y.

Referenced by ipe::SelectTool::mouseButton(), and ipe::Bezier::snap().

Friends And Related Function Documentation

◆ operator<<()

Stream & operator<< ( Stream stream,
const Rect rhs 
)
related

The documentation for this class was generated from the following files:
  • ipegeo.h
  • ipegeo.cpp

ipe-7.2.13/build/doc/manual_13.html0000644000175000017500000001001613561570220016544 0ustar otfriedotfried Ipe Manual -- 3.10 Layers
3.11 Mouse shortcuts3 General Concepts3.9 Groups3.10 Layers

3.10 Layers

A page of an Ipe document consists of one or more layers. Each object on the page belongs to a layer. There is no relationship between layers and the back-to-front ordering of objects, so the layer is really just an attribute of the object.

The layers of the current page are displayed in the layer list, at the bottom left of the Ipe window. The checkmark to the left of the layer name determines whether the layer is visible. The layer marked with a yellow background is the active layer. New objects are always created in the active layer. You can change the active layer by left-clicking on the layer name (on Windows, double-click on the layer name).

By right-clicking on a layer name, you open the layer context menu that allows you to change layer attributes, to rename layers, to delete empty layers, and to change the ordering of layers in the layer list (this ordering has no other significance).

A layer may be editable or locked. Objects can be selected and modified only if their layer is editable. Locked layer are displayed in the layer list with a pink background. You can lock and unlock layers from the layer context menu, but note that the active layer cannot be locked.

A layer may have snapping on or off—objects will behave magnetically only if their layer has snapping on. Layers without snapping are displayed dimmed in the layer list.

Layers are also used to create pages that are displayed incrementally in Acrobat Reader. Once you have distributed your objects over various layers, you can create views, which defines in what order which layers of the page are shown.

ipe-7.2.13/build/doc/functions_func_l.html0000644000175000017500000001215013561570220020323 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- l -


ipe-7.2.13/build/doc/classipe_1_1_attribute.html0000644000175000017500000031442013561570220021320 0ustar otfriedotfried Ipelib: ipe::Attribute Class Reference
Ipelib

#include <ipeattributes.h>

Public Member Functions

 Attribute ()
 
 Attribute (bool symbolic, String name)
 
 Attribute (Fixed value)
 
 Attribute (Color color)
 
 Attribute (THorizontalAlignment align)
 
 Attribute (TVerticalAlignment align)
 
 Attribute (TLineJoin join)
 
 Attribute (TLineCap cap)
 
 Attribute (TFillRule rule)
 
 Attribute (TPinned pin)
 
 Attribute (TTransformations trans)
 
 Attribute (TPathMode pm)
 
bool isSymbolic () const
 
bool isString () const
 
bool isColor () const
 
bool isNumber () const
 
bool isEnum () const
 
bool isBoolean () const
 
bool isNormal () const
 
int index () const
 
int internal () const
 
String string () const
 
Fixed number () const
 
Color color () const
 
bool boolean () const
 
THorizontalAlignment horizontalAlignment () const
 
TVerticalAlignment verticalAlignment () const
 
TLineJoin lineJoin () const
 
TLineCap lineCap () const
 
TFillRule fillRule () const
 
TPinned pinned () const
 
TTransformations transformations () const
 
TPathMode pathMode () const
 
bool operator== (const Attribute &rhs) const
 
bool operator!= (const Attribute &rhs) const
 
bool isArcArrow () const
 

Static Public Member Functions

static Attribute Boolean (bool flag)
 
static Attribute BLACK ()
 
static Attribute WHITE ()
 
static Attribute ONE ()
 
static Attribute NORMAL ()
 
static Attribute UNDEFINED ()
 
static Attribute BACKGROUND ()
 
static Attribute SYM_STROKE ()
 
static Attribute SYM_FILL ()
 
static Attribute SYM_PEN ()
 
static Attribute ARROW_NORMAL ()
 
static Attribute OPAQUE ()
 
static Attribute ARROW_ARC ()
 
static Attribute ARROW_FARC ()
 
static Attribute ARROW_PTARC ()
 
static Attribute ARROW_FPTARC ()
 
static Attribute makeColor (String str, Attribute deflt)
 
static Attribute makeScalar (String str, Attribute deflt)
 
static Attribute makeDashStyle (String str)
 
static Attribute makeTextSize (String str)
 
static Attribute normal (Kind kind)
 

Friends

class StyleSheet
 

Detailed Description

An attribute of an Ipe Object.

An attribute is either an absolute value or a symbolic name that has to be looked up in a StyleSheet.

All string values are replaced by indices into a Repository (that applies both to symbolic names and to absolute values that are strings). All other values are stored directly inside the attribute, either as a Fixed or a Color.

There are five different kinds of Attribute objects:

  • if isSymbolic() is true, index() returns the index into the repository, and string() returns the symbolic name.
  • if isColor() is true, color() returns an absolute RGB color.
  • if isNumeric() is true, number() returns an absolute scalar value.
  • if isEnum() is true, the attribute represents an enumeration value.
  • otherwise, isString() is true, and index() returns the index into the repository (for a string expressing the absolute value of the attribute), and string() returns the string itself.

Constructor & Destructor Documentation

◆ Attribute() [1/12]

ipe::Attribute::Attribute ( )
inlineexplicit

Default constructor.

Referenced by Attribute().

◆ Attribute() [2/12]

Attribute::Attribute ( bool  symbolic,
String  name 
)
explicit

Create an attribute with string value.

References ipe::Repository::get(), and ipe::Repository::toIndex().

◆ Attribute() [3/12]

Attribute::Attribute ( Fixed  value)
explicit

Create an absolute numeric attribute.

References ipe::Fixed::internal().

◆ Attribute() [4/12]

Attribute::Attribute ( Color  color)
explicit

Create an attribute with absolute color.

References Attribute(), ipe::Color::iBlue, ipe::Color::iGreen, ipe::Fixed::internal(), and ipe::Color::iRed.

◆ Attribute() [5/12]

ipe::Attribute::Attribute ( THorizontalAlignment  align)
inlineexplicit

◆ Attribute() [6/12]

ipe::Attribute::Attribute ( TVerticalAlignment  align)
inlineexplicit

◆ Attribute() [7/12]

ipe::Attribute::Attribute ( TLineJoin  join)
inlineexplicit

◆ Attribute() [8/12]

ipe::Attribute::Attribute ( TLineCap  cap)
inlineexplicit

◆ Attribute() [9/12]

ipe::Attribute::Attribute ( TFillRule  rule)
inlineexplicit

◆ Attribute() [10/12]

ipe::Attribute::Attribute ( TPinned  pin)
inlineexplicit

◆ Attribute() [11/12]

ipe::Attribute::Attribute ( TTransformations  trans)
inlineexplicit

◆ Attribute() [12/12]

ipe::Attribute::Attribute ( TPathMode  pm)
inlineexplicit

Member Function Documentation

◆ Boolean()

static Attribute ipe::Attribute::Boolean ( bool  flag)
inlinestatic

◆ isSymbolic()

◆ isString()

bool ipe::Attribute::isString ( ) const
inline

Is it an absolute string value?

◆ isColor()

bool ipe::Attribute::isColor ( ) const
inline

Is it a color?

Referenced by ipe::ImlParser::parseStyle().

◆ isNumber()

bool ipe::Attribute::isNumber ( ) const
inline

◆ isEnum()

bool ipe::Attribute::isEnum ( ) const
inline

◆ isBoolean()

bool ipe::Attribute::isBoolean ( ) const
inline

Is it a boolean?

◆ isNormal()

◆ index()

◆ internal()

int ipe::Attribute::internal ( ) const
inline

◆ string()

◆ number()

◆ color()

◆ boolean()

bool ipe::Attribute::boolean ( ) const
inline

◆ horizontalAlignment()

THorizontalAlignment ipe::Attribute::horizontalAlignment ( ) const
inline

Referenced by ipe::Text::setAttribute().

◆ verticalAlignment()

TVerticalAlignment ipe::Attribute::verticalAlignment ( ) const
inline

Referenced by ipe::Text::setAttribute().

◆ lineJoin()

TLineJoin ipe::Attribute::lineJoin ( ) const
inline

Referenced by ipe::Path::setAttribute().

◆ lineCap()

TLineCap ipe::Attribute::lineCap ( ) const
inline

Referenced by ipe::Path::setAttribute().

◆ fillRule()

TFillRule ipe::Attribute::fillRule ( ) const
inline

Referenced by ipe::Path::setAttribute().

◆ pinned()

TPinned ipe::Attribute::pinned ( ) const
inline

◆ transformations()

TTransformations ipe::Attribute::transformations ( ) const
inline

◆ pathMode()

TPathMode ipe::Attribute::pathMode ( ) const
inline

Referenced by ipe::Path::setAttribute().

◆ operator==()

bool ipe::Attribute::operator== ( const Attribute rhs) const
inline

Are two values equal (only compares index!)

◆ operator!=()

bool ipe::Attribute::operator!= ( const Attribute rhs) const
inline

Are two values different (only compares index!)

◆ BLACK()

static Attribute ipe::Attribute::BLACK ( )
inlinestatic

◆ WHITE()

static Attribute ipe::Attribute::WHITE ( )
inlinestatic

Create absolute white color.

Referenced by ipe::Reference::Reference(), and ipe::Reference::saveAsXml().

◆ ONE()

static Attribute ipe::Attribute::ONE ( )
inlinestatic

Create absolute number one.

Referenced by normal(), ipe::Reference::Reference(), and ipe::Reference::saveAsXml().

◆ NORMAL()

◆ UNDEFINED()

static Attribute ipe::Attribute::UNDEFINED ( )
inlinestatic

Create symbolic attribute "undefined".

Referenced by ipe::StyleSheet::find(), ipe::Cascade::find(), and ipe::Object::getAttribute().

◆ BACKGROUND()

static Attribute ipe::Attribute::BACKGROUND ( )
inlinestatic

◆ SYM_STROKE()

static Attribute ipe::Attribute::SYM_STROKE ( )
inlinestatic

◆ SYM_FILL()

static Attribute ipe::Attribute::SYM_FILL ( )
inlinestatic

◆ SYM_PEN()

static Attribute ipe::Attribute::SYM_PEN ( )
inlinestatic

Create symbolic attribute "sym-pen".

Referenced by ipe::Painter::setPen(), and ipe::Painter::setSymPen().

◆ ARROW_NORMAL()

static Attribute ipe::Attribute::ARROW_NORMAL ( )
inlinestatic

Create symbolic attribute "arrow/normal(spx)".

Referenced by normal().

◆ OPAQUE()

static Attribute ipe::Attribute::OPAQUE ( )
inlinestatic

◆ ARROW_ARC()

static Attribute ipe::Attribute::ARROW_ARC ( )
inlinestatic

Create symbolic attribute "arrow/arc(spx)".

◆ ARROW_FARC()

static Attribute ipe::Attribute::ARROW_FARC ( )
inlinestatic

Create symbolic attribute "arrow/farc(spx)".

Referenced by ipe::Path::drawArrow().

◆ ARROW_PTARC()

static Attribute ipe::Attribute::ARROW_PTARC ( )
inlinestatic

Create symbolic attribute "arrow/ptarc(spx)".

Referenced by ipe::Path::drawArrow().

◆ ARROW_FPTARC()

static Attribute ipe::Attribute::ARROW_FPTARC ( )
inlinestatic

Create symbolic attribute "arrow/fptarc(spx)".

Referenced by ipe::Path::drawArrow().

◆ isArcArrow()

bool ipe::Attribute::isArcArrow ( ) const
inline

Is it one of the symbolic attributes "arrow/*arc(spc)"?

Referenced by ipe::Path::draw(), and ipe::Path::drawArrow().

◆ makeColor()

Attribute Attribute::makeColor ( String  str,
Attribute  deflt 
)
static

Make a color attribute.

If the string starts with a letter, make a symbolic attribute. Otherwise, it's either a single gray value (0.0 to 1.0), or the three red, green, and blue components, separated by spaces. If it's an empty string, return deflt.

References ipe::Color::Color(), and ipe::String::empty().

Referenced by ipe::ImlParser::parseStyle(), ipe::Reference::Reference(), and ipe::Text::Text().

◆ makeScalar()

Attribute Attribute::makeScalar ( String  str,
Attribute  deflt 
)
static

Make a scalar attribute.

If str is empty, simply return deflt. If str starts with a letter, make a symbolic attribute. Otherwise, must be a number.

References ipe::String::empty().

Referenced by ipe::ImlParser::parseStyle(), and ipe::Reference::Reference().

◆ makeDashStyle()

Attribute Attribute::makeDashStyle ( String  str)
static

Construct dash style attribute from string.

Strings starting with '[' create an absolute dash style. The empty string is equivalent to 'normal'. Any other string creates a symbolic dash style.

References ipe::String::empty(), and NORMAL().

Referenced by ipe::ImlParser::parseStyle().

◆ makeTextSize()

Attribute Attribute::makeTextSize ( String  str)
static

Construct text size attribute from string.

String starting with digit creates a numeric absolute value, string starting with letter creates symbolic text size, anything else creates absolute (string) text size. The empty string is treated like "normal".

References ipe::String::empty(), and NORMAL().

Referenced by ipe::ImlParser::parseStyle(), and ipe::Text::Text().

◆ normal()

Friends And Related Function Documentation

◆ StyleSheet

friend class StyleSheet
friend

The documentation for this class was generated from the following files:
  • ipeattributes.h
  • ipeattributes.cpp

ipe-7.2.13/build/doc/classipe_1_1_pdf_bool.html0000644000175000017500000003277613561570220021114 0ustar otfriedotfried Ipelib: ipe::PdfBool Class Reference
Ipelib
ipe::PdfBool Class Reference

#include <ipepdfparser.h>

Inherits ipe::PdfObj.

Public Member Functions

 PdfBool (bool val)
 
virtual const PdfBoolboolean () const noexcept
 
bool value () const noexcept
 
virtual void write (Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept
 
- Public Member Functions inherited from ipe::PdfObj
virtual ~PdfObj ()=0
 
virtual const PdfNullnull () const noexcept
 
virtual const PdfNumbernumber () const noexcept
 
virtual const PdfStringstring () const noexcept
 
virtual const PdfNamename () const noexcept
 
virtual const PdfRefref () const noexcept
 
virtual const PdfArrayarray () const noexcept
 
virtual const PdfDictdict () const noexcept
 
String repr () const noexcept
 

Detailed Description

The PDF bool object.

Constructor & Destructor Documentation

◆ PdfBool()

ipe::PdfBool::PdfBool ( bool  val)
inlineexplicit

Member Function Documentation

◆ boolean()

const PdfBool * PdfBool::boolean ( ) const
virtualnoexcept

Return this object as PDF bool object.

Reimplemented from ipe::PdfObj.

◆ value()

bool ipe::PdfBool::value ( ) const
inlinenoexcept

References ipe::PdfObj::write().

◆ write()

void PdfBool::write ( Stream stream,
const PdfRenumber renumber,
bool  inflate 
) const
virtualnoexcept

Implements ipe::PdfObj.


The documentation for this class was generated from the following files:
  • ipepdfparser.h
  • ipepdfparser.cpp

ipe-7.2.13/build/doc/classipe_1_1_pdf_number.html0000644000175000017500000003455513561570220021446 0ustar otfriedotfried Ipelib: ipe::PdfNumber Class Reference
Ipelib
ipe::PdfNumber Class Reference

#include <ipepdfparser.h>

Inherits ipe::PdfObj.

Public Member Functions

 PdfNumber (double val)
 
virtual const PdfNumbernumber () const noexcept
 
virtual void write (Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept
 
double value () const noexcept
 
- Public Member Functions inherited from ipe::PdfObj
virtual ~PdfObj ()=0
 
virtual const PdfNullnull () const noexcept
 
virtual const PdfBoolboolean () const noexcept
 
virtual const PdfStringstring () const noexcept
 
virtual const PdfNamename () const noexcept
 
virtual const PdfRefref () const noexcept
 
virtual const PdfArrayarray () const noexcept
 
virtual const PdfDictdict () const noexcept
 
String repr () const noexcept
 

Detailed Description

The PDF number object.

Constructor & Destructor Documentation

◆ PdfNumber()

ipe::PdfNumber::PdfNumber ( double  val)
inlineexplicit

Member Function Documentation

◆ number()

const PdfNumber * PdfNumber::number ( ) const
virtualnoexcept

Return this object as PDF number object.

Reimplemented from ipe::PdfObj.

◆ write()

void PdfNumber::write ( Stream stream,
const PdfRenumber renumber,
bool  inflate 
) const
virtualnoexcept

Implements ipe::PdfObj.

◆ value()


The documentation for this class was generated from the following files:
  • ipepdfparser.h
  • ipepdfparser.cpp

ipe-7.2.13/build/doc/classipe_1_1_xml_parser.html0000644000175000017500000005733513561570220021502 0ustar otfriedotfried Ipelib: ipe::XmlParser Class Reference
Ipelib

#include <ipexml.h>

Inherited by ipe::ImlParser.

Public Member Functions

 XmlParser (DataSource &source)
 
virtual ~XmlParser ()
 
int parsePosition () const
 
String parseToTag ()
 
bool parseAttributes (XmlAttributes &attr, bool qm=false)
 
bool parsePCDATA (String tag, String &pcdata)
 
bool isTagChar (int ch)
 
void getChar ()
 
bool eos ()
 
void skipWhitespace ()
 

Protected Member Functions

String parseToTagX ()
 

Protected Attributes

DataSourceiSource
 
String iTopElement
 
int iCh
 
int iPos
 

Detailed Description

Base class for XML stream parsing.

This is the base class for Ipe's XML parser. It only provides some utility functions for parsing tags and PCDATA. Derived classes implement the actual parsing using recursive descent parsers—after experimenting with various schemes for XML parsing, this seems to work best for Ipe.

Tag names and attribute names must consist of ASCII letters only. Only entities for '&', '<', and '>' are recognized.

Constructor & Destructor Documentation

◆ XmlParser()

XmlParser::XmlParser ( DataSource source)

Construct with a data source.

Referenced by ipe::XmlAttributes::has().

◆ ~XmlParser()

XmlParser::~XmlParser ( )
virtual

Virtual destructor, so one can destroy through pointer.

Member Function Documentation

◆ parsePosition()

int ipe::XmlParser::parsePosition ( ) const
inline

◆ parseToTag()

String XmlParser::parseToTag ( )

Parse whitespace and the name of a tag.

Like ParseToTagX, but silently skips over all tags whose name starts with "x-"

References ipe::String::size().

Referenced by ipe::ImlParser::parseDocument(), ipe::ImlParser::parseObject(), ipe::ImlParser::parsePage(), ipe::ImlParser::parsePageSelection(), ipe::ImlParser::parseStyle(), and ipe::ImlParser::parseStyleSheet().

◆ parseAttributes()

bool XmlParser::parseAttributes ( XmlAttributes attr,
bool  qm = false 
)

Parse XML attributes.

Returns with stream just after >. Caller can check whether the tag ended with a / by checking attr.slash().

Set qm to true to allow a question mark just before the >.

References ipe::XmlAttributes::add(), ipe::XmlAttributes::clear(), ipe::String::empty(), and ipe::XmlAttributes::setSlash().

Referenced by ipe::ImlParser::parseBitmap(), ipe::ImlParser::parseDocument(), ipe::ImlParser::parseObject(), ipe::ImlParser::parsePage(), ipe::ImlParser::parsePageSelection(), ipe::ImlParser::parseStyle(), and ipe::ImlParser::parseStyleSheet().

◆ parsePCDATA()

bool XmlParser::parsePCDATA ( String  tag,
String pcdata 
)

Parse PCDATA.

Checks whether the data is terminated by </tag>, and returns with stream past the >.

References ipe::String::size().

Referenced by ipe::ImlParser::parseBitmap(), ipe::ImlParser::parseDocument(), ipe::ImlParser::parseObject(), ipe::ImlParser::parsePage(), and ipe::ImlParser::parseStyle().

◆ isTagChar()

bool ipe::XmlParser::isTagChar ( int  ch)
inline

◆ getChar()

void ipe::XmlParser::getChar ( )
inline

◆ eos()

bool ipe::XmlParser::eos ( )
inline

◆ skipWhitespace()

void XmlParser::skipWhitespace ( )

◆ parseToTagX()

String XmlParser::parseToTagX ( )
protected

Parse whitespace and the name of a tag.

If the tag is a closing tag, skips > and returns with stream after that. Otherwise, returns with stream just after the tag name.

Comments and <!TAG .. > are skipped silently.

Member Data Documentation

◆ iSource

DataSource& ipe::XmlParser::iSource
protected

◆ iTopElement

String ipe::XmlParser::iTopElement
protected

◆ iCh

int ipe::XmlParser::iCh
protected

◆ iPos

int ipe::XmlParser::iPos
protected

The documentation for this class was generated from the following files:
  • ipexml.h
  • ipexml.cpp

ipe-7.2.13/build/doc/classipe_1_1_latex-members.html0000644000175000017500000001071513561570220022062 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Latex Member List

This is the complete list of members for ipe::Latex, including all inherited members.

addPageNumber(int pno, int vno, int npages, int nviews)ipe::Latex
createLatexSource(Stream &stream, String preamble)ipe::Latex
ipe::TextCollectingVisitor classipe::Latexfriend
Latex(const Cascade *sheet, LatexType latexType)ipe::Latex
readPdf(DataSource &source)ipe::Latex
scanObject(const Object *obj)ipe::Latex
scanPage(Page *page)ipe::Latex
takeResources()ipe::Latex
updateTextObjects()ipe::Latex
~Latex()ipe::Latex

ipe-7.2.13/build/doc/classipe_1_1_pdf_file_resources-members.html0000644000175000017500000001244413561570220024610 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PdfFileResources Member List

This is the complete list of members for ipe::PdfFileResources, including all inherited members.

findResource(String kind, String name) const noexceptipe::PdfResourceBase
findResource(const PdfDict *xf, String kind, String name) const noexceptipe::PdfResourceBase
getDeep(const PdfDict *d, String key) const noexceptipe::PdfResourceBase
getDict(const PdfDict *d, String key) const noexceptipe::PdfResourceBase
iPageResourcesipe::PdfResourceBaseprotected
object(int num) const noexceptipe::PdfFileResourcesvirtual
PdfFileResources(const PdfFile *file)ipe::PdfFileResources
PdfResourceBase()ipe::PdfResourceBase
resourcesOfKind(String kind) const noexceptipe::PdfResourceBase
~PdfFileResources()=defaultipe::PdfFileResources
~PdfResourceBase()ipe::PdfResourceBasevirtual

ipe-7.2.13/build/doc/structipe_1_1_ipelet_data.html0000644000175000017500000002024313561570220022004 0ustar otfriedotfried Ipelib: ipe::IpeletData Struct Reference
Ipelib
ipe::IpeletData Struct Reference

#include <ipelet.h>

Public Attributes

PageiPage
 
const DocumentiDoc
 
int iPageNo
 
int iView
 
int iLayer
 
AllAttributes iAttributes
 
Snap iSnap
 

Detailed Description

Information provided to an ipelet when it is run.

Member Data Documentation

◆ iPage

Page* ipe::IpeletData::iPage

◆ iDoc

const Document* ipe::IpeletData::iDoc

◆ iPageNo

int ipe::IpeletData::iPageNo

◆ iView

int ipe::IpeletData::iView

◆ iLayer

int ipe::IpeletData::iLayer

◆ iAttributes

AllAttributes ipe::IpeletData::iAttributes

◆ iSnap

Snap ipe::IpeletData::iSnap

The documentation for this struct was generated from the following file:
  • ipelet.h

ipe-7.2.13/build/doc/classipe_1_1_curve.html0000644000175000017500000011433013561570220020437 0ustar otfriedotfried Ipelib: ipe::Curve Class Reference
Ipelib

#include <ipeshape.h>

Inherits ipe::SubPath.

Public Member Functions

 Curve ()
 
virtual Type type () const
 
virtual bool closed () const
 
virtual const CurveasCurve () const
 
virtual void save (Stream &stream) const
 
virtual void draw (Painter &painter) const
 
virtual void addToBBox (Rect &box, const Matrix &m, bool cp) const
 
virtual double distance (const Vector &v, const Matrix &m, double bound) const
 
virtual void snapVtx (const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) const
 
virtual void snapBnd (const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const
 
int countSegments () const
 
CurveSegment segment (int i) const
 
CurveSegment closingSegment (Vector u[2]) const
 
void appendSegment (const Vector &v0, const Vector &v1)
 
void appendArc (const Matrix &m, const Vector &v0, const Vector &v1)
 
void appendSpline (const std::vector< Vector > &v)
 
void appendOldSpline (const std::vector< Vector > &v)
 
void setClosed (bool closed)
 
- Public Member Functions inherited from ipe::SubPath
virtual ~SubPath ()=0
 
virtual const EllipseasEllipse () const
 
virtual const ClosedSplineasClosedSpline () const
 

Additional Inherited Members

- Public Types inherited from ipe::SubPath
enum  Type { ECurve, EEllipse, EClosedSpline }
 

Detailed Description

Subpath consisting of a sequence of CurveSegment's.

Constructor & Destructor Documentation

◆ Curve()

Curve::Curve ( )

Create an empty, open subpath.

Referenced by ipe::CurveSegment::snapBnd().

Member Function Documentation

◆ type()

SubPath::Type Curve::type ( ) const
virtual

Return type of this subpath.

Implements ipe::SubPath.

◆ closed()

virtual bool ipe::Curve::closed ( ) const
inlinevirtual

◆ asCurve()

const Curve * Curve::asCurve ( ) const
virtual

Return this object as an Curve, or else nullptr.

Reimplemented from ipe::SubPath.

◆ save()

void Curve::save ( Stream stream) const
virtual

◆ draw()

void Curve::draw ( Painter painter) const
virtual

Draw subpath (does not call drawPath()).

Implements ipe::SubPath.

References ipe::Painter::closePath(), and ipe::Painter::moveTo().

◆ addToBBox()

void Curve::addToBBox ( Rect box,
const Matrix m,
bool  cp 
) const
virtual

Add subpath to box.

Implements ipe::SubPath.

◆ distance()

double Curve::distance ( const Vector v,
const Matrix m,
double  bound 
) const
virtual

Return distance from v to subpath transformed by m.

Implements ipe::SubPath.

◆ snapVtx()

void Curve::snapVtx ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound,
bool  cp 
) const
virtual

Snap to vertex.

Implements ipe::SubPath.

◆ snapBnd()

void Curve::snapBnd ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound 
) const
virtual

Snap to boundary of subpath.

Implements ipe::SubPath.

◆ countSegments()

int ipe::Curve::countSegments ( ) const
inline

Return number of segments. This does not include the closing segment for a closed path.

Referenced by ipe::Shape::isSegment().

◆ segment()

CurveSegment Curve::segment ( int  i) const

Return segment.

If i is negative, elements from the end are returned. The closing segment of a closed path is not accessible this way (use closingSegment() instead)!

Referenced by ipe::Path::clone(), ipe::Path::draw(), and ipe::Shape::isSegment().

◆ closingSegment()

CurveSegment Curve::closingSegment ( Vector  u[2]) const

Returns the closing segment of a closed path.

Since the closing segment isn't actually stored inside this object, you have to provide a length-2 vector for the control points.

This method panics if the Curve is not closed.

References ipe::CurveSegment::ESegment, and ipe::SubPath::~SubPath().

◆ appendSegment()

void Curve::appendSegment ( const Vector v0,
const Vector v1 
)

Append a straight segment to the subpath.

References ipe::CurveSegment::ESegment.

Referenced by ipe::Shape::load(), and ipe::Shape::Shape().

◆ appendArc()

void Curve::appendArc ( const Matrix m,
const Vector v0,
const Vector v1 
)

◆ appendSpline()

void ipe::Curve::appendSpline ( const std::vector< Vector > &  v)
inline

◆ appendOldSpline()

void ipe::Curve::appendOldSpline ( const std::vector< Vector > &  v)
inline

◆ setClosed()

void Curve::setClosed ( bool  closed)

Set whether subpath is closed or not.

Referenced by ipe::Shape::load(), and ipe::Shape::Shape().


The documentation for this class was generated from the following files:
  • ipeshape.h
  • ipeshape.cpp

ipe-7.2.13/build/doc/structipe_1_1_text_padding.html0000644000175000017500000001617313561570220022212 0ustar otfriedotfried Ipelib: ipe::TextPadding Struct Reference
Ipelib
ipe::TextPadding Struct Reference

#include <ipeattributes.h>

Public Attributes

double iLeft
 
double iRight
 
double iTop
 
double iBottom
 

Detailed Description

Padding for text bounding box.

Member Data Documentation

◆ iLeft

◆ iRight

◆ iTop

◆ iBottom

double ipe::TextPadding::iBottom

The documentation for this struct was generated from the following file:
  • ipeattributes.h

ipe-7.2.13/build/doc/manual_47.html0000644000175000017500000001274313561570220016564 0ustar otfriedotfried Ipe Manual -- 9.2 The <page> element
9.3 Ipe object elements9 The Ipe file format9.1 The <ipe> element9.2 The <page> element

9.2 The <page> element

Attributes

title
(optional) title of this page (displayed at a fixed location in a format specified by the style sheet),
section
(optional) Title of document section starting with this page. If the attribute is not present, this page continues the section of the previous page. If the attribute is present, but its value is an empty string, then the contents of the title attribute is used instead.
subsection
(optional) Title of document subsection starting with this page. If the attribute is not present, this page continues the subsection of the previous page. If the attribute is present, but its value is an empty string, then the contents of the title attribute is used instead.
marked
(optional) The page is marked for printing unless the value of this attribute is no.

Contents

  1. An optional <notes> element,
  2. a possibly empty sequence of <layer> elements,
  3. a possibly empty sequence of <view> elements,
  4. a possibly empty sequence of Ipe object elements.

If a page contains no layer element, Ipe automatically adds a default layer named "alpha", visible and editable.

If a page contains no view element, a single view where all layers are visible is assumed.

9.2.1 The <notes> element

This element has no attributes. Its contents is plain text, containing notes for this page.

9.2.2 The <layer> element

Attributes

name
(required) Name of the layer. It must not contain white space.
edit
(optional) The value should be yes or no and indicates whether the user can select and modify the contents of the layer in the Ipe user interface (of course the user can always modify the setting of the attribute).

The layer element must be empty.

9.2.3 The <view> element

Attributes

layers
(required) The value must be a sequence of layer names defined in this page, separated by white space.
active
(required) The layer that is the active layer in this view.
effect
(optional) The symbolic name of a graphics effect to be used during the PDF page transition. The effect must be defined in the style sheet.
marked
(optional) The view is marked for printing if the value of this attribute is yes.

The view element must be empty.

ipe-7.2.13/build/doc/functions_func_0x7e.html0000644000175000017500000001426413561570220020663 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- ~ -


ipe-7.2.13/build/doc/manual_45.html0000644000175000017500000001027513561570220016560 0ustar otfriedotfried Ipe Manual -- 9 The Ipe file format
10 Using Ipe figures in LatexTop8 Advanced topics9 The Ipe file format

9 The Ipe file format

Ipe can store documents in two different formats. One of them is standard PDF, which can be read by any application capable of opening PDF files. (Ipe embeds its own information inside PDF files. The way this is done is not documented here, and may change between releases of Ipe.)

The second Ipe file format is a pure XML implementation. Files stored in this format can be parsed with any XML-aware application, and you can create XML files for Ipe from your own applications.

A DTD for the Ipe format is available as ipe.dtd. For instance, you can use this to validate an Ipe document using

xmllint --dtdvalid ipe.dtd --noout file.ipe

The tags understood by Ipe are described informally in this section. Tags in the XML file can carry attributes other than the ones documented here. Ipe ignores all attributes it does't understand, and they will be lost if the document is saved again from Ipe. Ipe will complain about any XML elements not described here, with the exception that you can use elements whose name starts with "x-" freely to add your own information inside an Ipe file.

An Ipe XML file must contain exactly one <ipe> element, while an Ipe stylesheet file must contain exactly one <ipestyle> element (both types of files are allowed to start with an <?xml> tag, which is simply ignored by Ipe). An Ipe file may also contain a <!DOCTYPE> tag.

All elements are documented below.

ipe-7.2.13/build/doc/manual_52.html0000644000175000017500000000544513561570220016561 0ustar otfriedotfried Ipe Manual -- 11.1 Ipe
11.2 Ipetoipe: converting Ipe file formats11 The command line programs11.1 Ipe

11.1 Ipe

Ipe supports the following command line options:

-sheet style sheet name
Adds the designated style sheet to any newly created documents.
-show-configuration
With this option, Ipe will display the current configuration options on stdout, and terminate.
In addition, you can specify the name of an Ipe file to open on the command line.
ipe-7.2.13/build/doc/structipe_1_1_canvas_base_1_1_style.html0000644000175000017500000002732013561570220023661 0ustar otfriedotfried Ipelib: ipe::CanvasBase::Style Struct Reference
Ipelib
ipe::CanvasBase::Style Struct Reference

#include <ipecanvas.h>

Public Attributes

Color paperColor
 
Color primarySelectionColor
 
Color secondarySelectionColor
 
bool pretty
 
bool classicGrid
 
double thinLine
 
double thickLine
 
int thinStep
 
int thickStep
 
bool paperClip
 
bool numberPages
 

Detailed Description

In pretty display, no dashed lines are drawn around text objects, and if Latex font data is not available, no text is drawn at all.

Member Data Documentation

◆ paperColor

Color ipe::CanvasBase::Style::paperColor

◆ primarySelectionColor

Color ipe::CanvasBase::Style::primarySelectionColor

◆ secondarySelectionColor

Color ipe::CanvasBase::Style::secondarySelectionColor

◆ pretty

bool ipe::CanvasBase::Style::pretty

◆ classicGrid

bool ipe::CanvasBase::Style::classicGrid

◆ thinLine

double ipe::CanvasBase::Style::thinLine

◆ thickLine

double ipe::CanvasBase::Style::thickLine

◆ thinStep

int ipe::CanvasBase::Style::thinStep

◆ thickStep

int ipe::CanvasBase::Style::thickStep

◆ paperClip

bool ipe::CanvasBase::Style::paperClip

◆ numberPages

bool ipe::CanvasBase::Style::numberPages

The documentation for this struct was generated from the following file:
  • ipecanvas.h

ipe-7.2.13/build/doc/functions_vars_d.html0000644000175000017500000000312113561570220020331 0ustar otfriedotfried Ipelib: Class Members - Variables
Ipelib
 

- d -


ipe-7.2.13/build/doc/classipe_1_1_cascade.html0000644000175000017500000012074013561570220020700 0ustar otfriedotfried Ipelib: ipe::Cascade Class Reference
Ipelib

#include <ipestyle.h>

Public Member Functions

 Cascade ()
 
 Cascade (const Cascade &rhs)
 
Cascadeoperator= (const Cascade &rhs)
 
 ~Cascade ()
 
int count () const
 
StyleSheetsheet (int index)
 
const StyleSheetsheet (int index) const
 
void insert (int index, StyleSheet *sheet)
 
void remove (int index)
 
void saveAsXml (Stream &stream) const
 
bool has (Kind kind, Attribute sym) const
 
Attribute find (Kind, Attribute sym) const
 
const SymbolfindSymbol (Attribute sym) const
 
const GradientfindGradient (Attribute sym) const
 
const TilingfindTiling (Attribute sym) const
 
const EffectfindEffect (Attribute sym) const
 
const LayoutfindLayout () const
 
const TextPaddingfindTextPadding () const
 
const StyleSheet::TitleStylefindTitleStyle () const
 
const StyleSheet::PageNumberStylefindPageNumberStyle () const
 
String findPreamble () const
 
TLineCap lineCap () const
 
TLineJoin lineJoin () const
 
TFillRule fillRule () const
 
void allNames (Kind kind, AttributeSeq &seq) const
 
int findDefinition (Kind kind, Attribute sym) const
 

Detailed Description

A cascade of style sheets.

The StyleSheets of a document cascade in the sense that a document can refer to several StyleSheets, which are arranged in a stack. A lookup is done from top to bottom, and returns as soon as a match is found. Ipe always appends the built-in "standard" style sheet at the bottom of the cascade.

Constructor & Destructor Documentation

◆ Cascade() [1/2]

Cascade::Cascade ( )

Create an empty cascade.

This does not add the standard style sheet.

References ipe::size().

◆ Cascade() [2/2]

Cascade::Cascade ( const Cascade rhs)

Copy constructor.

References count().

◆ ~Cascade()

Cascade::~Cascade ( )

Destructor.

Member Function Documentation

◆ operator=()

Cascade & Cascade::operator= ( const Cascade rhs)

Assignment operator.

References count().

◆ count()

int ipe::Cascade::count ( ) const
inline

Return number of style sheets.

Referenced by Cascade(), and operator=().

◆ sheet() [1/2]

StyleSheet* ipe::Cascade::sheet ( int  index)
inline

Return StyleSheet at index.

◆ sheet() [2/2]

const StyleSheet* ipe::Cascade::sheet ( int  index) const
inline

Return StyleSheet at index.

◆ insert()

void Cascade::insert ( int  index,
StyleSheet sheet 
)

Insert a style sheet into the cascade.

Takes ownership of sheet.

Referenced by ipe::Document::Document(), and ipe::ImlParser::parseDocument().

◆ remove()

void Cascade::remove ( int  index)

Remove a style sheet from the cascade.

The old sheet is deleted.

◆ saveAsXml()

void Cascade::saveAsXml ( Stream stream) const

◆ has()

bool Cascade::has ( Kind  kind,
Attribute  sym 
) const

◆ find()

◆ findSymbol()

◆ findGradient()

const Gradient * Cascade::findGradient ( Attribute  sym) const

◆ findTiling()

const Tiling * Cascade::findTiling ( Attribute  sym) const

◆ findEffect()

const Effect * Cascade::findEffect ( Attribute  sym) const

◆ findLayout()

const Layout * Cascade::findLayout ( ) const

Find page layout (such as text margins).

Referenced by ipe::PanTool::draw(), and ipe::Thumbnail::Thumbnail().

◆ findTextPadding()

const TextPadding * Cascade::findTextPadding ( ) const

Find text padding (for text bbox computation).

Referenced by ipe::BBoxPainter::doDrawText().

◆ findTitleStyle()

const StyleSheet::TitleStyle * Cascade::findTitleStyle ( ) const

Get style of page titles (or 0 if none defined).

Referenced by ipe::Page::applyTitleStyle().

◆ findPageNumberStyle()

const StyleSheet::PageNumberStyle * Cascade::findPageNumberStyle ( ) const

Return style of page numbering (or 0 if none defined).

◆ findPreamble()

String Cascade::findPreamble ( ) const

Return total LaTeX preamble (of the whole cascade).

◆ lineCap()

TLineCap Cascade::lineCap ( ) const

◆ lineJoin()

TLineJoin Cascade::lineJoin ( ) const

◆ fillRule()

TFillRule Cascade::fillRule ( ) const

◆ allNames()

void Cascade::allNames ( Kind  kind,
AttributeSeq seq 
) const

◆ findDefinition()

int Cascade::findDefinition ( Kind  kind,
Attribute  sym 
) const

Find stylesheet defining the attribute.

This method goes through the cascade looking for a definition of the symbolic attribute sym. It returns the index of the stylesheet defining the attribute, or -1 if the attribute is not defined.

The method panics if sym is not symbolic. It also works for ESymbol, EGradient, ETiling, and EEffect.

References ipe::Attribute::isSymbolic().

Referenced by ipe::Object::checkSymbol().


The documentation for this class was generated from the following files:
  • ipestyle.h
  • ipestyle.cpp

ipe-7.2.13/build/doc/classipe_1_1_file_source-members.html0000644000175000017500000000540013561570220023237 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::FileSource Member List

This is the complete list of members for ipe::FileSource, including all inherited members.

FileSource(std::FILE *file)ipe::FileSource
getChar()ipe::FileSourcevirtual
~DataSource()=0ipe::DataSourcepure virtual

ipe-7.2.13/build/doc/classipe_1_1_object.html0000644000175000017500000026316013561570220020567 0ustar otfriedotfried Ipelib: ipe::Object Class Reference
Ipelib

#include <ipeobject.h>

Inherited by ipe::Group, ipe::Image, ipe::Path, ipe::Reference, and ipe::Text.

Public Types

enum  Type {
  EGroup, EPath, EText, EImage,
  EReference
}
 

Public Member Functions

virtual ~Object ()=0
 
virtual void accept (Visitor &visitor) const =0
 
virtual Objectclone () const =0
 
virtual GroupasGroup ()
 
virtual const GroupasGroup () const
 
virtual TextasText ()
 
virtual PathasPath ()
 
virtual ImageasImage ()
 
virtual ReferenceasReference ()
 
virtual Type type () const =0
 
virtual TPinned pinned () const
 
void setPinned (TPinned pin)
 
TTransformations transformations () const
 
void setTransformations (TTransformations trans)
 
void setMatrix (const Matrix &matrix)
 
const Matrixmatrix () const
 
virtual bool setAttribute (Property prop, Attribute value)
 
virtual Attribute getAttribute (Property prop) const noexcept
 
virtual void saveAsXml (Stream &stream, String layer) const =0
 
virtual void draw (Painter &painter) const =0
 
virtual void drawSimple (Painter &painter) const =0
 
virtual double distance (const Vector &v, const Matrix &m, double bound) const =0
 
virtual void addToBBox (Rect &box, const Matrix &m, bool cp) const =0
 
virtual void snapVtx (const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const
 
virtual void snapCtl (const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const
 
virtual void snapBnd (const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const
 
virtual void checkStyle (const Cascade *sheet, AttributeSeq &seq) const
 

Protected Member Functions

 Object ()
 
 Object (const AllAttributes &attr)
 
 Object (const Object &rhs)
 
 Object (const XmlAttributes &attr)
 
void saveAttributesAsXml (Stream &stream, String layer) const
 

Static Protected Member Functions

static void checkSymbol (Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq)
 

Protected Attributes

Matrix iMatrix
 
TPinned iPinned: 8
 
TTransformations iTransformations: 8
 

Detailed Description

Base class for all Ipe objects, composite or leaf.

All objects are derived from this class. It provides functionality common to all objects, and carries the standard attributes.

All Object's provide a constant time copy constructor (and a virtual Object::clone() method). Objects of non-constant size realize this by separating the implementation and using reference counting. In particular, copying a composite object does not create new copies of the components.

Object has only three attributes: the transformation matrix, the pinning status, and the allowed transformations.

If an object is pinned, it cannot be moved at all (or only in the non-pinned direction) from the Ipe user interface.

Restricting the allowed transformations works somewhat differently: It doesn't stop transformations being applied to the object, but they only effect the position of the reference point (the origin of the object coordinate system), and (if transformations() == ETransformationsRigidMotions) the orientation of the object coordinate system.

Member Enumeration Documentation

◆ Type

Enumerator
EGroup 
EPath 
EText 
EImage 
EReference 

Constructor & Destructor Documentation

◆ ~Object()

Object::~Object ( )
pure virtual

Pure virtual destructor.

◆ Object() [1/4]

Object::Object ( )
explicitprotected

Create object with identity matrix, no pinning, all transformations.

References ipe::ENoPin, ipe::ETransformationsAffine, iPinned, and iTransformations.

Referenced by matrix().

◆ Object() [2/4]

Object::Object ( const AllAttributes attr)
explicitprotected

Create object by taking pinning/transforming from attr and setting identity matrix.

References iPinned, ipe::AllAttributes::iPinned, iTransformations, and ipe::AllAttributes::iTransformations.

◆ Object() [3/4]

Object::Object ( const Object rhs)
protected

Copy constructor.

References iMatrix, iPinned, and iTransformations.

◆ Object() [4/4]

Object::Object ( const XmlAttributes attr)
explicitprotected

Construct from XML stream.

Member Function Documentation

◆ accept()

virtual void ipe::Object::accept ( Visitor visitor) const
pure virtual

◆ clone()

virtual Object* ipe::Object::clone ( ) const
pure virtual

Make a copy of this object (constant-time).

Implemented in ipe::Group, ipe::Reference, ipe::Text, ipe::Path, and ipe::Image.

Referenced by ipe::Symbol::operator=(), and ipe::Symbol::Symbol().

◆ asGroup() [1/2]

Group * Object::asGroup ( )
virtual

Return pointer to this object if it is an Group, nullptr otherwise.

Reimplemented in ipe::Group.

Referenced by ipe::PdfWriter::createPageView().

◆ asGroup() [2/2]

const Group * Object::asGroup ( ) const
virtual

Return pointer to this object if it is an Group, nullptr otherwise.

Reimplemented in ipe::Group.

◆ asText()

Text * Object::asText ( )
virtual

Return pointer to this object if it is an Text, nullptr otherwise.

Reimplemented in ipe::Text.

◆ asPath()

Path * Object::asPath ( )
virtual

Return pointer to this object if it is an Path, nullptr otherwise.

Reimplemented in ipe::Path.

◆ asImage()

Image * Object::asImage ( )
virtual

Return pointer to this object if it is an Image , nullptr otherwise.

Reimplemented in ipe::Image.

◆ asReference()

Reference * Object::asReference ( )
virtual

Return pointer to this object if it is an Ref, nullptr otherwise.

Reimplemented in ipe::Reference.

◆ type()

virtual Type ipe::Object::type ( ) const
pure virtual

◆ pinned()

TPinned Object::pinned ( ) const
virtual

Return pinning mode of the object.

Reimplemented in ipe::Group.

References iPinned.

Referenced by getAttribute(), ipe::Group::pinned(), ipe::Group::push_back(), and ipe::TransformTool::TransformTool().

◆ setPinned()

void Object::setPinned ( TPinned  pin)

Set pinning mode of the object.

References iPinned.

◆ transformations()

◆ setTransformations()

void Object::setTransformations ( TTransformations  trans)

Set allowed transformations of the object.

References iTransformations.

Referenced by ipe::Text::setAttribute(), and transformations().

◆ setMatrix()

void Object::setMatrix ( const Matrix matrix)

Set the transformation matrix.

Don't use this on an Object in a Page, because it wouldn't invalidate its bounding box. Call Page::transform instead.

References iMatrix, and matrix().

Referenced by ipe::Page::applyTitleStyle(), ipe::Page::transform(), and transformations().

◆ matrix()

◆ setAttribute()

◆ getAttribute()

Attribute Object::getAttribute ( Property  prop) const
virtualnoexcept

Get setting of an attribute of this object.

If object does not have this attribute, returnes "undefined" attribute.

Reimplemented in ipe::Path, ipe::Group, ipe::Reference, ipe::Text, and ipe::Image.

References ipe::EPropPinned, ipe::EPropTransformations, iTransformations, pinned(), and ipe::Attribute::UNDEFINED().

Referenced by ipe::Image::getAttribute(), ipe::Text::getAttribute(), ipe::Reference::getAttribute(), ipe::Group::getAttribute(), ipe::Path::getAttribute(), and matrix().

◆ saveAsXml()

virtual void ipe::Object::saveAsXml ( Stream stream,
String  layer 
) const
pure virtual

Save the object in XML format.

Implemented in ipe::Path, ipe::Group, ipe::Reference, ipe::Text, and ipe::Image.

Referenced by matrix().

◆ draw()

◆ drawSimple()

virtual void ipe::Object::drawSimple ( Painter painter) const
pure virtual

Draw simple version for selecting and transforming.

Implemented in ipe::Path, ipe::Group, ipe::Reference, ipe::Text, and ipe::Image.

Referenced by ipe::PanTool::draw(), ipe::SelectTool::draw(), ipe::TransformTool::draw(), ipe::Reference::drawSimple(), and matrix().

◆ distance()

virtual double ipe::Object::distance ( const Vector v,
const Matrix m,
double  bound 
) const
pure virtual

Return distance of transformed object to point v. If larger than bound, can just return bound.

Implemented in ipe::Path, ipe::Group, ipe::Text, ipe::Reference, and ipe::Image.

Referenced by ipe::Page::distance(), and matrix().

◆ addToBBox()

virtual void ipe::Object::addToBBox ( Rect box,
const Matrix m,
bool  cp 
) const
pure virtual

Extend box to include the object transformed by m.

For objects in a page, don't call this directly. The Page caches the bounding box of each object, so it is far more efficient to call Page::bbox.

Control points that lie outside the visual object are included if cp is true.

If called with an empty box and cp == false, the result of this function is a tight bounding box for the object, with a little leeway in case the boundary is determined by a spline (it has to be approximated to perform this operation).

Implemented in ipe::Path, ipe::Group, ipe::Text, ipe::Reference, and ipe::Image.

Referenced by matrix(), and ipe::SelectTool::mouseButton().

◆ snapVtx()

void Object::snapVtx ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound 
) const
virtual

Compute vertex snapping position for transformed object.

Looks only for positions closer than bound. If successful, modify pos and bound. The default implementation does nothing.

Reimplemented in ipe::Path, ipe::Group, and ipe::Reference.

Referenced by matrix(), and ipe::Page::snapVtx().

◆ snapCtl()

void Object::snapCtl ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound 
) const
virtual

Compute control point snapping position for transformed object.

Looks only for positions closer than bound. If successful, modify pos and bound. The default implementation does nothing.

Reimplemented in ipe::Path, ipe::Group, ipe::Text, and ipe::Image.

Referenced by matrix(), and ipe::Page::snapCtl().

◆ snapBnd()

void Object::snapBnd ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound 
) const
virtual

Compute boundary snapping position for transformed object.

Looks only for positions closer than bound. If successful, modify pos and bound. The default implementation does nothing.

Reimplemented in ipe::Path, ipe::Group, and ipe::Reference.

References ipe::Visitor::~Visitor().

Referenced by matrix(), and ipe::Page::snapBnd().

◆ checkStyle()

void Object::checkStyle ( const Cascade sheet,
AttributeSeq seq 
) const
virtual

Check all symbolic attributes.

Reimplemented in ipe::Group, ipe::Path, ipe::Reference, and ipe::Text.

Referenced by ipe::Document::checkStyle(), and matrix().

◆ saveAttributesAsXml()

◆ checkSymbol()

void Object::checkSymbol ( Kind  kind,
Attribute  attr,
const Cascade sheet,
AttributeSeq seq 
)
staticprotected

Check whether attribute is either absolute or defined in the style sheet cascade sheet. Add attr to seq if this is not the case.

References ipe::Cascade::findDefinition(), and ipe::Attribute::isSymbolic().

Referenced by ipe::Text::checkStyle(), ipe::Reference::checkStyle(), ipe::Path::checkStyle(), and matrix().

Member Data Documentation

◆ iMatrix

Matrix ipe::Object::iMatrix
protected

◆ iPinned

TPinned ipe::Object::iPinned
protected

◆ iTransformations


The documentation for this class was generated from the following files:
  • ipeobject.h
  • ipeobject.cpp

ipe-7.2.13/build/doc/classipe_1_1_iml_parser-members.html0000644000175000017500000002373213561570220023105 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::ImlParser Member List

This is the complete list of members for ipe::ImlParser, including all inherited members.

eos()ipe::XmlParserinline
Errors enum nameipe::ImlParser
ESuccess enum valueipe::ImlParser
ESyntaxError enum valueipe::ImlParser
EVersionTooOld enum valueipe::ImlParser
EVersionTooRecent enum valueipe::ImlParser
getChar()ipe::XmlParserinline
iChipe::XmlParserprotected
ImlParser(DataSource &source)ipe::ImlParserexplicit
iPosipe::XmlParserprotected
iSourceipe::XmlParserprotected
isTagChar(int ch)ipe::XmlParserinline
iTopElementipe::XmlParserprotected
parseAttributes(XmlAttributes &attr, bool qm=false)ipe::XmlParser
parseBitmap()ipe::ImlParser
parseDocument(Document &doc)ipe::ImlParser
parseObject(String tag, Page *page=nullptr, int *currentLayer=nullptr)ipe::ImlParser
parsePage(Page &page)ipe::ImlParser
parsePageSelection()ipe::ImlParser
parsePCDATA(String tag, String &pcdata)ipe::XmlParser
parsePosition() constipe::XmlParserinline
parseStyle(StyleSheet &sheet)ipe::ImlParser
parseStyleSheet()ipe::ImlParser
parseToTag()ipe::XmlParser
parseToTagX()ipe::XmlParserprotected
pdfStream(int objNum)ipe::ImlParservirtual
skipWhitespace()ipe::XmlParser
XmlParser(DataSource &source)ipe::XmlParser
~XmlParser()ipe::XmlParservirtual

ipe-7.2.13/build/doc/classipe_1_1_pdf_string.html0000644000175000017500000003720413561570220021456 0ustar otfriedotfried Ipelib: ipe::PdfString Class Reference
Ipelib
ipe::PdfString Class Reference

#include <ipepdfparser.h>

Inherits ipe::PdfObj.

Public Member Functions

 PdfString (const String &val, bool binary=false)
 
virtual const PdfStringstring () const noexcept
 
virtual void write (Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept
 
String value () const noexcept
 
String decode () const noexcept
 
- Public Member Functions inherited from ipe::PdfObj
virtual ~PdfObj ()=0
 
virtual const PdfNullnull () const noexcept
 
virtual const PdfBoolboolean () const noexcept
 
virtual const PdfNumbernumber () const noexcept
 
virtual const PdfNamename () const noexcept
 
virtual const PdfRefref () const noexcept
 
virtual const PdfArrayarray () const noexcept
 
virtual const PdfDictdict () const noexcept
 
String repr () const noexcept
 

Detailed Description

The PDF string object.

Constructor & Destructor Documentation

◆ PdfString()

ipe::PdfString::PdfString ( const String val,
bool  binary = false 
)
inlineexplicit

Member Function Documentation

◆ string()

const PdfString * PdfString::string ( ) const
virtualnoexcept

Return this object as PDF string object.

Reimplemented from ipe::PdfObj.

◆ write()

void PdfString::write ( Stream stream,
const PdfRenumber renumber,
bool  inflate 
) const
virtualnoexcept

Implements ipe::PdfObj.

◆ value()

String ipe::PdfString::value ( ) const
inlinenoexcept

◆ decode()

String PdfString::decode ( ) const
noexcept

Return value of string after decoding binary strings.

References ipe::Lex::eos(), and ipe::Lex::getHexByte().

Referenced by ipe::CairoPainter::executeStream().


The documentation for this class was generated from the following files:
  • ipepdfparser.h
  • ipepdfparser.cpp

ipe-7.2.13/build/doc/classipe_1_1_fonts.html0000644000175000017500000002275613561570220020456 0ustar otfriedotfried Ipelib: ipe::Fonts Class Reference
Ipelib

#include <ipefonts.h>

Public Member Functions

 Fonts (const PdfResourceBase *resources)
 
FacegetFace (const PdfDict *d)
 
const PdfResourceBaseresources () const noexcept
 

Static Public Member Functions

static cairo_font_face_t * screenFont ()
 
static String freetypeVersion ()
 

Detailed Description

Provides the fonts used to render text.

Constructor & Destructor Documentation

◆ Fonts()

Fonts::Fonts ( const PdfResourceBase resources)

Member Function Documentation

◆ getFace()

Face * Fonts::getFace ( const PdfDict d)

Get a typeface.

Corresponds to a Freetype "face", or a PDF font resource. A Face can be loaded at various sizes (transformations), resulting in individual FaceSize's.

Referenced by ipe::CairoPainter::executeStream().

◆ screenFont()

cairo_font_face_t * Fonts::screenFont ( )
static

Return a Cairo font to render to the screen w/o Latex font.

Referenced by ipe::CairoPainter::doDrawText().

◆ freetypeVersion()

String Fonts::freetypeVersion ( )
static

◆ resources()

const PdfResourceBase* ipe::Fonts::resources ( ) const
inlinenoexcept

The documentation for this class was generated from the following files:
  • ipefonts.h
  • ipefonts.cpp

ipe-7.2.13/build/doc/classipe_1_1_snap-members.html0000644000175000017500000002007113561570220021702 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Snap Member List

This is the complete list of members for ipe::Snap, including all inherited members.

ESnapAngle enum valueipe::Snap
ESnapAuto enum valueipe::Snap
ESnapBd enum valueipe::Snap
ESnapCtl enum valueipe::Snap
ESnapGrid enum valueipe::Snap
ESnapInt enum valueipe::Snap
ESnapNone enum valueipe::Snap
ESnapVtx enum valueipe::Snap
getLine(const Vector &mouse, const Vector &base) const noexceptipe::Snap
iAngleSizeipe::Snap
iDiripe::Snap
iGridSizeipe::Snap
iGridVisibleipe::Snap
intersectionSnap(const Vector &pos, Vector &fifi, const Page *page, int view, double &snapDist) const noexceptipe::Snap
iOriginipe::Snap
iSnapipe::Snap
iSnapDistanceipe::Snap
iWithAxesipe::Snap
setEdge(const Vector &pos, const Page *page, int view) noexceptipe::Snap
simpleSnap(Vector &pos, const Page *page, int view, double snapDist, Tool *tool=nullptr) const noexceptipe::Snap
snap(Vector &pos, const Page *page, int view, double snapDist, Tool *tool=nullptr, Vector *autoOrg=nullptr) const noexceptipe::Snap
snapAngularIntersection(Vector &pos, const Line &l, const Page *page, int view, double snapDist) const noexceptipe::Snap
TSnapModes enum nameipe::Snap

ipe-7.2.13/build/doc/classipe_1_1_ps_writer-members.html0000644000175000017500000000676013561570220022770 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PsWriter Member List

This is the complete list of members for ipe::PsWriter, including all inherited members.

createHeader(int pno=0, int vno=0)ipe::PsWriter
createPageView(int pno=0, int vno=0)ipe::PsWriter
createTrailer()ipe::PsWriter
createXml(int compressLevel)ipe::PsWriter
PsWriter(TellStream &stream, const Document *doc, bool noColor)ipe::PsWriter
~PsWriter()ipe::PsWriter

ipe-7.2.13/build/doc/functions_func_f.html0000644000175000017500000001574013561570220020325 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- f -


ipe-7.2.13/build/doc/classipe_1_1_attribute-members.html0000644000175000017500000004651013561570220022752 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Attribute Member List

This is the complete list of members for ipe::Attribute, including all inherited members.

ARROW_ARC()ipe::Attributeinlinestatic
ARROW_FARC()ipe::Attributeinlinestatic
ARROW_FPTARC()ipe::Attributeinlinestatic
ARROW_NORMAL()ipe::Attributeinlinestatic
ARROW_PTARC()ipe::Attributeinlinestatic
Attribute()ipe::Attributeinlineexplicit
Attribute(bool symbolic, String name)ipe::Attributeexplicit
Attribute(Fixed value)ipe::Attributeexplicit
Attribute(Color color)ipe::Attributeexplicit
Attribute(THorizontalAlignment align)ipe::Attributeinlineexplicit
Attribute(TVerticalAlignment align)ipe::Attributeinlineexplicit
Attribute(TLineJoin join)ipe::Attributeinlineexplicit
Attribute(TLineCap cap)ipe::Attributeinlineexplicit
Attribute(TFillRule rule)ipe::Attributeinlineexplicit
Attribute(TPinned pin)ipe::Attributeinlineexplicit
Attribute(TTransformations trans)ipe::Attributeinlineexplicit
Attribute(TPathMode pm)ipe::Attributeinlineexplicit
BACKGROUND()ipe::Attributeinlinestatic
BLACK()ipe::Attributeinlinestatic
Boolean(bool flag)ipe::Attributeinlinestatic
boolean() constipe::Attributeinline
color() constipe::Attribute
fillRule() constipe::Attributeinline
horizontalAlignment() constipe::Attributeinline
index() constipe::Attributeinline
internal() constipe::Attributeinline
isArcArrow() constipe::Attributeinline
isBoolean() constipe::Attributeinline
isColor() constipe::Attributeinline
isEnum() constipe::Attributeinline
isNormal() constipe::Attributeinline
isNumber() constipe::Attributeinline
isString() constipe::Attributeinline
isSymbolic() constipe::Attributeinline
lineCap() constipe::Attributeinline
lineJoin() constipe::Attributeinline
makeColor(String str, Attribute deflt)ipe::Attributestatic
makeDashStyle(String str)ipe::Attributestatic
makeScalar(String str, Attribute deflt)ipe::Attributestatic
makeTextSize(String str)ipe::Attributestatic
normal(Kind kind)ipe::Attributestatic
NORMAL()ipe::Attributeinlinestatic
number() constipe::Attribute
ONE()ipe::Attributeinlinestatic
OPAQUE()ipe::Attributeinlinestatic
operator!=(const Attribute &rhs) constipe::Attributeinline
operator==(const Attribute &rhs) constipe::Attributeinline
pathMode() constipe::Attributeinline
pinned() constipe::Attributeinline
string() constipe::Attribute
StyleSheet classipe::Attributefriend
SYM_FILL()ipe::Attributeinlinestatic
SYM_PEN()ipe::Attributeinlinestatic
SYM_STROKE()ipe::Attributeinlinestatic
transformations() constipe::Attributeinline
UNDEFINED()ipe::Attributeinlinestatic
verticalAlignment() constipe::Attributeinline
WHITE()ipe::Attributeinlinestatic

ipe-7.2.13/build/doc/classipe_1_1_color-members.html0000644000175000017500000001200313561570220022053 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Color Member List

This is the complete list of members for ipe::Color, including all inherited members.

Color()ipe::Colorinline
Color(String str)ipe::Colorexplicit
Color(int r, int g, int b)ipe::Colorexplicit
iBlueipe::Color
iGreenipe::Color
iRedipe::Color
isGray() constipe::Color
operator!=(const Color &rhs) constipe::Colorinline
operator<<(Stream &stream, const Color &attr)ipe::Colorrelated
operator==(const Color &rhs) constipe::Color
save(Stream &stream) constipe::Color
saveRGB(Stream &stream) constipe::Color

ipe-7.2.13/build/doc/classipe_1_1_pan_tool-members.html0000644000175000017500000001075313561570220022562 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PanTool Member List

This is the complete list of members for ipe::PanTool, including all inherited members.

draw(Painter &painter) constipe::PanToolvirtual
iCanvasipe::Toolprotected
key(String text, int modifiers)ipe::Toolvirtual
mouseButton(int button, bool press)ipe::PanToolvirtual
mouseMove()ipe::PanToolvirtual
PanTool(CanvasBase *canvas, const Page *page, int view)ipe::PanTool
snapVtx(const Vector &mouse, Vector &pos, double &bound, bool cp) constipe::Toolvirtual
Tool(CanvasBase *canvas)ipe::Toolprotected
~Tool()ipe::Toolvirtual

ipe-7.2.13/build/doc/classipe_1_1_visitor-members.html0000644000175000017500000000717013561570220022445 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Visitor Member List

This is the complete list of members for ipe::Visitor, including all inherited members.

visitGroup(const Group *obj)ipe::Visitorvirtual
visitImage(const Image *obj)ipe::Visitorvirtual
visitPath(const Path *obj)ipe::Visitorvirtual
visitReference(const Reference *obj)ipe::Visitorvirtual
visitText(const Text *obj)ipe::Visitorvirtual
~Visitor()ipe::Visitorvirtual

ipe-7.2.13/build/doc/classipe_1_1_cairo_painter-members.html0000644000175000017500000005732113561570220023570 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::CairoPainter Member List

This is the complete list of members for ipe::CairoPainter, including all inherited members.

addClipPath()ipe::Painter
CairoPainter(const Cascade *sheet, Fonts *fonts, cairo_t *cc, double zoom, bool pretty)ipe::CairoPainter
cascade() constipe::Painterinline
closePath()ipe::Painter
curveTo(const Vector &v1, const Vector &v2, const Vector &v3)ipe::Painter
curveTo(const Bezier &bezier)ipe::Painterinline
dashStyle() constipe::Painterinline
dashStyle(std::vector< double > &dashes, double &offset) constipe::Painter
doAddClipPath()ipe::CairoPainterprotectedvirtual
doClosePath()ipe::CairoPainterprotectedvirtual
doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3)ipe::CairoPainterprotectedvirtual
doDrawArc(const Arc &arc)ipe::CairoPainterprotectedvirtual
doDrawBitmap(Bitmap bitmap)ipe::CairoPainterprotectedvirtual
doDrawPath(TPathMode mode)ipe::CairoPainterprotectedvirtual
doDrawSymbol(Attribute symbol)ipe::Painterprotectedvirtual
doDrawText(const Text *text)ipe::CairoPainterprotectedvirtual
doLineTo(const Vector &v)ipe::CairoPainterprotectedvirtual
doMoveTo(const Vector &v)ipe::CairoPainterprotectedvirtual
doNewPath()ipe::Painterprotectedvirtual
doPop()ipe::CairoPainterprotectedvirtual
doPush()ipe::CairoPainterprotectedvirtual
drawArc(const Arc &arc)ipe::Painter
drawArcAsBezier(double alpha)ipe::Painterprotected
drawBitmap(Bitmap bitmap)ipe::Painter
drawEllipse()ipe::Painter
drawPath(TPathMode mode)ipe::Painter
drawSymbol(Attribute symbol)ipe::Painter
drawText(const Text *text)ipe::Painter
executeStream(const PdfDict *stream, const PdfDict *resources)ipe::CairoPainter
fill() constipe::Painterinline
fillRule() constipe::Painterinline
gradient() constipe::Painterinline
iCascadeipe::Painterprotected
iInPathipe::Painterprotected
iMatrixipe::Painterprotected
iStateipe::Painterprotected
lineCap() constipe::Painterinline
lineJoin() constipe::Painterinline
lineTo(const Vector &v)ipe::Painter
matrix() constipe::Painterinline
moveTo(const Vector &v)ipe::Painter
newPath()ipe::Painter
opacity() constipe::Painterinline
Painter(const Cascade *style)ipe::Painter
pen() constipe::Painterinline
pop()ipe::Painter
popMatrix()ipe::Painter
push()ipe::Painter
pushMatrix()ipe::Painter
rect(const Rect &re)ipe::Painter
setDashStyle(Attribute dash)ipe::Painter
setDimmed(bool dim)ipe::CairoPainterinline
setFill(Attribute color)ipe::Painter
setFillRule(TFillRule rule)ipe::Painter
setGradient(Attribute grad)ipe::Painter
setLineCap(TLineCap cap)ipe::Painter
setLineJoin(TLineJoin join)ipe::Painter
setOpacity(Attribute opaq)ipe::Painter
setPen(Attribute pen)ipe::Painter
setState(const State &state)ipe::Painter
setStroke(Attribute color)ipe::Painter
setStrokeOpacity(Attribute opaq)ipe::Painter
setSymFill(Attribute color)ipe::Painter
setSymPen(Attribute wid)ipe::Painter
setSymStroke(Attribute color)ipe::Painter
setTiling(Attribute til)ipe::Painter
state() constipe::Painterinline
stroke() constipe::Painterinline
strokeOpacity() constipe::Painterinline
symFill() constipe::Painterinline
symPen() constipe::Painterinline
symStroke() constipe::Painterinline
tiling() constipe::Painterinline
transform(const Matrix &m)ipe::Painter
translate(const Vector &v)ipe::Painter
untransform(TTransformations trans)ipe::Painter
~CairoPainter()ipe::CairoPainterinlinevirtual
~Painter()ipe::Paintervirtual

ipe-7.2.13/build/doc/manual_59.html0000644000175000017500000003071413561570220016565 0ustar otfriedotfried Ipe Manual -- 12 History and acknowledgments
13 CopyrightTop11 The command line programs12 History and acknowledgments

12 History and acknowledgments

The name "Ipe" is older than the program itself. When I made figures for my papers using Idraw in 1992, I was annoyed that I had to store two versions of each figure: one with Latex text, one with Postscript information. I came up with a file format that I called "Ipe", for "Integrated Picture Environment", and which was at the same time legal Latex source code and a legal Postscript file.

When I wrote the first version of Ipe at Utrecht University in the summer of 1993, it created this file format directly, and inherited the name. The first versions of Ipe (Ipe 2.0 up to 4.1) were based on my experiences with Idraw, XFig, and Jean-Pierre Merlet's JPDraw, used IRIS-GL and Mark Overmars' FORMS library, and run on SGI workstations only.

Due to popular demand, I spent two weeks in the summer of 1994 to teach myself Motif and to rewrite Ipe to run under the X window system. Unfortunately, two weeks were really not enough, and the 1994 X-version of Ipe was somewhat of a hack. I didn't have time to port the code that displayed bitmaps on the screen, it crashed on both monochrome and truecolor (24-bit) displays, and was in general quite unmaintainable.

These versions of Ipe were supported by the Netherlands' Organization for Scientific Research (NWO), and I would never have started working on it without Geert-Jan Giezeman's PLAGEO library. For testing, support, and inspiration in that original period, I'm grateful to Mark de Berg, Maarten Pennings, Jules Vleugels, Vincenzo Ferrucci, and Anil Rao. Many students of the department at Utrecht University served as alpha-testers (who apparently referred to Ipe as "the cute little core-dumper").

I gave a presentation about Ipe at the Dagstuhl Workshop on Computational Geometry in 1995, and made a poster presentation at the ACM Symposium on Computational Geometry in Vancouver in the same year. Both served to create a small but faithful community of Ipe addicts within the Computational Geometry community.

Ipe proved itself invaluable to me over the years, especially when we used it to make all the illustrations in our book "Computational Geometry: Algorithms and Applications" (Springer 1997, with Mark de Berg, Marc van Kreveld, and Mark Overmars). Nevertheless, the problems were undeniable: It was hard to compile Ipe on other C++ compilers and it only worked on 8-bit displays. It was only due to the efforts of Ipe fans such as Tycho Strijk, Robert-Paul Berretty, Alexander Wolff, and Sariel Har-Peled that the 1994 version of Ipe continued to be used until 2003.

I was teaching myself C++ while writing the first version of Ipe, and it showed—Ipe 5 was full of elementary object-oriented design mistakes. When teaching C++ to second-year students at Postech in 1996 I started to think about a clean rewrite of Ipe. My first notes on such a rewrite stem from evenings spent at a hotel in Machida, close to IBM Tokyo in July 1996 (the idea at that time was to embed Ipe into Emacs!). It proved impossible, though, to do a full rewrite next to teaching and research, and nothing really happened until the Dagstuhl Workshop on Computational Geometry in 2001, where Christian Knauer explained to me how to use Pdflatex to create presentations. I realized that PDF was ideally suited for a new version of Ipe.

Ipe 5 figures were at the same time Latex and Postscript files, and required special handling to be included into Latex documents, which sometimes required a bit of explaining when talking to co-authors or publishers. While editing a figure, Ipe 5 kept a Ghostscript window open that would show what the figure looked like after processing by Latex.

Several developments that had happened between 1993 and 2001 allowed me to use a completely new approach: First, Hàn Thê Thàn's Pdflatex takes Latex source and directly produces a PDF file with a PDF representation of the text and all necessary fonts. Second, Derek Noonburg's Xpdf contained an open-source PDF parser that I could use to parse this PDF representation and to extract the processed text and fonts. Third, all relevant Latex fonts are now available as scalable Type1 fonts, and so it is possible to embed Latex text and formulas in figures that may still need to be scaled later. Finally, the Ghostscript window was no longer necessary as Ipe could use the beautiful Freetype library to directly display the text on-screen as it will appear on paper.

Directly after the Dagstuhl workshop I implemented a proof-of-concept: I defined the Ipe XML format (there was no question that Ipe 6 would have to be able to communicate in XML, of course), wrote "ipe5toxml" (reusing my old Ipe parsing code) and a program that runs Pdflatex, parses its PDF output, extracts text objects and font data, and creates a PDF file for the whole Ipe figure.

All that remained to be done was to rewrite the user interface. Mark de Berg and the TU Eindhoven made it possible for me to take some time off from teaching and research. The final design changes were made during the Second McGill-INRIA Workshop on Computational Geometry in Computer Graphics at McGill's Bellairs Research Institute in February 2003, and much inspiration was due to the atmosphere at the workshop and the magnificient cooking by Gwen, Bellair's chef. An early preview of Ipe 6.0 was "formally" released at the Dagstuhl Workshop on Computational Geometry in March 2003, to celebrate the Dagstuhl influence on Ipe.

Other than the file format, there weren't really that many changes to Ipe's functionality between Ipe 5 and Ipe 6. René van Oostrum insisted that no self-respecting drawing program can do without style sheets and layers. Views allow you to incrementally build up a page in a PDF presentation.

I also revised the interface to ipelets (which used to be called "Iums" in the good old days when people still thought that "applets" were small apples)—it is now based on dynamically loaded libraries (a technology that was still somewhat poorly understood in the early nineties, at least by me).

And, of course, there was a Windows version of Ipe 6. Who would have thought that ten years earlier!

There were many releases of Ipe 6.0, all of them called "previews", because I never considered that I had reached a stable state. A number of experimental features were tried and either built into Ipe or discarded. Ipe 6 migrated from Qt 2 and Qt 3 to Qt 4, a somewhat painful process due to a number of annyoing Qt bugs that cost me a lot of time.

When in 2007 I discovered the fantastic Cairo library for rendering, I immediately decided to switch Ipe to use this: a small dedicated library with a nice API to do the rendering, instead of the buggy monster that was Qt. The Cairo API fit Ipe so well that I could write a Cairo painter for Ipe in an hour or so. Cairo supports Freetype directly, instead of Ipe having to render each glyph into a bitmap that is then blit onto the canvas.

I made the huge mistake of announcing on the Ipe discussion list that Ipe 6.0 preview 28 was the last version of Ipe 6, and that there would soon be a new version, Ipe 7. I should have known that this was impossible during a time where I advised several graduate students, taught several new courses, and went through the tenure process. I had to release several bugfix releases of Ipe 6 while really wanting to work on Ipe 7.

However, the delay left me with enough time to carefully think about another change I wanted to make: It would be nice if Ipe embedded a scripting language that could be used to write simple ipelets without compilation. I looked at Scheme/Guile, Python, and Lua, and finally decided for Lua: a small, elegant, stable language with a tiny footprint, easily embedded with a very nice C interface.

In 2009, I had my first sabbatical ever, which I spent in the group of Ulrik Brandes at the University of Konstanz. Here I finally had the time to work on Ipe 7, and I'm very grateful to Ulrik and all members of his group for the wonderful time I had in Konstanz. Next to the two big changes mentioned above, Ipe 7 introduced tiling patterns, gradients, clipping paths, transparency, user-definable arrows and marks, and SVG output.

I wanted to avoid Qt in Ipe 7 as it had caused me quite a bit of pain during the life of Ipe 6, but it was hard to find a good replacement that would allow Ipe to run on Linux, Windows, and Macs. During the Korean Workshop on Computational Geometry organized by Tetsuo Asano at Hakusan seminar house in June 2009, I discussed using Ipe on tablet PCs with Vida Dujmovic, Jit Bose, and Stefan Langerman. It is their fault that Ipe 7 comes with a tablet input tool, and finally Stefan and Sébastien Collette convinced me that there isn't really an alternative to Qt that has the same support for tablets and Macs. So Ipe 7 is still using Qt, but in a much more restricted way than before—it turned out that this part of Qt is quite stable and not prone to new bugs.

Even though I was only using a small part of Qt to create the UI, I still had to bundle the huge Qt library, ten times the size of Ipe itself, with Ipe's binary builds for Windows and OSX. This bothered me, since of course Windows and OSX already provide all the functionality for building UIs natively. After some experimentation with building simple UIs in Windows and GTK, I settled on a new architecture where the UI library would only be used in the Ipe program itself, in the Ipe canvas, and in the small Lua library ipeui that can be used to build dialogs from Lua (and which is entirely independent of Ipe). The native Windows UI was finished while I was visiting Emo Welzl in Zurich in early 2015, on a small Windows-tablet, and was first released in Ipe 7.1.7. During my sabbatical at Bayreuth University in 2016 Christian Knauer and his group provided me with a Mac in my office, providing both the opportunity and the time to learn Objective C and Cocoa. Ipe 7.2.1 was released in Bayreuth with the first native OSX UI.

ipe-7.2.13/build/doc/structipe_1_1_document_1_1_s_properties-members.html0000644000175000017500000001234413561570220026240 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Document::SProperties Member List

ipe-7.2.13/build/doc/manual_61.html0000644000175000017500000002733213561570220016560 0ustar otfriedotfried Ipe Manual -- Contents
FootnotesTop13 CopyrightContents

Contents

ipe-7.2.13/build/doc/functions_l.html0000644000175000017500000001247313561570220017320 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- l -


ipe-7.2.13/build/doc/functions_b.html0000644000175000017500000001156413561570220017306 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- b -


ipe-7.2.13/build/doc/structipe_1_1_select_tool_1_1_s_obj-members.html0000644000175000017500000000510013561570220025304 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::SelectTool::SObj Member List

This is the complete list of members for ipe::SelectTool::SObj, including all inherited members.

distanceipe::SelectTool::SObj
indexipe::SelectTool::SObj

ipe-7.2.13/build/doc/functions_t.html0000644000175000017500000002266313561570220017332 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- t -


ipe-7.2.13/build/doc/onepage_2.html0000644000175000017500000000615113561570220016630 0ustar otfriedotfried Ipe Manual -- Footnotes
TopContentsFootnotes

Footnotes

 (1)
The line width can be set to zero to get the thinnest line the device can produce (i.e. approximately the same as 0.15 for a 600 dpi printer or 0.3 for a 300 dpi printer). The PDF and Postscript authorities discourage using this feature, since it makes your Postscript files device-dependent.
 (2)
J. D. Foley, A. Van Dam, S. K. Feiner, and J. F. Hughes, Computer Graphics: Principles and Practice, Addison-Wesley, 1990.
 (3)
Fifi is called after the dog in the rogue computer game installed on most Unix systems in the 1980's, because it also keeps running around your feet.
ipe-7.2.13/build/doc/functions_vars.html0000644000175000017500000000322213561570220020030 0ustar otfriedotfried Ipelib: Class Members - Variables
Ipelib
 

- a -


ipe-7.2.13/build/doc/sync_off.png0000644000175000017500000000152513561570220016417 0ustar otfriedotfried‰PNG  IHDRàw=øIDATxíÝKhTWÀñÿä1I&3™8M¦Iš™†I3Ú©b$cÌ I1V1±-(Tö±±Ð.* t!‚K[¥Ä¥ˆ„¨´f£`l(øl©"Y”¤6ÆgÌTú}·sgîܹ ±d{8?æÌ¹÷;çÜuíÚ`:!±F¬¢BäŠ?ŰÄm'yÊÅ>ÑlU¯½üý‰è_‹?€Œê ]€Y(ŠNñ±8fý1°Öqún-eâ¨øtºmâÈ Ó0}b›ù%·©µ×Œ®=Ÿ0´³?Š1sŸ‹0€¯8À‘;_ ‹W|%\ Zð— >舽ln¨p©.aÇ{ )t;Ú b nŸš¯›65°¢¡2çÅÔ?Žž>Oдàuönm¤¢Ì`×­Z¬WjC~>‘Ö¾0+á {{©fÝ×Mæ·æÅ•ìÙ¼˜` Ý›%uA6´½ÅÆö¨Á,]k¢ÄW¼™u±›]‹ˆ7§¯iòh€ ¶¶¬ÏÖu1 ló —Ҷ̺–:ÞÍ\ÄcãÏxøhR²Êè‡Qt$¿ß§¨ ª fdºü<4BÿÙ[•f¸d7=.Mé9/—éªÃëù/ÿO Üaàò}€,‘j?Ÿõ.5Úšm?œÿŸ®ŽXÿ2¬#¸d píæ(£?cÛú¼!½›a1¥Þ—ŽòØ©ܾ7dÔK:‚ùÒ‰ì)Ê3‚Ü™àÌà]€,±H€µ+køöäu<|`·LhC7¹ÔeÍ Ÿ×Ÿ˜tÜ‹ óH$^2%l.êaeÐäýE”ÌÉ|ÅÜìî‰Ýsä }¸ýDû^hzé~ðR›¦Ã¡¿]|#ü¯@×—Ö‡[k¹–<|š(Ç*€Ý¹dÇtMé:Ýñø«Ø,êÅû¢]”' øXÓ_nò¡Æ|Øý /c§fžâOIEND®B`‚ipe-7.2.13/build/doc/classipe_1_1_canvas_observer-members.html0000644000175000017500000000755013561570220024132 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::CanvasObserver Member List

This is the complete list of members for ipe::CanvasObserver, including all inherited members.

canvasObserverMouseAction(int button)ipe::CanvasObservervirtual
canvasObserverPositionChanged()ipe::CanvasObservervirtual
canvasObserverSizeChanged()ipe::CanvasObservervirtual
canvasObserverToolChanged(bool hasTool)ipe::CanvasObservervirtual
canvasObserverWheelMoved(double xDegrees, double yDegrees, int kind)ipe::CanvasObservervirtual
~CanvasObserver()ipe::CanvasObservervirtual

ipe-7.2.13/build/doc/functions_func_p.html0000644000175000017500000003031713561570220020334 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- p -


ipe-7.2.13/build/doc/manual.css0000644000175000017500000000066613561570220016077 0ustar otfriedotfriedbody, table, div, p { font-family: Georgia, serif; } h1 { font-family: Lucida Grande, Verdana, Geneva, Arial, sans-serif; color: #153788; text-align: left; } h2 { font-family: Lucida Grande, Verdana, Geneva, Arial, sans-serif; color: #153788; text-align: left; } h3 { font-family: Lucida Grande, Verdana, Geneva, Arial, sans-serif; color: #153788; text-align: left; } em { color: #FF9900; }ipe-7.2.13/build/doc/functions_v.html0000644000175000017500000001020713561570220017323 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- v -


ipe-7.2.13/build/doc/folderclosed.png0000644000175000017500000000115013561570220017250 0ustar otfriedotfried‰PNG  IHDRÚ}\ˆ/IDATxí]MOÔ@~ÚúuØlp]ö¿#›Å]PYECˆ\9ù¼yÑß`ÖÄÿàÿÀÉxóâ¢C &=qÐÄ£—vZçv¶3m؃‡vžLûNç}Þ÷}Þ½ZA@n° OäNp ’xóþK°ññ€xÜj”°8sÑ€“ “€œ_¼[Âíæ§ïD'‚•yye+ø¼û 7#rNŸlïük* ¾0Ь_d«_(àñÖ±àôz=ñxõv§÷h©‰z¹€šØP-äóä’̪uý¼$»\DãJc—B4¯ãÝÖ.:£Ï-ÑÏß}µŠLEíºþ #—ûáºÀÏgN;BŠ€6ïýñ䬜…ö@’Ðåñp&™h>p9¤™EEά¨ÎÊ‘" u¥n€$R"?{¹<˜…ë…%PNtâ$‰ß¶±úá+^<é"§2 ªDq”q´\¬«Ò™a–Œ‘©Aÿ€"Ôµ ™êŸèP£}#Eàz{û.8i îp³ê(ADwD¦E<ê¬cE¦$ HdÊÄ ”.:Ù GŽ-`ŒL‚ý¾'¢‰Ä<¤CIª½;ÙÇTZd±i};>èôß‚z×;K×§8t ¤Ž q”:uvÿv•Ý›¬²ÙvEân{„M·FXg¼ÌfZÖ¨°¹‰*›ßÌß©±ù©:›j–YqèÜë#3çÏSøWøÿÿÑr'ø Ôùù‚ ©¡IEND®B`‚ipe-7.2.13/build/doc/classipe_1_1_pdf_writer.html0000644000175000017500000006272113561570220021466 0ustar otfriedotfried Ipelib: ipe::PdfWriter Class Reference
Ipelib
ipe::PdfWriter Class Reference

#include <ipepdfwriter.h>

Public Member Functions

 PdfWriter (TellStream &stream, const Document *doc, const PdfResources *resources, uint32_t flags, int fromPage, int toPage, int compression)
 
 ~PdfWriter ()
 
void createPages ()
 
void createPageView (int page, int view)
 
void createBookmarks ()
 
void createNamedDests ()
 
void createXmlStream (String xmldata, bool preCompressed)
 
void createTrailer ()
 

Detailed Description

Create PDF file.

This class is responsible for the creation of a PDF file from the Ipe data. You have to create a PdfWriter first, providing a file that has been opened for (binary) writing and is empty. Then call createPages() to embed the pages. Optionally, call createXmlStream to embed a stream with the XML representation of the document. Finally, call createTrailer to complete the PDF document, and close the file.

Some reserved PDF object numbers:

  • 0: Must be left empty (a PDF restriction).
  • 1: XML stream.
  • 2: Parent of all pages objects.
  • 3: ExtGState resource from pdflatex
  • 4: Shading resource from pdflatex
  • 5: Pattern resource from pdflatex
  • 6: ColorSpace resource from pdflatex

Constructor & Destructor Documentation

◆ PdfWriter()

PdfWriter::PdfWriter ( TellStream stream,
const Document doc,
const PdfResources resources,
uint32_t  flags,
int  fromPage,
int  toPage,
int  compression 
)

Create a PDF writer operating on this (open and empty) file.

Referenced by ipe::PdfPainter::doDrawSymbol().

◆ ~PdfWriter()

Member Function Documentation

◆ createPages()

void PdfWriter::createPages ( )

Create all PDF pages.

References ipe::SaveFlag::MarkedView.

Referenced by ipe::Document::exportPages(), and ipe::Document::save().

◆ createPageView()

◆ createBookmarks()

void PdfWriter::createBookmarks ( )

Create the bookmarks (PDF outline).

References ipe::String::empty(), ipe::PdfPainter::iStream, ipe::SaveFlag::MarkedView, and ipe::size().

Referenced by ipe::Document::save().

◆ createNamedDests()

void PdfWriter::createNamedDests ( )

Create the named destinations.

References ipe::String::empty(), ipe::PdfPainter::iStream, and ipe::SaveFlag::MarkedView.

Referenced by ipe::Document::save().

◆ createXmlStream()

void PdfWriter::createXmlStream ( String  xmldata,
bool  preCompressed 
)

Create a stream containing the XML data.

References ipe::String::data(), ipe::PdfPainter::iStream, ipe::String::size(), and ipe::String::unicode().

Referenced by ipe::Document::save().

◆ createTrailer()


The documentation for this class was generated from the following files:
  • ipepdfwriter.h
  • ipepdfwriter.cpp

ipe-7.2.13/build/doc/up.png0000644000175000017500000000225013561570220015231 0ustar otfriedotfried‰PNG  IHDR D¤ŠÆsRGB®ÎégAMA± üa cHRMz&€„ú€èu0ê`:˜pœºQ<PLTEÿÿÿ™ÌÿÂõ†¹ì|¯âs¦ÙiœÏ_’ÅV‰¼L²Cv©:m 0c–&YŒPƒFy =p3f sx pHYsÄÄ•+IDAT8O}“Y„ D\@Íý/;dÍÇLyv’&tý#\sÒÝó.„OÀD7…ñ¢ˆ˜%O×X‰ð’f¢6ŠÀžóDG‘¨€ 5O´g¢Cjc1"Ú>Ƭ„^ó+ÿœÚ‹¢€Ó#?ñ_쵚ú¥€$Ò'‹ÈôìR€¥4ûÆ@òQ:š@!U ìMd€l6mn©mš'v=çÍÄ=àlféÕÖ!Ÿ5—%6¬Í¾d£ôPnÃÔwÁbÐð¡P‡¨ö0ªÑï 3eŒC…C4S£±*œ\¢}Weaä¹ó[X¶å} Ù–æÙ1 =Lk ݈Çë¾?„xxS ˆIEND®B`‚ipe-7.2.13/build/doc/classipe_1_1_shape-members.html0000644000175000017500000001610713561570220022046 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Shape Member List

This is the complete list of members for ipe::Shape, including all inherited members.

addToBBox(Rect &box, const Matrix &m, bool cp) constipe::Shape
appendSubPath(SubPath *sp)ipe::Shape
countSubPaths() constipe::Shapeinline
distance(const Vector &v, const Matrix &m, double bound) constipe::Shape
draw(Painter &painter) constipe::Shape
isSegment() constipe::Shape
load(String data)ipe::Shape
operator=(const Shape &rhs)ipe::Shape
save(Stream &stream) constipe::Shape
Shape()ipe::Shape
Shape(const Rect &rect)ipe::Shapeexplicit
Shape(const Segment &seg)ipe::Shapeexplicit
Shape(const Vector &center, double radius)ipe::Shapeexplicit
Shape(const Vector &center, double radius, double alpha0, double alpha1)ipe::Shapeexplicit
Shape(const Shape &rhs)ipe::Shape
snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Shape
snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound, bool cp) constipe::Shape
subPath(int i) constipe::Shapeinline
~Shape()ipe::Shape

ipe-7.2.13/build/doc/classipe_1_1_buffer_source.html0000644000175000017500000001567413561570220022157 0ustar otfriedotfried Ipelib: ipe::BufferSource Class Reference
Ipelib
ipe::BufferSource Class Reference

#include <ipebase.h>

Inherits ipe::DataSource.

Public Member Functions

 BufferSource (const Buffer &buffer)
 
virtual int getChar ()
 
void setPosition (int pos)
 
- Public Member Functions inherited from ipe::DataSource
virtual ~DataSource ()=0
 

Detailed Description

Data source for parsing from a buffer.

Constructor & Destructor Documentation

◆ BufferSource()

BufferSource::BufferSource ( const Buffer buffer)

Member Function Documentation

◆ getChar()

int BufferSource::getChar ( )
virtual

Get one more character, or EOF.

Implements ipe::DataSource.

References ipe::Buffer::size().

◆ setPosition()

void BufferSource::setPosition ( int  pos)

The documentation for this class was generated from the following files:
  • ipebase.h
  • ipebase.cpp

ipe-7.2.13/build/doc/functions_h.html0000644000175000017500000000606413561570220017313 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- h -


ipe-7.2.13/build/doc/manual_1.html0000644000175000017500000001157013561570220016467 0ustar otfriedotfried Ipe Manual -- 1 Introduction
2 About Ipe filesTop1 Introduction

1 Introduction

Preparing figures for a scientific article is a time-consuming process. If you are using the LaTeX document preparation system in an environment where you can include (encapsulated) Postscript figures or PDF figures, then the extensible drawing editor Ipe may be able to help you in the task. Ipe allows you to prepare and edit drawings containing a variety of basic geometry primitives like lines, splines, polygons, circles etc.

Ipe also allows you to add text to your drawings, and unlike most other drawing programs, Ipe treats these text object as LaTeX text. This has the advantage that all usual LaTeX commands can be used within the drawing, which makes the inclusion of mathematical formulae (or even simple labels like "qi") much simpler. Ipe processes your LaTeX source and includes its Postscript or PDF rendering in the figure.

In addition, Ipe offers you some editing functions that can usually only be found in professional drawing programs or cad systems. For instance, it incorporates a context sensitive snapping mechanism, which allows you to draw objects meeting in a point, having parallel edges, objects aligned on intersection points of other objects, rectilinear and c-oriented objects and the like. Whenever one of the snapping modes is enabled, Ipe shows you Fifi, a secondary cursor, which keeps track of the current aligning.

One of the nicest features of Ipe is the fact that it is extensible. You can write your own functions, so-called ipelets. Once registered with Ipe by adding them to your ipelet path, you can use those functions like Ipe's own editing functions. (In fact, some of the functions in the standard Ipe distribution are actually implemented as ipelets.) Ipelets can be written in Lua, an easy-to-learn interpreted language that is embedded into Ipe, or also in C++. Among others, there is an ipelet to compute Voronoi diagrams.

Making a presentation is another task that requires drawing figures. You can use Ipe to prepare presentations in PDF format. Ipe offers many features to make attractive presentations.

Ipe tries to be self-explanatory. There is online help available, and most commands tell you about options, shortcuts, or errors. Nevertheless, it would probably be wise to read at least a few sections of this manual. The chapter on general concepts and the chapter explaining the snapping functions would be a useful read. If you want to use Ipe to prepare presentations, you should also read the chapter on presentations.

ipe-7.2.13/build/doc/functions_func_k.html0000644000175000017500000000372213561570220020327 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- k -


ipe-7.2.13/build/doc/doxygen.png0000644000175000017500000000730313561570220016266 0ustar otfriedotfried‰PNG  IHDRh ;ˆØŠIDATxí]y\•Õº~45%TL Q”PE"q–Û11±]8a„w*©¨(*â" ˆzÀè`8 ¨‰¢mÅ,’òà„p$%”œBó(8k†Ü÷ýÜû6lòö»§k÷Ç÷[ÏÞß·Ö;?k½ëßÕÕÕPxÑêÏ't´ÏùÈ€zÀÇÅ3_€Q4€g@œmÿ ¾ò‰âci‰ôçÿ{ ðÇð¬ù~½Á€4:õHcÂü ðŸÁ³„ª'ÕPÆæ P7^h،♠zb„cóP¨„ 3‚† Ò}çÿO²qÁºNkÝTÛ(É?d Ç~z<’«4Óǡ؞Þv­zµÙ¦õ¬ZâdÛ,Ë6Ók±]Fz< ¾ZçƒsÕ?ìƒsUø2SÉåwê1”c`[ì—}%ѽ.Ô¼6‚BLZ˜û!F8[ ¹…×TéÛ— »Þ#gó]å:vžu?‡vèbÙR˜?wùŽŸ¾ÊÐgbÑÉÌÕ$kF~Ê;عÆ•¢ïX®?ÉèlÆÙôõà»Nʪ¼­,ìHC§gAz•ÆlÓº­gÑú ]œjÎñåM…3ÓÚæoÒ³'=‘$Ò÷f}G•ŸS_‡öèco.Êȹ :ó£ Ãds®Ù:1=¼{ƒå9?÷ý…zqÛvîÓi‰D’p¿Ë šmÙíoÛâýaÖüEqÒµwÌ}¿~{òj€ç{ôºŸFNëí[ëOq·ÇOSúXO]°>‚‚muæÄ¾e¤“5Ë{¨JÕ¯£(›´«bÂçû’ÍlÓÅ}žïú`éUÞy„ac§Á†ÔCºŠóAkl‘±y¥†ô¢ùôs÷Aø¬7ÄõôoJ±äÄ ù.¥Be. Z¬Ð×ÇÈöå¹­ù'Ù-PëìŠyF.ž‚žÝÚ€lp&.êˆð•jò7’re’z19»ã§HGíø%œüq°ïüz׈c¬_k_")ŸHJnÐÑ~ˆÐÖ˜á´äÕ5 µÁq€ÿ5#¸·îà¶+9T‘‚ ðŽ÷Rܸrz“Ï´Ì =Ï…{ðáO£Èf ¡Íwg|Ž’Ü/¢Þ$÷¯¢ëðúÀ;¿à¨Ö™âÒÆ­]¯ÜW"Þ/< ‡÷DÏà°½üB}çyIEc^—ƒ=[V“Ýh²ëMä$l];Kû®¸ýr¦È*Åò ÿtÒõ$]•MŸ÷´;×I€1èó!‚œõ¸M õ¨(fÌæ<ÁÎÎò5~z¿ù¶ž mÌêÕ >–âÚ©âëˆIÎÞçz;ãu[i·eç^ÆÜÙÓ³NÞëF6B\}7†»+üŽÓ,Ã'a ½˜-yHY¿,‘^—ñfú~ß?Hcø¸…¸ñó{Z+4\såƒû·¯Ù·nߣð«íFÆ¡sغëû§D¾?ò<–Ævkx0ÅM±ælذÁIÓxÿd”žÜÉ÷EE»AªM«g*È£YEí7Û™^[uíý®v[wGå†=Ed¼n×¶ÆæÖÅl¡'¨pGÚk+‹æ¢À¬¨C8ªâš2 dz3H£ß ¡¨BÒûSÃÅù[wŘ ~xpçútÁæmö¤Å£¥iQæ­‰AB1ÉfÙ‰›4u¹ïìIÒ]Ë6äò%ÿ†† 1t.’NJph¬zÌ ÎR1Ž"3-"¸‡‹&ìó°1âüžìó[:‡ï„¼‘……N m–“W0®_èÜœ ×õ6ùò&»)Æìꦬýæ}¬ñ~»{múù]z½£M•ºP~^Îá:eQTÙ_*7ÕÄ9É8—·Ëï 3°¶47E•î¿u÷“SÉ»U¯ _ NíºôW¬e¸ÄNÓ|»;™¿;ŒæÅd"ȉôøòÞµõï¾®½"èÄ´ÖMM+bYµ‘_ÉæEÝüÎ]P»¹XKÐI½Þ¥oE<_¹(„EP±Œ|mÇÁ¡‘Ý,ŠÓ©ººZ±Îߺ§×kÝ,kÍMš`Äø…jzeU»æ ™Át3ÓÀ½˜6—ÒöùË·r¨¹Ñ}““wö:Χùë¼ ¿|‚TܵÉQˆKßç_ÁâÀ™œ”pÑÐóໃ¼Ydâ0!®àa –øöçW$ÃÁ‘Á$/\¬$ð 2ÞímÞLH‹Ÿ èd£HVÜ,:ò½»RÍZšJ­a„z*>‹_…NT(ù‚^SVF­U¹8ñEþôñ܈óùnd;«®8™\C]ø=Èêm¬Æ:‚´ÆbãDd=Áãßžˆ‹UU5O‹|]þð®Pèêv‰á\]2ßìÿ"yÈ[ïyʧz£g{Y«{„Ùø5©ÿ;w{N3é­nâĨw§Á¢ÍK¢Ý­ûÏ29Id¿’ì y)ìPÞò8ŒÅ©¯‰±@mPÔñwjl,6 áhWÕ˜d öà uõmÁp®.™á£Ç…twöR x­BδYcŒxg*vo  yò‘•“[¬?ÜVœ˜0ÒN¡O난~Žó’¯·h#´Hkýœ±8kÓß^Àq@]àÓ“ø,56´¯÷Í-κU»n…[>]@nîøÏœp›[œ6# €4tën¯:ŽÒþ}…—8äT9_žY$/´G’K™©ù†•(óÑ’Mø©`ŸÉdѺ;ùO‹B Ó&P{qöhJÉ+Úé–§¦l2«MïöÝ_1ÑÓ«’t¸½±l€ëØya ¦ô©«®½ÆL^¬žêñš¸ùy.¾Û½Š[ u/]½‹iS}øN>²e1™q‡jfÚ&¢©iT\=kÏ›ÀXô-.84V5ðu!TE˜ þ.ŒOH´¶4—zwTr.ï‰¦Ë xõµ·œÖ„HÆù£žÈHùg Ñhñ’T$ßyq¸zþ¨p¿´ë< q•ró÷š‰wÿÍÑð–I]´–æI²é²˜sÂ"×:Õ–bÕ¦“ÈÙL6¢9VÊÓWž§<æ;”3?ý©Mê3AV#µ±ËÞ¯‘ž K£UrÝ9!›qát¦H£Ù+6ÇV…/TS^pÃùqgLP'Ú5E ‚–ÀÞºîÄ Ën"2|Ÿ;®W»Îý"Ö¬TwÖâµtúŽO'› á+W Ã+¦âZÌ–<ÕÆ&nOÝ,IŠ£06.ÁZ.Çñúøh*INÚ’Oe½ÉgBXÐÔZóäøä9èü“hÒíDSš¥¡Ê µA¯/Ôc¸ö“`A§¯"zå|‘ €ÅŸ¨ú;HÍ#‚Î|%ÄOˆƒ«OàÌÉÐÜD ž mÜðâc–ƤÉÂqm¶uË&~÷núÒË £ÇÏ€ZÕj =«_n[‡‡÷nN§ÏÝ$_¾bE˜‚€Õ)ù8¾?6‘lú“ÍÙæÖ}#bW( œ³d-®•p&¡ý’œÖa”"9öõņÐ$’Ú›AÜ!ä;ÐÑõè{~á¹8‘ÛÞ£1ÛÓÉ0ž`²#´kÒuäNÅÖ Q¹bhæ ”8ûÓMáŽa›•¿”w±h²¢®qŠæ°(bK ‚’Z¾Ò%ÐÆémáãÖË(Éý‚ÛJ)@> þ›7% ï{y Á“¾ÆÒîohfòô>{pÿ.­_Î%±ÉèägëlZØ\B2B #™¸ÚüÒºp‚hÝšü®[¥Ü<‹#SpñÌA7’ãØHƒt4:Ÿ|g¨tÓL¶*($Æ©»ì…®ù’ó÷$;b›ÔÙ`=¶£¦M„MÌÄ5ò«·Ç¾“H·ÌH.¼žHeAîº5}r­dõ¨±)ÀT};€Q5iÖ2…O0ü…0óñÃ;óæ,Š´²µ냔}g‘£]‹7å9ˆà©_{üèîêžC>úhê{Ž .ÈìðIIð€?[Kswz6Òuíý¬;µ€ç§OåâJÉa˶zv°éd† ¤µâ‚l´é舊«Åüy¾c÷ÁèÖÍ'ràúÅ™TWÕôÓ°¡L €|ʽŒ¼ì­høBã ÝTëî'ò]Kø£ìâÏ(=¹Kx €¿ LÌ,Pý¤Êµu‡¹…׈ §Å¾÷à1Ý«Äý;¿pGDäxZYÛ kfæ6¸ùóæ7®œ®þ6·ÕoÚ¾ÔH~ò®Þ¸â 8Uø“p<ºw3¡a£ÏÑ’‘3èÏ"€bˆ-ÎܺÏ_ªÅ]+ËM©zü°s“f-êçhÇãÑýÊãôÿ5}ZQNb{Ó?å%ÿ\SUõعIÓæ}~}p[œoÔÄ„êÐMMZáNÅå@>Œ„²á6(?¡Åé âK½+ü?À%ÝÝ·/Ç1‚9áUø?B)”ÕèâÞlÈÒêÏ @=àùÄÞžk­®ÅIEND®B`‚ipe-7.2.13/build/doc/manual_36.html0000644000175000017500000000732513561570220016562 0ustar otfriedotfried Ipe Manual -- 8.2 Sharing Latex definitions with your Latex document
8.3 Writing ipelets8 Advanced topics8.1 Multiple figures in one Ipe document8.2 Sharing Latex definitions with your Latex document

8.2 Sharing Latex definitions with your Latex document

When using Ipe figures in a Latex document, it is convenient to have access to some of the definitions from the document.

Ipe comes with a Lua script update-master that makes this easy.

In your Latex document, say master.tex, surround the interesting definitions using %%BeginIpePreamble and %%EndIpePreamble, for instance like this:

  %%BeginIpePreamble
  \usepackage{amsfonts}
  \newcommand{\R}{\mathbb{R}}
  %%EndIpePreamble

Running the script as

  ipescript update-master master.tex
extracts these definitions and saves them as a stylesheet master-preamble.isy. (This filename is fixed, and does not depend on the document name.)

Running this script as

  ipescript update-master master.tex figures/*.ipe
creates the stylesheet master-preamble.isy as above. In addition, it looks at all the Ipe figures mentioned on the command line. The script adds the new stylesheet to each figure, or updates the stylesheet to the newest version (if the figure already contains a stylesheet named "master-preamble").
ipe-7.2.13/build/doc/structipe_1_1_gradient_1_1_stop-members.html0000644000175000017500000000503213561570220024462 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Gradient::Stop Member List

This is the complete list of members for ipe::Gradient::Stop, including all inherited members.

coloripe::Gradient::Stop
offsetipe::Gradient::Stop

ipe-7.2.13/build/doc/classipe_1_1_style_sheet.html0000644000175000017500000017224213561570220021651 0ustar otfriedotfried Ipelib: ipe::StyleSheet Class Reference
Ipelib

#include <ipestyle.h>

Classes

struct  PageNumberStyle
 
struct  TitleStyle
 

Public Member Functions

 StyleSheet ()
 
void addSymbol (Attribute name, const Symbol &symbol)
 
const SymbolfindSymbol (Attribute sym) const
 
void addGradient (Attribute name, const Gradient &s)
 
const GradientfindGradient (Attribute sym) const
 
void addTiling (Attribute name, const Tiling &s)
 
const TilingfindTiling (Attribute sym) const
 
void addEffect (Attribute name, const Effect &e)
 
const EffectfindEffect (Attribute sym) const
 
void add (Kind kind, Attribute name, Attribute value)
 
bool has (Kind kind, Attribute sym) const
 
Attribute find (Kind, Attribute sym) const
 
void remove (Kind kind, Attribute sym)
 
void saveAsXml (Stream &stream, bool saveBitmaps=false) const
 
void allNames (Kind kind, AttributeSeq &seq) const
 
bool isStandard () const
 
String preamble () const
 
void setPreamble (const String &str)
 
const Layoutlayout () const
 
void setLayout (const Layout &margins)
 
const TextPaddingtextPadding () const
 
void setTextPadding (const TextPadding &pad)
 
const TitleStyletitleStyle () const
 
void setTitleStyle (const TitleStyle &ts)
 
const PageNumberStylepageNumberStyle () const
 
void setPageNumberStyle (const PageNumberStyle &pns)
 
void setLineCap (TLineCap s)
 
void setLineJoin (TLineJoin s)
 
void setFillRule (TFillRule s)
 
TLineCap lineCap () const
 
TLineJoin lineJoin () const
 
TFillRule fillRule () const
 
String name () const
 
void setName (const String &name)
 

Static Public Member Functions

static StyleSheetstandard ()
 

Detailed Description

A style sheet maps symbolic names to absolute values.

Ipe documents can use symbolic attributes, such as 'normal', 'fat', or 'thin' for line thickness, or 'red', 'navy', 'turquoise' for color. The mapping to an absolute pen thickness or RGB value is performed by a StyleSheet.

Style sheets are always included when the document is saved, so that an Ipe document is self-contained.

The built-in standard style sheet is minimal, and only needed to provide sane fallbacks for all the "normal" settings.

Constructor & Destructor Documentation

◆ StyleSheet()

StyleSheet::StyleSheet ( )

The default constructor creates an empty style sheet.

References ipe::EDefaultCap, ipe::EDefaultJoin, and ipe::EDefaultRule.

Member Function Documentation

◆ standard()

StyleSheet * StyleSheet::standard ( )
static

Create standard built-in style sheet.

References ipe::ImlParser::parseStyleSheet().

Referenced by ipe::Document::Document(), and ipe::PdfThumbnail::PdfThumbnail().

◆ addSymbol()

void StyleSheet::addSymbol ( Attribute  name,
const Symbol symbol 
)

Add a symbol object.

References ipe::Attribute::index(), and ipe::Attribute::isSymbolic().

Referenced by ipe::ImlParser::parseStyle().

◆ findSymbol()

const Symbol * StyleSheet::findSymbol ( Attribute  attr) const

Find a symbol object with given name.

If attr is not symbolic or if the symbol doesn't exist, returns 0.

References ipe::Attribute::index(), and ipe::Attribute::isSymbolic().

◆ addGradient()

void StyleSheet::addGradient ( Attribute  name,
const Gradient s 
)

Add gradient to this style sheet.

References ipe::Attribute::index(), and ipe::Attribute::isSymbolic().

Referenced by ipe::ImlParser::parseStyle().

◆ findGradient()

const Gradient * StyleSheet::findGradient ( Attribute  sym) const

Find gradient in style sheet cascade.

References ipe::Attribute::index(), and ipe::Attribute::isSymbolic().

◆ addTiling()

void StyleSheet::addTiling ( Attribute  name,
const Tiling s 
)

Add tiling to this style sheet.

References ipe::Attribute::index(), and ipe::Attribute::isSymbolic().

Referenced by ipe::ImlParser::parseStyle().

◆ findTiling()

const Tiling * StyleSheet::findTiling ( Attribute  sym) const

Find tiling in style sheet cascade.

References ipe::Attribute::index(), and ipe::Attribute::isSymbolic().

◆ addEffect()

void StyleSheet::addEffect ( Attribute  name,
const Effect e 
)

◆ findEffect()

const Effect * StyleSheet::findEffect ( Attribute  sym) const

◆ add()

void StyleSheet::add ( Kind  kind,
Attribute  name,
Attribute  value 
)

Add an attribute.

Does nothing if name is not symbolic.

References ipe::Attribute::index(), and ipe::Attribute::isSymbolic().

Referenced by ipe::ImlParser::parseStyle().

◆ has()

bool StyleSheet::has ( Kind  kind,
Attribute  sym 
) const

Check whether symbolic attribute is defined.

This method also works for ESymbol, EGradient, ETiling, and EEffect.

Returns true if sym is not symbolic.

References ipe::EEffect, ipe::EGradient, ipe::ESymbol, ipe::ETiling, ipe::Attribute::index(), and ipe::Attribute::isSymbolic().

◆ find()

Attribute StyleSheet::find ( Kind  kind,
Attribute  sym 
) const

Find a symbolic attribute.

If sym is not symbolic, returns sym itself. If sym cannot be found, returns the "undefined" attribute. In all other cases, the returned attribute is guaranteed to be absolute.

References ipe::Attribute::index(), ipe::Attribute::isSymbolic(), and ipe::Attribute::UNDEFINED().

◆ remove()

void StyleSheet::remove ( Kind  kind,
Attribute  sym 
)

Removes definition for a symbolic attribute from this stylesheet.

This method also works for ESymbol, EGradient, ETiling, and EEffect. It is okay if the symbolic attribute is not defined in the stylesheet, nothing happens in this case.

References ipe::EEffect, ipe::EGradient, ipe::ESymbol, ipe::ETiling, and ipe::Attribute::index().

◆ saveAsXml()

◆ allNames()

void StyleSheet::allNames ( Kind  kind,
AttributeSeq seq 
) const

Return all symbolic names in the style sheet cascade.

Names are simply appended from top to bottom of the cascade. Names are inserted only once.

References ipe::EEffect, ipe::EGradient, ipe::ESymbol, and ipe::ETiling.

◆ isStandard()

bool ipe::StyleSheet::isStandard ( ) const
inline

Return whether this is the standard style sheet built into Ipe.

◆ preamble()

String ipe::StyleSheet::preamble ( ) const
inline

Return Latex preamble.

◆ setPreamble()

void ipe::StyleSheet::setPreamble ( const String str)
inline

Set LaTeX preamble.

Referenced by ipe::ImlParser::parseStyle().

◆ layout()

const Layout * StyleSheet::layout ( ) const

Return page layout (or 0 if none defined).

◆ setLayout()

void StyleSheet::setLayout ( const Layout margins)

Set page layout.

Referenced by ipe::ImlParser::parseStyle().

◆ textPadding()

const TextPadding * StyleSheet::textPadding ( ) const

Return text object padding (for bbox computation).

◆ setTextPadding()

void StyleSheet::setTextPadding ( const TextPadding pad)

Set padding for text object bbox computation.

Referenced by ipe::ImlParser::parseStyle().

◆ titleStyle()

const StyleSheet::TitleStyle * StyleSheet::titleStyle ( ) const

Return title style (or 0 if none defined).

◆ setTitleStyle()

void StyleSheet::setTitleStyle ( const TitleStyle ts)

Set style of page titles.

Referenced by ipe::ImlParser::parseStyle().

◆ pageNumberStyle()

const StyleSheet::PageNumberStyle * StyleSheet::pageNumberStyle ( ) const

Return page number style.

◆ setPageNumberStyle()

void StyleSheet::setPageNumberStyle ( const PageNumberStyle pns)

Set style of page numbering.

Referenced by ipe::ImlParser::parseStyle().

◆ setLineCap()

void StyleSheet::setLineCap ( TLineCap  s)

Set line cap.

Referenced by ipe::ImlParser::parseStyle().

◆ setLineJoin()

void StyleSheet::setLineJoin ( TLineJoin  s)

Set line join.

Referenced by ipe::ImlParser::parseStyle().

◆ setFillRule()

void StyleSheet::setFillRule ( TFillRule  s)

Set fill rule.

Referenced by ipe::ImlParser::parseStyle().

◆ lineCap()

TLineCap ipe::StyleSheet::lineCap ( ) const
inline

Return line cap.

◆ lineJoin()

TLineJoin ipe::StyleSheet::lineJoin ( ) const
inline

Return line join.

◆ fillRule()

TFillRule ipe::StyleSheet::fillRule ( ) const
inline

Return path fill rule.

◆ name()

String ipe::StyleSheet::name ( ) const
inline

Return name of style sheet.

◆ setName()

void ipe::StyleSheet::setName ( const String name)
inline

Set name of style sheet.

Referenced by ipe::ImlParser::parseStyle().


The documentation for this class was generated from the following files:
  • ipestyle.h
  • ipestdstyles.cpp
  • ipestyle.cpp

ipe-7.2.13/build/doc/classipe_1_1_a85_stream-members.html0000644000175000017500000001334413561570220022716 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::A85Stream Member List

This is the complete list of members for ipe::A85Stream, including all inherited members.

A85Stream(Stream &stream)ipe::A85Stream
close()ipe::A85Streamvirtual
operator<<(char ch)ipe::Streaminline
operator<<(const String &s)ipe::Streaminline
operator<<(const char *s)ipe::Streaminline
operator<<(int i)ipe::Stream
operator<<(double d)ipe::Stream
putChar(char ch)ipe::A85Streamvirtual
putCString(const char *s)ipe::Streamvirtual
putHexByte(char b)ipe::Stream
putRaw(const char *data, int size)ipe::Streamvirtual
putString(String s)ipe::Streamvirtual
putXmlString(String s)ipe::Stream
~Stream()ipe::Streamvirtual

ipe-7.2.13/build/doc/classipe_1_1_group-members.html0000644000175000017500000004451613561570220022107 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Group Member List

This is the complete list of members for ipe::Group, including all inherited members.

accept(Visitor &visitor) constipe::Groupvirtual
addToBBox(Rect &box, const Matrix &m, bool cp) constipe::Groupvirtual
asGroup()ipe::Groupvirtual
asGroup() constipe::Groupvirtual
asImage()ipe::Objectvirtual
asPath()ipe::Objectvirtual
asReference()ipe::Objectvirtual
asText()ipe::Objectvirtual
begin() constipe::Groupinline
checkStyle(const Cascade *sheet, AttributeSeq &seq) constipe::Groupvirtual
checkSymbol(Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq)ipe::Objectprotectedstatic
clip() constipe::Groupinline
clone() constipe::Groupvirtual
const_iterator typedefipe::Group
count() constipe::Groupinline
distance(const Vector &v, const Matrix &m, double bound) constipe::Groupvirtual
draw(Painter &painter) constipe::Groupvirtual
drawSimple(Painter &painter) constipe::Groupvirtual
EGroup enum valueipe::Object
EImage enum valueipe::Object
end() constipe::Groupinline
EPath enum valueipe::Object
EReference enum valueipe::Object
EText enum valueipe::Object
getAttribute(Property prop) const noexceptipe::Groupvirtual
Group()ipe::Groupexplicit
Group(const Group &rhs)ipe::Group
Group(const XmlAttributes &attr)ipe::Groupexplicit
iMatrixipe::Objectprotected
iPinnedipe::Objectprotected
iTransformationsipe::Objectprotected
matrix() constipe::Objectinline
Object()ipe::Objectexplicitprotected
Object(const AllAttributes &attr)ipe::Objectexplicitprotected
Object(const Object &rhs)ipe::Objectprotected
Object(const XmlAttributes &attr)ipe::Objectexplicitprotected
object(int i) constipe::Groupinline
operator=(const Group &rhs)ipe::Group
pinned() constipe::Groupvirtual
push_back(Object *)ipe::Group
saveAsXml(Stream &stream, String layer) constipe::Groupvirtual
saveAttributesAsXml(Stream &stream, String layer) constipe::Objectprotected
saveComponentsAsXml(Stream &stream) constipe::Group
setAttribute(Property prop, Attribute value)ipe::Groupvirtual
setClip(const Shape &clip)ipe::Group
setMatrix(const Matrix &matrix)ipe::Object
setPinned(TPinned pin)ipe::Object
setTransformations(TTransformations trans)ipe::Object
setUrl(String url)ipe::Group
snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Groupvirtual
snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Groupvirtual
snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Groupvirtual
transformations() constipe::Objectinline
Type enum nameipe::Object
type() constipe::Groupvirtual
url() constipe::Groupinline
~Group()ipe::Groupvirtual
~Object()=0ipe::Objectpure virtual

ipe-7.2.13/build/doc/classipe_1_1_matrix-members.html0000644000175000017500000001742413561570220022255 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Matrix Member List

This is the complete list of members for ipe::Matrix, including all inherited members.

aipe::Matrix
determinant() constipe::Matrixinline
inverse() constipe::Matrix
isIdentity() constipe::Matrixinline
linear() constipe::Matrixinline
Matrix()ipe::Matrixinline
Matrix(const Linear &linear)ipe::Matrixinline
Matrix(const Linear &linear, const Vector &t)ipe::Matrixinlineexplicit
Matrix(double m11, double m21, double m12, double m22, double t1, double t2)ipe::Matrixinlineexplicit
Matrix(const Vector &v)ipe::Matrixinlineexplicit
Matrix(String str)ipe::Matrixexplicit
operator*(const Vector &rhs) constipe::Matrixinline
operator*(const Bezier &rhs) constipe::Matrixinline
operator*(const Bezier &rhs) constipe::Matrixrelated
operator*(const Vector &rhs) constipe::Matrixrelated
operator*(const Matrix &lhs, const Matrix &rhs)ipe::Matrixrelated
operator*(const Matrix &lhs, const Arc &rhs)ipe::Matrixrelated
operator<<(Stream &stream, const Matrix &rhs)ipe::Matrixrelated
operator==(const Matrix &rhs) constipe::Matrixinline
translation() constipe::Matrixinline

ipe-7.2.13/build/doc/classipe_1_1_image-members.html0000644000175000017500000004034513561570220022031 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Image Member List

This is the complete list of members for ipe::Image, including all inherited members.

accept(Visitor &visitor) const overrideipe::Imagevirtual
addToBBox(Rect &box, const Matrix &m, bool) const overrideipe::Imagevirtual
asGroup()ipe::Objectvirtual
asGroup() constipe::Objectvirtual
asImage() overrideipe::Imagevirtual
asPath()ipe::Objectvirtual
asReference()ipe::Objectvirtual
asText()ipe::Objectvirtual
bitmap() constipe::Imageinline
checkStyle(const Cascade *sheet, AttributeSeq &seq) constipe::Objectvirtual
checkSymbol(Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq)ipe::Objectprotectedstatic
clone() const overrideipe::Imagevirtual
distance(const Vector &v, const Matrix &m, double bound) const overrideipe::Imagevirtual
draw(Painter &painter) const overrideipe::Imagevirtual
drawSimple(Painter &painter) const overrideipe::Imagevirtual
EGroup enum valueipe::Object
EImage enum valueipe::Object
EPath enum valueipe::Object
EReference enum valueipe::Object
EText enum valueipe::Object
getAttribute(Property prop) const noexcept overrideipe::Imagevirtual
Image(const Rect &rect, Bitmap bitmap)ipe::Imageexplicit
Image(const XmlAttributes &attr, String data)ipe::Imageexplicit
Image(const XmlAttributes &attr, Bitmap bitmap)ipe::Imageexplicit
iMatrixipe::Objectprotected
iPinnedipe::Objectprotected
iTransformationsipe::Objectprotected
matrix() constipe::Objectinline
Object()ipe::Objectexplicitprotected
Object(const AllAttributes &attr)ipe::Objectexplicitprotected
Object(const Object &rhs)ipe::Objectprotected
Object(const XmlAttributes &attr)ipe::Objectexplicitprotected
opacity() constipe::Imageinline
pinned() constipe::Objectvirtual
rect() constipe::Imageinline
saveAsXml(Stream &stream, String layer) const overrideipe::Imagevirtual
saveAttributesAsXml(Stream &stream, String layer) constipe::Objectprotected
setAttribute(Property prop, Attribute value) overrideipe::Imagevirtual
setMatrix(const Matrix &matrix)ipe::Object
setOpacity(Attribute opaq)ipe::Image
setPinned(TPinned pin)ipe::Object
setTransformations(TTransformations trans)ipe::Object
snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Objectvirtual
snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const overrideipe::Imagevirtual
snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Objectvirtual
transformations() constipe::Objectinline
type() const overrideipe::Imagevirtual
Type enum nameipe::Object
~Object()=0ipe::Objectpure virtual

ipe-7.2.13/build/doc/functions_func.html0000644000175000017500000002446613561570220020025 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- a -


ipe-7.2.13/build/doc/functions_vars_t.html0000644000175000017500000000424213561570220020356 0ustar otfriedotfried Ipelib: Class Members - Variables
Ipelib

ipe-7.2.13/build/doc/luageo.html0000644000175000017500000002077313561570220016253 0ustar otfriedotfried Ipelib: Lua bindings for geometric objects
Ipelib
Lua bindings for geometric objects

All Ipelib objects have constructors of the form:

 v = ipe.Vector()
 m = ipe.Matrix()
 m = ipe.Translation()  -- another Matrix constructor
 m = ipe.Rotation()     -- yet another Matrix constructor
 r = ipe.Rect()
 l = ipe.Line()
 l = ipe.LineThrough()  -- another Line constructor
 l = ipe.Bisector()     -- yet another Line constructor
 s = ipe.Segment()
 b = ipe.Bezier()
 a = ipe.Arc()

Note that ipe::Angle and ipe::Linear are not bound in Lua. Use numbers and ipe.Matrix instead. A useful method for angles is:

beta = ipe.normalizeAngle(alpha, lowLimit)

Vector

ipe.Vector binds ipe::Vector. There are the following methods:

v = ipe.Vector()         -- zero vector
v = ipe.Vector(x, y)
v = ipe.Direction(alpha) -- unit vector in this direction 
a = v.x                  -- read only access to x and y coordinates
b = v.y

v:len() -- returns norm of vector
v:sqLen() -- returns square of norm
v:normalized() -- returns this vector normalized
v:orthogonal() -- returns this vector rotated left by 90 degrees
v:factorize(u) -- factors v = lambda u + x, where x orth. to u, u is unit
v:angle()     -- return direction 
v == w        -- vector equality
v ~= w
-v            -- unary minus
v + w         -- vector addition
v - w         -- vector difference
5 * v         -- multiplication with a scalar
v * 5         -- multiplication with a scalar
v ^ w         -- dot product

Matrix

ipe.Matrix binds ipe::Matrix. It has the following methods:

m = ipe.Matrix()                        -- identity matrix
m = ipe.Matrix(a1, a2, a3, a4)          -- linear transformation
m = ipe.Matrix(a1, a2, a3, a4, a5, a6)  -- affine transformation
m = ipe.Matrix( { a1, a2, a3, a4, a5, a6 } ) -- same from table
m = ipe.Rotation(alpha)                 -- rotation matrix
m = ipe.Translation(v)                  -- v is a vector
m = ipe.Translation(x, y)

m1 == m2          -- matrix equality
m1 * m2           -- matrix multiplication
m * v             -- matrix * vector
m * arc           -- matrix * arc

m:elements()      -- returns six-element array with elements

m:isIdentity()
m:isSingular()
m:inverse()
m:translation()   -- return translation component
m:linear()        -- returns matrix without the translation component

Rect

ipe.Rect binds ipe::Rect. This is the only mutable geometric object - take care not to be surprised when ipe.Rect objects are shared.

It has the following methods:

r = ipe.Rect()    -- empty
r:isEmpty()
r:topRight()
r:bottomLeft()
r:topLeft()
r:bottomRight()
r:left()
r:right()
r:bottom()
r:top()
r:width()
r:height()
r:add(v)          -- extend to cover vector v
r1:add(r2)        -- extend to cover rectangle r2
r1:clipTo(r2)     -- clip r1 to lie inside r2
r:contains(v)     
r1:contains(r2)
r1:intersects(r2)

Line

ipe.Line binds ipe::Line. It has the following methods:

l = ipe.Line(p, dir)      -- dir must be unit vector
l = ipe.LineThrough(p, q)
l = ipe.Bisector(p, q)

-- l:side() returns +1 if v lies to the left side of the line, 
-- 0 if on line, -1 if on the right side
l:side(v)                 
l:point()                 -- starting point of line
l:dir()                   -- unit direction vector
l:normal()                -- unit normal vector pointing to the left side
l:distance(v)             -- returns distance from point to line
l1:intersects(l2)         -- returns intersection point or nil
l:project(p)              -- projection of point on line

Segment

ipe.Segment binds ipe::Segment. It has the following methods:

s = ipe.Segment(p, q)   
p, q = s:endpoints()      -- returns both endpoints
s:line()                  -- returns an ipe.Line
s:project(p)              -- returns projection or nil
s:distance(p)
s:intersects(l)           -- return intersection point or nil
s1:intersects(s2)

Bezier

ipe.Bezier binds ipe::Bezier. It has the following methods:

b = ipe.Bezier(v1, v2, v3, v4)  
b:point(t)                -- point at value t
v1, v2, v3, v4 = b:controlpoints()  -- returns all four control points
b:bbox()
t, p = b:snap(pos)

-- intersections: 
-- x is line, segment, or bezier
-- returns table of intersection points
b:intersect(x)

Arc

ipe.Arc binds ipe::Arc. It has the following methods:

a = ipe.Arc(m)            -- ellipse defined by ipe.Matrix m
a = ipe.Arc(m, p, q)      -- arc from p to q
a = ipe.Arc(m, alpha, beta)

a:endpoints()             -- returns two endpoints
a:angles()                -- returns two angles
a:bbox()
a:matrix()
a:isEllipse() 
alpha, p = a:snap(pos)

-- intersections: 
-- x is line, segment, arc, or bezier
-- returns table of intersection points
a:intersect(x)

ipe-7.2.13/build/doc/classipe_1_1_string.html0000644000175000017500000020305513561570220020624 0ustar otfriedotfried Ipelib: ipe::String Class Reference
Ipelib

#include <ipebase.h>

Public Member Functions

 String () noexcept
 
 String (const char *str) noexcept
 
 String (const char *str, int len) noexcept
 
 String (const String &rhs) noexcept
 
 String (const String &rhs, int index, int len) noexcept
 
Stringoperator= (const String &rhs) noexcept
 
 ~String () noexcept
 
char operator[] (int i) const noexcept
 
bool empty () const noexcept
 
const char * data () const noexcept
 
int size () const noexcept
 
void operator+= (const String &rhs) noexcept
 
void operator+= (const char *rhs) noexcept
 
void operator+= (char ch) noexcept
 
String substr (int i, int len=-1) const noexcept
 
String left (int i) const noexcept
 
String right (int i) const noexcept
 
bool operator!= (const String &rhs) const noexcept
 
bool operator!= (const char *rhs) const noexcept
 
int find (char ch) const noexcept
 
int rfind (char ch) const noexcept
 
int find (const char *rhs) const noexcept
 
void erase () noexcept
 
void append (const String &rhs) noexcept
 
void append (const char *rhs) noexcept
 
void append (char ch) noexcept
 
bool hasPrefix (const char *rhs) const noexcept
 
bool operator== (const String &rhs) const noexcept
 
bool operator== (const char *rhs) const noexcept
 
bool operator< (const String &rhs) const noexcept
 
String operator+ (const String &rhs) const noexcept
 
int unicode (int &index) const noexcept
 
String getLine (int &index) const noexcept
 
const char * z () const noexcept
 

Static Public Member Functions

static String withData (char *data, int len=0) noexcept
 

Detailed Description

Strings and buffers.

String is is an implicitly shared byte string. It is designed to be efficient for strings of arbitrary length, and supposed to be passed by value (the size of String is a single pointer). Sharing is implicit—the string creates its own representation as soon as it is modified.

String can be used for binary data. For text, it is usually assumed that the string is UTF-8 encoded, but only the unicode member function actually requires this. In particular, all indices into the string are byte indices, not Unicode character indices.

Constructor & Destructor Documentation

◆ String() [1/5]

String::String ( )
noexcept

Construct an empty string.

Referenced by right(), and ipe::Platform::runLatex().

◆ String() [2/5]

String::String ( const char *  str)
noexcept

Construct a string by making copy of str.

◆ String() [3/5]

String::String ( const char *  str,
int  len 
)
noexcept

Construct string by making copy of str with given len.

◆ String() [4/5]

String::String ( const String rhs)
noexcept

Copy constructor. This only copies the reference and takes constant time.

◆ String() [5/5]

String::String ( const String rhs,
int  index,
int  len 
)
noexcept

Construct a substring.

index must be >= 0. len can be negative or too large to return entire string.

◆ ~String()

String::~String ( )
noexcept

Destruct string if reference count has reached zero.

Member Function Documentation

◆ operator=()

String & String::operator= ( const String rhs)
noexcept

Assignment takes constant time.

◆ withData()

String String::withData ( char *  data,
int  len = 0 
)
staticnoexcept

Construct string by taking ownership of given data.

References data().

◆ operator[]()

char ipe::String::operator[] ( int  i) const
inlinenoexcept

Return character at index i.

◆ empty()

◆ data()

◆ size()

◆ operator+=() [1/3]

void ipe::String::operator+= ( const String rhs)
inlinenoexcept

Operator syntax for append.

◆ operator+=() [2/3]

void ipe::String::operator+= ( const char *  rhs)
inlinenoexcept

Operator syntax for append.

◆ operator+=() [3/3]

void ipe::String::operator+= ( char  ch)
inlinenoexcept

Operator syntax for append.

◆ substr()

◆ left()

◆ right()

String String::right ( int  i) const
noexcept

Create substring at the right.

Returns the entire string if i is larger than its length.

References size(), and String().

Referenced by ipe::Bitmap::Bitmap(), ipe::Document::formatFromFilename(), and ipe::Platform::latexDirectory().

◆ operator!=() [1/2]

bool ipe::String::operator!= ( const String rhs) const
inlinenoexcept

Operator !=.

◆ operator!=() [2/2]

bool ipe::String::operator!= ( const char *  rhs) const
inlinenoexcept

Operator !=.

◆ find() [1/2]

int String::find ( char  ch) const
noexcept

Return index of first occurrence of ch.

Return -1 if character does not appear.

References size().

Referenced by ipe::PdfWriter::createTrailer(), ipe::Painter::dashStyle(), ipe::CairoPainter::doDrawText(), ipe::Reference::flagsFromName(), ipe::Document::runLatex(), and ipe::StyleSheet::saveAsXml().

◆ rfind()

int String::rfind ( char  ch) const
noexcept

Return index of last occurrence of ch.

Return -1 if character does not appear.

References size().

Referenced by ipe::Reference::flagsFromName(), and ipe::Platform::ipeDrive().

◆ find() [2/2]

int String::find ( const char *  rhs) const
noexcept

Return index of first occurrence of rhs.

Return -1 if not substring is not present.

References size().

◆ erase()

void String::erase ( )
noexcept

Make string empty.

◆ append() [1/3]

void String::append ( const String rhs)
noexcept

Append rhs to this string.

Referenced by operator+(), and ipe::Platform::readFile().

◆ append() [2/3]

void String::append ( const char *  rhs)
noexcept

Append rhs to this string.

◆ append() [3/3]

void String::append ( char  ch)
noexcept

Append ch to this string.

◆ hasPrefix()

bool String::hasPrefix ( const char *  rhs) const
noexcept

Does string start with this prefix? (bytewise comparison)

References size().

◆ operator==() [1/2]

bool String::operator== ( const String rhs) const
noexcept

Equality operator (bytewise comparison).

References size().

◆ operator==() [2/2]

bool String::operator== ( const char *  rhs) const
noexcept

Equality operator (bytewise comparison).

References size().

◆ operator<()

bool String::operator< ( const String rhs) const
noexcept

Inequality operator (bytewise comparison).

References size().

◆ operator+()

String String::operator+ ( const String rhs) const
noexcept

Concatenate this string with rhs.

References append().

◆ unicode()

int String::unicode ( int &  index) const
noexcept

Return Unicode value from UTF-8 string.

The index is incremented to the next UTF-8 character. This returns 0xfffd if there is any problem in parsing UTF-8.

References ipe::Fixed::fromInternal(), and ipe::Fixed::mult().

Referenced by ipe::PdfWriter::createXmlStream().

◆ getLine()

String String::getLine ( int &  index) const
noexcept

Return line starting at position index. Index is updated to point to next line.

References size(), and substr().

Referenced by ipe::Platform::libVersion().

◆ z()


The documentation for this class was generated from the following files:
  • ipebase.h
  • ipebase.cpp

ipe-7.2.13/build/doc/classipe_1_1_pdf_null.html0000644000175000017500000003050313561570220021115 0ustar otfriedotfried Ipelib: ipe::PdfNull Class Reference
Ipelib
ipe::PdfNull Class Reference

#include <ipepdfparser.h>

Inherits ipe::PdfObj.

Public Member Functions

 PdfNull ()
 
virtual const PdfNullnull () const noexcept
 
virtual void write (Stream &stream, const PdfRenumber *renumber, bool inflate) const noexcept
 
- Public Member Functions inherited from ipe::PdfObj
virtual ~PdfObj ()=0
 
virtual const PdfBoolboolean () const noexcept
 
virtual const PdfNumbernumber () const noexcept
 
virtual const PdfStringstring () const noexcept
 
virtual const PdfNamename () const noexcept
 
virtual const PdfRefref () const noexcept
 
virtual const PdfArrayarray () const noexcept
 
virtual const PdfDictdict () const noexcept
 
String repr () const noexcept
 

Detailed Description

The PDF null object.

Constructor & Destructor Documentation

◆ PdfNull()

ipe::PdfNull::PdfNull ( )
inlineexplicit

Member Function Documentation

◆ null()

const PdfNull * PdfNull::null ( ) const
virtualnoexcept

Return this object as PDF null object.

Reimplemented from ipe::PdfObj.

◆ write()

void PdfNull::write ( Stream stream,
const PdfRenumber renumber,
bool  inflate 
) const
virtualnoexcept

Implements ipe::PdfObj.


The documentation for this class was generated from the following files:
  • ipepdfparser.h
  • ipepdfparser.cpp

ipe-7.2.13/build/doc/manual_29.html0000644000175000017500000001546413561570220016567 0ustar otfriedotfried Ipe Manual -- 7.1 Presentation stylesheets
7.2 Views7 Presentations7.1 Presentation stylesheets

7.1 Presentation stylesheets

A presentation must use a dedicated stylesheet. Presentations must use much larger fonts than what is normal for a figure. Don't try to make use of the "LARGE" and "huge" textsizes, but use a stylesheet that properly defines "normal" to be a large textsize.

Ipe comes with a style sheet presentation.isy that can be used for presentations. To create a new presentation, you can simply say:

 
  ipe -sheet presentation
Note that presentation.isy is meant to be used instead of basic.isy (not in addition to it).

This presentation stylesheet enlarges all standard sizes by a factor 2.8. Note the use of the <textstretch> element to magnify text:

<textstretch name="normal" value="2.8"/>
<textstretch name="large" value="2.8"/>
The text size you choose from the Ipe user interface ("large", for instance) is in fact used for two symbolic attributes, namely textsize (where large maps to \large) and textstretch (where it maps to no stretch in the standard style sheet). By setting the text stretch, you can magnify fonts.

In addition, the <layout> element in this stylesheet redefines the paper size to be of the correct proportions for a projector, and defines a smaller area of the paper as the frame. The frame is the area that should be used for the contents. The Insert text box function, for instance, creates text objects that fill exactly the width of the frame.

The <titlestyle> element defines the style of the page title outside the frame. You can set the title for each page using the Edit title & sections function in the Page menu.

The LaTeX-preamble defined in the <preamble> element redefines the standard font shape to cmss (Computer Modern Sans Serif). Many people find sans-serif fonts easier to read on a screen. In addition, it redefines the list environments to use less spacing, and the text styles to not justify paragraphs (the <textstyle> elements).

If you wish to use the page transition effects of Acrobat Reader, you can define the effects in the stylesheet (using <effect> elements), and set them using Edit effect in the View menu.

If you want to number the pages of the presentation, you'll need to use the <pagenumberstyle> element. It defines color, size, position, and alignment of the page number, and provides a template for the page number text. The template can use the following Latex counters:

  • ipePage for the current page number,
  • ipeView for the current view number,
  • ipePages for the total number of pages,
  • ipeViews for the number of views of the current page,
and the special macro \ipeNumber{x}{y} that evaluates to x when the page has only one view, and to y if there is more than one view.

If the template is empty, this has the same effect as the following definition (this is also the default definition):

\ipeNumber{\arabic{ipePage}}{\arabic{ipePage} - \arabic{ipeView}}

The following example definition indicates the views of a single page with letters A, B, C, …:

<pagenumberstyle pos="300 100" size="Huge" color="navy" 
  halign="center">\ipeNumber{\arabic{ipePage}}{\arabic{ipePage} 
\Alph{ipeView}}</pagenumberstyle>

The following definition uses roman numerals for the pages and does not indicate different views at all:

<pagenumberstyle pos="580 20" size="Huge" color="purple" 
  halign="right">\roman{ipePage}</pagenumberstyle>

And this shows both the current page and the total number of pages:

<pagenumberstyle pos="20 820" size="Huge" color="0.5 0 0" 
  valign="top">\arabic{ipePage}/\arabic{ipePages}</pagenumberstyle>
ipe-7.2.13/build/doc/functions_g.html0000644000175000017500000001436513561570220017315 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- g -


ipe-7.2.13/build/doc/structipe_1_1_text_1_1_x_form.html0000644000175000017500000002330313561570220022527 0ustar otfriedotfried Ipelib: ipe::Text::XForm Struct Reference
Ipelib
ipe::Text::XForm Struct Reference

#include <ipetext.h>

Public Attributes

int iRefCount
 
Rect iBBox
 
int iDepth
 
float iStretch
 
String iName
 
Vector iTranslation
 

Member Data Documentation

◆ iRefCount

int ipe::Text::XForm::iRefCount

◆ iBBox

Rect ipe::Text::XForm::iBBox

◆ iDepth

◆ iStretch

◆ iName

◆ iTranslation


The documentation for this struct was generated from the following file:
  • ipetext.h

ipe-7.2.13/build/doc/manual_51.html0000644000175000017500000000561613561570220016560 0ustar otfriedotfried Ipe Manual -- 11 The command line programs ipe-7.2.13/build/doc/classipe_1_1_bitmap.html0000644000175000017500000016220413561570220020572 0ustar otfriedotfried Ipelib: ipe::Bitmap Class Reference
Ipelib

#include <ipebitmap.h>

Public Types

enum  Flags {
  ERGB = 0x01, EAlpha = 0x02, EDCT = 0x04, EInflate = 0x08,
  ENative = 0x10
}
 

Public Member Functions

 Bitmap ()
 
 Bitmap (int width, int height, uint32_t flags, Buffer data)
 
 Bitmap (const XmlAttributes &attr, String data)
 
 Bitmap (const XmlAttributes &attr, Buffer data, Buffer smask)
 
 Bitmap (const Bitmap &rhs)
 
 ~Bitmap ()
 
Bitmapoperator= (const Bitmap &rhs)
 
void saveAsXml (Stream &stream, int id, int pdfObjNum=-1) const
 
bool isNull () const
 
bool equal (Bitmap rhs) const
 
int width () const
 
int height () const
 
bool isJpeg () const
 
bool isGray () const
 
bool hasAlpha () const
 
int colorKey () const
 
Buffer pixelData ()
 
int objNum () const
 
void setObjNum (int objNum) const
 
std::pair< Buffer, Bufferembed () const
 
bool operator== (const Bitmap &rhs) const
 
bool operator!= (const Bitmap &rhs) const
 
bool operator< (const Bitmap &rhs) const
 
void savePixels (const char *fname)
 

Static Public Member Functions

static const char * readJpegInfo (FILE *file, int &width, int &height, Vector &dotsPerInch, uint32_t &flags)
 
static Bitmap readJpeg (const char *fname, Vector &dotsPerInch, const char *&errmsg)
 
static Bitmap readPNG (const char *fname, Vector &dotsPerInch, const char *&errmsg)
 

Detailed Description

A bitmap.

Bitmaps are explicitely shared using reference-counting. Copying is cheap, so Bitmap objects are meant to be passed by value.

The bitmap provides a slot for short-term storage of an "object number". The PDF embedder, for instance, sets it to the PDF object number when embedding the bitmap, and can reuse it when "drawing" the bitmap.

Member Enumeration Documentation

◆ Flags

Enumerator
ERGB 
EAlpha 
EDCT 
EInflate 
ENative 

Constructor & Destructor Documentation

◆ Bitmap() [1/5]

Bitmap::Bitmap ( )

Default constructor constructs null bitmap.

Referenced by readJpeg().

◆ Bitmap() [2/5]

Bitmap::Bitmap ( int  width,
int  height,
uint32_t  flags,
Buffer  data 
)

Create a new image from given image data.

If you already have data in native-endian ARGB32 without premultiplication, pass it with flag ENative. Otherwise pass a byte stream and set ERGB and EAlpha correctly: EAlpha: each pixel starts with one byte of alpha channel, ERGB: each pixel has three bytes of R, G, B, in this order, otherwise each pixel has one byte of gray value.

References colorKey(), ipe::Buffer::data(), EAlpha, EDCT, EInflate, ENative, ERGB, hasAlpha(), height(), isGray(), isJpeg(), ipe::Buffer::size(), and width().

◆ Bitmap() [3/5]

Bitmap::Bitmap ( const XmlAttributes attr,
String  data 
)

◆ Bitmap() [4/5]

Bitmap::Bitmap ( const XmlAttributes attr,
Buffer  data,
Buffer  smask 
)

◆ Bitmap() [5/5]

Bitmap::Bitmap ( const Bitmap rhs)

Copy constructor.

Since Bitmaps are reference counted, this is very fast.

◆ ~Bitmap()

Bitmap::~Bitmap ( )

Destructor.

Member Function Documentation

◆ operator=()

Bitmap & Bitmap::operator= ( const Bitmap rhs)

Assignment operator (takes care of reference counting).

Very fast.

◆ saveAsXml()

void Bitmap::saveAsXml ( Stream stream,
int  id,
int  pdfObjNum = -1 
) const

◆ isNull()

bool ipe::Bitmap::isNull ( ) const
inline

Is this a null bitmap?

Referenced by ipe::ImlParser::parseObject().

◆ equal()

bool Bitmap::equal ( Bitmap  rhs) const

◆ width()

int ipe::Bitmap::width ( ) const
inline

◆ height()

int ipe::Bitmap::height ( ) const
inline

◆ isJpeg()

bool ipe::Bitmap::isJpeg ( ) const
inline

Is this bitmap a JPEG photo?

References EDCT.

Referenced by Bitmap(), embed(), pixelData(), saveAsXml(), savePixels(), and ipe::PdfWriter::~PdfWriter().

◆ isGray()

bool ipe::Bitmap::isGray ( ) const
inline

Is the bitmap grayscale?

References ERGB.

Referenced by Bitmap(), embed(), saveAsXml(), and ipe::PdfWriter::~PdfWriter().

◆ hasAlpha()

bool ipe::Bitmap::hasAlpha ( ) const
inline

Does the bitmap have transparency?

Bitmaps with color key will return false here.

References EAlpha.

Referenced by Bitmap(), embed(), pixelData(), saveAsXml(), and ipe::PdfWriter::~PdfWriter().

◆ colorKey()

int ipe::Bitmap::colorKey ( ) const
inline

Return the color key or -1 if none.

Referenced by Bitmap(), pixelData(), saveAsXml(), and ipe::PdfWriter::~PdfWriter().

◆ pixelData()

Buffer Bitmap::pixelData ( )

Return pixels for rendering.

Returns empty buffer if it cannot decode the bitmap information. Otherwise, returns a buffer of size width() * height() uint32_t's. The data is in cairo ARGB32 format, that is native-endian uint32_t's with premultiplied alpha.

References colorKey(), hasAlpha(), height(), isJpeg(), and width().

Referenced by ipe::CairoPainter::doDrawBitmap().

◆ objNum()

int ipe::Bitmap::objNum ( ) const
inline

◆ setObjNum()

void ipe::Bitmap::setObjNum ( int  objNum) const
inline

Set object number of the bitmap.

References objNum().

Referenced by ipe::Page::saveAsIpePage(), ipe::Page::saveSelection(), and ipe::PdfWriter::~PdfWriter().

◆ embed()

std::pair< Buffer, Buffer > Bitmap::embed ( ) const

Create the data to be embedded in an XML or PDF file.

For Jpeg images, this is simply the bitmap data. For other images, rgb/grayscale data and alpha channel are split and deflated separately.

References ipe::Buffer::data(), ipe::DeflateStream::deflate(), hasAlpha(), height(), isGray(), isJpeg(), ipe::Buffer::size(), and width().

Referenced by saveAsXml(), and ipe::PdfWriter::~PdfWriter().

◆ operator==()

bool ipe::Bitmap::operator== ( const Bitmap rhs) const
inline

Two bitmaps are equal if they share the same data.

◆ operator!=()

bool ipe::Bitmap::operator!= ( const Bitmap rhs) const
inline

Two bitmaps are equal if they share the same data.

◆ operator<()

bool ipe::Bitmap::operator< ( const Bitmap rhs) const
inline

Less operator, to be able to sort bitmaps.

The checksum is used, when it is equal, the shared address. This guarantees that bitmaps that are == (share their implementation) are next to each other, and blocks of them are next to blocks that are identical in contents.

◆ readJpegInfo()

const char * Bitmap::readJpegInfo ( FILE *  file,
int &  width,
int &  height,
Vector dotsPerInch,
uint32_t &  flags 
)
static

Read information about JPEG image from file.

Returns NULL on success, an error message otherwise. Sets flags to EDCT and possibly ERGB.

References EDCT, and ERGB.

Referenced by readJpeg().

◆ readJpeg()

Bitmap Bitmap::readJpeg ( const char *  fname,
Vector dotsPerInch,
const char *&  errmsg 
)
static

Read JPEG image from file.

Returns the image as a DCT-encoded Bitmap. Sets dotsPerInch if the image file contains a resolution, otherwise sets it to (0,0). If reading the file fails, returns a null Bitmap, and sets the error message errmsg.

References Bitmap(), ipe::String::data(), ipe::Platform::fopen(), height(), ipe::Platform::readFile(), readJpegInfo(), ipe::String::size(), and width().

◆ readPNG()

Bitmap Bitmap::readPNG ( const char *  fname,
Vector dotsPerInch,
const char *&  errmsg 
)
static

Read PNG image from file.

Returns the image as a Bitmap. It will be compressed if deflate is set. Sets dotsPerInch if the image file contains a resolution, otherwise sets it to (0,0). If reading the file fails, returns a null Bitmap, and sets the error message errmsg.

References ipe::Buffer::data(), EAlpha, ERGB, and ipe::Platform::fopen().

◆ savePixels()

void Bitmap::savePixels ( const char *  fname)

The documentation for this class was generated from the following files:
  • ipebitmap.h
  • ipebitmap.cpp
  • ipebitmap_unix.cpp
  • ipebitmap_win.cpp

ipe-7.2.13/build/doc/classipe_1_1_face.html0000644000175000017500000003515013561570220020213 0ustar otfriedotfried Ipelib: ipe::Face Class Reference
Ipelib

#include <ipefonts.h>

Public Member Functions

 Face (const PdfDict *d, const PdfResourceBase *resources) noexcept
 
 ~Face () noexcept
 
bool matches (const PdfDict *d) const noexcept
 
FontType type () const noexcept
 
int width (int ch) const noexcept
 
int glyphIndex (int ch) noexcept
 
cairo_font_face_t * cairoFont () noexcept
 

Detailed Description

A typeface (aka font), actually loaded (from a font file or PDF file).

Constructor & Destructor Documentation

◆ Face()

◆ ~Face()

Face::~Face ( )
noexcept

Member Function Documentation

◆ matches()

bool ipe::Face::matches ( const PdfDict d) const
inlinenoexcept

◆ type()

FontType ipe::Face::type ( ) const
inlinenoexcept

◆ width()

int Face::width ( int  ch) const
noexcept

References ipe::size().

◆ glyphIndex()

◆ cairoFont()

cairo_font_face_t* ipe::Face::cairoFont ( )
inlinenoexcept

The documentation for this class was generated from the following files:
  • ipefonts.h
  • ipefonts.cpp

ipe-7.2.13/build/doc/manual_53.html0000644000175000017500000001035013561570220016551 0ustar otfriedotfried Ipe Manual -- 11.2 Ipetoipe: converting Ipe file formats
11.3 Iperender: exporting to a bitmap, EPS, or SVG11 The command line programs11.1 Ipe11.2 Ipetoipe: converting Ipe file formats

11.2 Ipetoipe: converting Ipe file formats

The auxiliary program ipetoipe converts between the different Ipe file formats:

  ipetoipe ( -xml | -pdf ) { <options> } infile [ outfile ]
The first argument determines the format of the output file. If no output filename is provided, Ipe will try to guess it by appending one of the extensions "ipe" or "pdf" to the input file's basename.

For example, the command line syntax

  ipetoipe -pdf figure1.ipe
converts figure1.ipe to figure1.pdf.

Ipetoipe understands the following options:

-export
No Ipe markup is included in the resulting output file. Ipe will not be able to open a file created that way, so make sure you keep your original!
-markedview
(PDF only)
Only the marked views of marked Ipe pages will be created in PDF format. If all views of a marked page are unmarked, the last view is exported. This is convenient to make handouts for slides.
-pages from-to
(PDF only)
Restrict exporting to PDF to this page range. This implies the -export option.
-view page-view
Only export this single view from the document. This implies the -export option.
-runlatex
Run Latex even for XML output. This has the effect of including the dimensions of each text object in the XML file.
-nozip
Do not compress streams in PDF output.
ipe-7.2.13/build/doc/classipe_1_1_a85_stream.html0000644000175000017500000003102513561570220021262 0ustar otfriedotfried Ipelib: ipe::A85Stream Class Reference
Ipelib

#include <ipeutils.h>

Inherits ipe::Stream.

Public Member Functions

 A85Stream (Stream &stream)
 
virtual void putChar (char ch)
 
virtual void close ()
 
- Public Member Functions inherited from ipe::Stream
virtual ~Stream ()
 
virtual void putString (String s)
 
virtual void putCString (const char *s)
 
virtual void putRaw (const char *data, int size)
 
Streamoperator<< (char ch)
 
Streamoperator<< (const String &s)
 
Streamoperator<< (const char *s)
 
Streamoperator<< (int i)
 
Streamoperator<< (double d)
 
void putHexByte (char b)
 
void putXmlString (String s)
 

Detailed Description

Filter stream adding ASCII85 encoding.

Constructor & Destructor Documentation

◆ A85Stream()

A85Stream::A85Stream ( Stream stream)

Member Function Documentation

◆ putChar()

void A85Stream::putChar ( char  ch)
virtual

Output character.

Implements ipe::Stream.

References ipe::Stream::putChar(), and ipe::Stream::putCString().

◆ close()

void A85Stream::close ( )
virtual

Close the stream. No more writing allowed!

Reimplemented from ipe::Stream.

References ipe::Stream::close(), and ipe::Stream::putCString().


The documentation for this class was generated from the following files:
  • ipeutils.h
  • ipeutils.cpp

ipe-7.2.13/build/doc/group__doc.html0000644000175000017500000000634513561570220017116 0ustar otfriedotfried Ipelib: Ipe Document
Ipelib
Ipe Document

Classes

class  ipe::Document
 
class  ipe::Page
 
class  ipe::StyleSheet
 
class  ipe::Cascade
 

Detailed Description

The classes managing an Ipe document.

The main class, Document, represents an entire Ipe document, and allows you to load, save, access, and modify such a document.

Other classes represent pages, layers, and views of a document. Another important class is the StyleSheet, which maps symbolic attributes to absolute values.


ipe-7.2.13/build/doc/classipe_1_1_tell_stream.html0000644000175000017500000002562613561570220021637 0ustar otfriedotfried Ipelib: ipe::TellStream Class Reference
Ipelib
ipe::TellStream Class Referenceabstract

#include <ipebase.h>

Inherits ipe::Stream.

Inherited by ipe::FileStream, and ipe::StringStream.

Public Member Functions

virtual long tell () const =0
 
- Public Member Functions inherited from ipe::Stream
virtual ~Stream ()
 
virtual void putChar (char ch)=0
 
virtual void close ()
 
virtual void putString (String s)
 
virtual void putCString (const char *s)
 
virtual void putRaw (const char *data, int size)
 
Streamoperator<< (char ch)
 
Streamoperator<< (const String &s)
 
Streamoperator<< (const char *s)
 
Streamoperator<< (int i)
 
Streamoperator<< (double d)
 
void putHexByte (char b)
 
void putXmlString (String s)
 

Detailed Description

Adds position feedback to IpeStream.

Member Function Documentation

◆ tell()

virtual long ipe::TellStream::tell ( ) const
pure virtual

Implemented in ipe::FileStream, and ipe::StringStream.


The documentation for this class was generated from the following file:
  • ipebase.h

ipe-7.2.13/build/doc/classipe_1_1_pdf_view_base.html0000644000175000017500000016107513561570220022120 0ustar otfriedotfried Ipelib: ipe::PdfViewBase Class Reference
Ipelib

#include <ipepdfview.h>

Inherited by ipe::PdfView, ipe::PdfView, and PdfView.

Public Member Functions

virtual ~PdfViewBase ()
 
void setPdf (const PdfFile *pdf)
 
void setPage (const PdfDict *page, const Rect &paper)
 
Vector pan () const
 
double zoom () const
 
Vector center () const
 
int viewWidth () const
 
int viewHeight () const
 
Vector devToUser (const Vector &arg) const
 
Vector userToDev (const Vector &arg) const
 
void setPan (const Vector &v)
 
void setZoom (double zoom)
 
Matrix canvasTfm () const
 
void updatePdf ()
 
virtual void invalidate (int x, int y, int w, int h)=0
 
virtual void invalidate ()=0
 

Protected Member Functions

 PdfViewBase ()
 
void drawPaper (cairo_t *cc)
 
void refreshSurface ()
 

Protected Attributes

double iWidth
 
double iHeight
 
double iBWidth
 
double iBHeight
 
Vector iPan
 
double iZoom
 
bool iRepaint
 
cairo_surface_t * iSurface
 
std::unique_ptr< CascadeiCascade
 
const PdfDictiPage
 
Rect iPaperBox
 
const PdfDictiStream
 
const PdfFileiPdf
 
std::unique_ptr< PdfFileResourcesiResources
 
std::unique_ptr< FontsiFonts
 

Detailed Description

A widget (control) that displays a PDF document.

Constructor & Destructor Documentation

◆ ~PdfViewBase()

PdfViewBase::~PdfViewBase ( )
virtual

destructor.

References iSurface.

◆ PdfViewBase()

PdfViewBase::PdfViewBase ( )
protected

Construct a new canvas.

Referenced by viewHeight().

Member Function Documentation

◆ setPdf()

void PdfViewBase::setPdf ( const PdfFile pdf)

Provide the PDF document.

References iFonts, iPage, iPdf, iResources, and iStream.

◆ setPage()

void PdfViewBase::setPage ( const PdfDict page,
const Rect paper 
)

Provide the page to view.

References ipe::PdfObj::dict(), ipe::PdfDict::get(), iPage, iPaperBox, iPdf, and iStream.

◆ pan()

Vector ipe::PdfViewBase::pan ( ) const
inline

Return current pan.

References iPan.

◆ zoom()

double ipe::PdfViewBase::zoom ( ) const
inline

Return current zoom.

References iZoom.

Referenced by setZoom(), and viewHeight().

◆ center()

Vector ipe::PdfViewBase::center ( ) const
inline

Return center of view.

References iHeight, and iWidth.

Referenced by canvasTfm(), devToUser(), and userToDev().

◆ viewWidth()

int ipe::PdfViewBase::viewWidth ( ) const
inline

Return width of view.

References iWidth.

◆ viewHeight()

int ipe::PdfViewBase::viewHeight ( ) const
inline

◆ devToUser()

Vector PdfViewBase::devToUser ( const Vector arg) const

Convert canvas (device) coordinates to user coordinates.

References center(), iPan, iZoom, ipe::Vector::x, and ipe::Vector::y.

Referenced by viewHeight().

◆ userToDev()

Vector PdfViewBase::userToDev ( const Vector arg) const

Convert user coordinates to canvas (device) coordinates.

References center(), iPan, iZoom, ipe::Vector::x, and ipe::Vector::y.

Referenced by viewHeight().

◆ setPan()

void PdfViewBase::setPan ( const Vector v)

Set current pan position.

The pan position is the user coordinate that is displayed at the very center of the canvas.

References iPan.

Referenced by viewHeight().

◆ setZoom()

void PdfViewBase::setZoom ( double  zoom)

Set current zoom factor.

The zoom factor maps user coordinates to screen pixel coordinates.

References iZoom, and zoom().

Referenced by viewHeight().

◆ canvasTfm()

Matrix PdfViewBase::canvasTfm ( ) const

Matrix mapping user coordinates to canvas coordinates.

References center(), iPan, and iZoom.

Referenced by viewHeight().

◆ updatePdf()

void PdfViewBase::updatePdf ( )

Mark for update with redrawing of PDF document.

References invalidate(), and iRepaint.

Referenced by viewHeight().

◆ invalidate() [1/2]

virtual void ipe::PdfViewBase::invalidate ( int  x,
int  y,
int  w,
int  h 
)
pure virtual

Implemented in ipe::PdfView.

◆ invalidate() [2/2]

virtual void ipe::PdfViewBase::invalidate ( )
pure virtual

Implemented in ipe::PdfView.

Referenced by updatePdf(), and viewHeight().

◆ drawPaper()

void PdfViewBase::drawPaper ( cairo_t *  cc)
protected

◆ refreshSurface()

Member Data Documentation

◆ iWidth

double ipe::PdfViewBase::iWidth
protected

◆ iHeight

double ipe::PdfViewBase::iHeight
protected

◆ iBWidth

double ipe::PdfViewBase::iBWidth
protected

◆ iBHeight

double ipe::PdfViewBase::iBHeight
protected

◆ iPan

Vector ipe::PdfViewBase::iPan
protected

◆ iZoom

double ipe::PdfViewBase::iZoom
protected

◆ iRepaint

bool ipe::PdfViewBase::iRepaint
protected

Referenced by refreshSurface(), and updatePdf().

◆ iSurface

cairo_surface_t* ipe::PdfViewBase::iSurface
protected

◆ iCascade

std::unique_ptr<Cascade> ipe::PdfViewBase::iCascade
protected

Referenced by refreshSurface().

◆ iPage

const PdfDict* ipe::PdfViewBase::iPage
protected

Referenced by refreshSurface(), setPage(), and setPdf().

◆ iPaperBox

Rect ipe::PdfViewBase::iPaperBox
protected

Referenced by drawPaper(), and setPage().

◆ iStream

const PdfDict* ipe::PdfViewBase::iStream
protected

Referenced by refreshSurface(), setPage(), and setPdf().

◆ iPdf

const PdfFile* ipe::PdfViewBase::iPdf
protected

Referenced by setPage(), and setPdf().

◆ iResources

std::unique_ptr<PdfFileResources> ipe::PdfViewBase::iResources
protected

Referenced by setPdf().

◆ iFonts

std::unique_ptr<Fonts> ipe::PdfViewBase::iFonts
protected

Referenced by refreshSurface(), and setPdf().


The documentation for this class was generated from the following files:
  • ipepdfview.h
  • ipepdfview.cpp

ipe-7.2.13/build/doc/classipe_1_1_path-members.html0000644000175000017500000005771213561570220021711 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Path Member List

This is the complete list of members for ipe::Path, including all inherited members.

accept(Visitor &visitor) constipe::Pathvirtual
addToBBox(Rect &box, const Matrix &m, bool cp) constipe::Pathvirtual
arrow() constipe::Pathinline
arrowShape() constipe::Pathinline
arrowSize() constipe::Pathinline
asGroup()ipe::Objectvirtual
asGroup() constipe::Objectvirtual
asImage()ipe::Objectvirtual
asPath()ipe::Pathvirtual
asReference()ipe::Objectvirtual
asText()ipe::Objectvirtual
checkStyle(const Cascade *sheet, AttributeSeq &seq) constipe::Pathvirtual
checkSymbol(Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq)ipe::Objectprotectedstatic
clone() constipe::Pathvirtual
create(const XmlAttributes &attr, String data)ipe::Pathstatic
dashStyle() constipe::Pathinline
distance(const Vector &v, const Matrix &m, double bound) constipe::Pathvirtual
draw(Painter &painter) constipe::Pathvirtual
drawArrow(Painter &painter, Vector pos, Angle alpha, Attribute shape, Attribute size, double radius)ipe::Pathstatic
drawSimple(Painter &painter) constipe::Pathvirtual
EGroup enum valueipe::Object
EImage enum valueipe::Object
EPath enum valueipe::Object
EReference enum valueipe::Object
EText enum valueipe::Object
fill() constipe::Pathinline
fillRule() constipe::Pathinline
getAttribute(Property prop) const noexceptipe::Pathvirtual
gradient() constipe::Pathinline
iMatrixipe::Objectprotected
iPinnedipe::Objectprotected
iTransformationsipe::Objectprotected
lineCap() constipe::Pathinline
lineJoin() constipe::Pathinline
matrix() constipe::Objectinline
Object()ipe::Objectexplicitprotected
Object(const AllAttributes &attr)ipe::Objectexplicitprotected
Object(const Object &rhs)ipe::Objectprotected
Object(const XmlAttributes &attr)ipe::Objectexplicitprotected
opacity() constipe::Pathinline
Path(const AllAttributes &attr, const Shape &shape, bool withArrows=false)ipe::Pathexplicit
pathMode() constipe::Pathinline
pen() constipe::Pathinline
pinned() constipe::Objectvirtual
rArrow() constipe::Pathinline
rArrowShape() constipe::Pathinline
rArrowSize() constipe::Pathinline
saveAsXml(Stream &stream, String layer) constipe::Pathvirtual
saveAttributesAsXml(Stream &stream, String layer) constipe::Objectprotected
setArrow(bool arrow, Attribute shape, Attribute size)ipe::Path
setAttribute(Property prop, Attribute value)ipe::Pathvirtual
setDashStyle(Attribute dash)ipe::Path
setFill(Attribute fill)ipe::Path
setFillRule(TFillRule s)ipe::Path
setGradient(Attribute a)ipe::Path
setLineCap(TLineCap s)ipe::Path
setLineJoin(TLineJoin s)ipe::Path
setMatrix(const Matrix &matrix)ipe::Object
setOpacity(Attribute opaq)ipe::Path
setPathMode(TPathMode pm)ipe::Path
setPen(Attribute pen)ipe::Path
setPinned(TPinned pin)ipe::Object
setRarrow(bool arrow, Attribute shape, Attribute size)ipe::Path
setShape(const Shape &shape)ipe::Path
setStroke(Attribute stroke)ipe::Path
setStrokeOpacity(Attribute opaq)ipe::Path
setTiling(Attribute a)ipe::Path
setTransformations(TTransformations trans)ipe::Object
shape() constipe::Pathinline
snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Pathvirtual
snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Pathvirtual
snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Pathvirtual
stroke() constipe::Pathinline
strokeOpacity() constipe::Pathinline
tiling() constipe::Pathinline
transformations() constipe::Objectinline
type() constipe::Pathvirtual
Type enum nameipe::Object
~Object()=0ipe::Objectpure virtual

ipe-7.2.13/build/doc/functions_z.html0000644000175000017500000000374513561570220017340 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- z -


ipe-7.2.13/build/doc/manual_5.html0000644000175000017500000001253213561570220016472 0ustar otfriedotfried Ipe Manual -- 3.2 The current selection
3.3 Moving and scaling objects3 General Concepts3.1 Order of objects3.2 The current selection

3.2 The current selection

Whenever you call an Ipe function, you have to specify which objects the function should operate on. This is done by selecting objects. The selected objects (the selection) consists of two parts: the primary selection consists of exactly one object (of course, this object could be a group). All additional selected objects form the secondary selection. Some functions (like the context menu) operate only on the primary selection, while others treat primary and secondary selections differently (the align functions, for instance, align the secondary selections with respect to the primary selection.)

The selection is shown by outlining the selected object in color. Note that the primary selection is shown with a slightly different look.

The primary and secondary selections can be set in selection mode. Clicking the left mouse button close to an object makes that object the primary selection and deselects all other objects. If you keep the Shift key pressed while clicking with the left mouse key, the object closest to the mouse will be added to or deleted from the current selection. You can also drag a rectangle with the mouse—when you release the mouse button, all objects inside the rectangle will be selected. With the Shift key, the selection status of all objects inside the rectangle will be switched.

To make it easier to select objects that are below or close to other objects, it is convenient to understand exactly how selecting objects works. In fact, when you press the mouse button, a list of all objects is computed that are sufficiently close to the mouse position (the exact distance is set as the select_distance in prefs.lua). This list is then sorted by increasing distance from the mouse and by increasing depth in the drawing. If Shift was not pressed, the current selection is now cleared. Then the first object in the list is presented. Now, while still keeping the mouse button pressed, you can use the Space key to step through the list of objects near the mouse in order of increasing depth and distance. When you release the right mouse button, the object is selected (or deselected).

When measuring the distance from the mouse position to objects, Ipe considers the boundary of objects only. So to select a filled object, don't just click somewhere in its interior, but close to its boundary.

Another way to select objects is using the Select all function from the Edit menu. It selects all objects on the page. Similarly, the Select all in layer function in the Layer menu selects all objects in the active layer.

ipe-7.2.13/build/doc/classipe_1_1_xml_parser-members.html0000644000175000017500000001410713561570220023120 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::XmlParser Member List

This is the complete list of members for ipe::XmlParser, including all inherited members.

eos()ipe::XmlParserinline
getChar()ipe::XmlParserinline
iChipe::XmlParserprotected
iPosipe::XmlParserprotected
iSourceipe::XmlParserprotected
isTagChar(int ch)ipe::XmlParserinline
iTopElementipe::XmlParserprotected
parseAttributes(XmlAttributes &attr, bool qm=false)ipe::XmlParser
parsePCDATA(String tag, String &pcdata)ipe::XmlParser
parsePosition() constipe::XmlParserinline
parseToTag()ipe::XmlParser
parseToTagX()ipe::XmlParserprotected
skipWhitespace()ipe::XmlParser
XmlParser(DataSource &source)ipe::XmlParser
~XmlParser()ipe::XmlParservirtual

ipe-7.2.13/build/doc/nav_f.png0000644000175000017500000000023113561570220015673 0ustar otfriedotfried‰PNG  IHDR8³»`IDATxíÝK€ EÑ–·[†øBÑmkâÄÂH—prÓ¼.‚Žó‚ꎤR6Z VI±E‚5j³„lóš›iI˜¬ÞêçJ0ŒÑÑ/Žû›™uøñóÞ¿6sH ÝõyIEND®B`‚ipe-7.2.13/build/doc/tab_s.png0000644000175000017500000000027013561570220015675 0ustar otfriedotfried‰PNG  IHDR$ÇÇ[IDATxíÝ ‚@@Ñ£?Q…¤"š¢%¦I‘—Šf–6[´HÃäQƒ<Þâõþ]ždr Í’s?ˆO=Ñññw'ÌF‡Ž íðö-~rÃ[œèŠ­ì¬mƒÖ¬ƒݯнŠÕF)Yº% §`nÌ,9B ™’©!ÑŒ\ý<Å#üîî•IEND®B`‚ipe-7.2.13/build/doc/classipe_1_1_fixed-members.html0000644000175000017500000001365513561570220022052 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Fixed Member List

This is the complete list of members for ipe::Fixed, including all inherited members.

Fixed(int val)ipe::Fixedinlineexplicit
Fixed()ipe::Fixedinlineexplicit
fromDouble(double val)ipe::Fixedstatic
fromInternal(int32_t val)ipe::Fixedinlinestatic
internal() constipe::Fixedinline
isInteger() constipe::Fixedinline
mult(int a, int b) constipe::Fixed
operator!=(const Fixed &rhs) constipe::Fixedinline
operator<(const Fixed &rhs) constipe::Fixedinline
operator<<(Stream &stream, const Fixed &f)ipe::Fixedfriend
operator<<(Stream &stream, const Fixed &f)ipe::Fixedrelated
operator==(const Fixed &rhs) constipe::Fixedinline
toDouble() constipe::Fixedinline
toInt() constipe::Fixedinline

ipe-7.2.13/build/doc/classipe_1_1_document-members.html0000644000175000017500000003610113561570220022560 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Document Member List

This is the complete list of members for ipe::Document, including all inherited members.

cascade()ipe::Documentinline
cascade() constipe::Documentinline
checkStyle(AttributeSeq &seq) constipe::Document
countPages() constipe::Documentinline
countTotalViews() constipe::Document
Document()ipe::Document
Document(const Document &rhs)ipe::Document
EFileOpenError enum valueipe::Document
ENotAnIpeFile enum valueipe::Document
ErrLatex enum valueipe::Document
ErrLatexOutput enum valueipe::Document
ErrNoDir enum valueipe::Document
ErrNone enum valueipe::Document
ErrNoText enum valueipe::Document
ErrOldPdfLatex enum valueipe::Document
ErrRunLatex enum valueipe::Document
ErrWritingSource enum valueipe::Document
EVersionTooOld enum valueipe::Document
EVersionTooRecent enum valueipe::Document
exportPages(const char *fname, uint32_t flags, int fromPage, int toPage) constipe::Document
exportView(const char *fname, FileFormat format, uint32_t flags, int pno, int vno) constipe::Document
fileFormat(DataSource &source)ipe::Documentstatic
findBitmaps(BitmapFinder &bm) constipe::Document
findPage(String nameOrNumber) constipe::Document
formatFromFilename(String fn)ipe::Documentstatic
insert(int no, Page *page)ipe::Document
load(DataSource &source, FileFormat format, int &reason)ipe::Documentstatic
load(const char *fname, int &reason)ipe::Documentstatic
LoadErrors enum nameipe::Document
loadWithErrorReport(const char *fname)ipe::Documentstatic
operator=(const Document &rhs)=deleteipe::Document
page(int no) constipe::Documentinline
page(int no)ipe::Documentinline
properties() constipe::Documentinline
push_back(Page *page)ipe::Document
remove(int no)ipe::Document
replaceCascade(Cascade *cascade)ipe::Document
resources() const noexceptipe::Documentinline
runLatex(String docname, String &logFile)ipe::Document
runLatex(String docname)ipe::Document
save(TellStream &stream, FileFormat format, uint32_t flags) constipe::Document
save(const char *fname, FileFormat format, uint32_t flags) constipe::Document
saveAsXml(Stream &stream, bool usePdfBitmaps=false) constipe::Document
set(int no, Page *page)ipe::Document
setProperties(const SProperties &info)ipe::Document
setResources(PdfResources *resources)ipe::Document
~Document()ipe::Document

ipe-7.2.13/build/doc/classipe_1_1_pdf_painter.html0000644000175000017500000024205413561570220021613 0ustar otfriedotfried Ipelib: ipe::PdfPainter Class Reference
Ipelib

#include <ipepdfwriter.h>

Inherits ipe::Painter.

Inherited by ipe::PsPainter.

Public Member Functions

 PdfPainter (const Cascade *style, Stream &stream)
 
virtual ~PdfPainter ()
 
- Public Member Functions inherited from ipe::Painter
 Painter (const Cascade *style)
 
virtual ~Painter ()
 
void transform (const Matrix &m)
 
void untransform (TTransformations trans)
 
void translate (const Vector &v)
 
void push ()
 
void pop ()
 
void pushMatrix ()
 
void popMatrix ()
 
void newPath ()
 
void moveTo (const Vector &v)
 
void lineTo (const Vector &v)
 
void curveTo (const Vector &v1, const Vector &v2, const Vector &v3)
 
void curveTo (const Bezier &bezier)
 
void rect (const Rect &re)
 
void drawEllipse ()
 
void drawArc (const Arc &arc)
 
void closePath ()
 
void drawPath (TPathMode mode)
 
void drawBitmap (Bitmap bitmap)
 
void drawText (const Text *text)
 
void drawSymbol (Attribute symbol)
 
void addClipPath ()
 
void setStroke (Attribute color)
 
void setFill (Attribute color)
 
void setPen (Attribute pen)
 
void setDashStyle (Attribute dash)
 
void setLineCap (TLineCap cap)
 
void setLineJoin (TLineJoin join)
 
void setFillRule (TFillRule rule)
 
void setSymStroke (Attribute color)
 
void setSymFill (Attribute color)
 
void setSymPen (Attribute wid)
 
void setOpacity (Attribute opaq)
 
void setStrokeOpacity (Attribute opaq)
 
void setTiling (Attribute til)
 
void setGradient (Attribute grad)
 
const Cascadecascade () const
 
Color stroke () const
 
Color fill () const
 
const Matrixmatrix () const
 
Fixed pen () const
 
String dashStyle () const
 
void dashStyle (std::vector< double > &dashes, double &offset) const
 
TLineCap lineCap () const
 
TLineJoin lineJoin () const
 
TFillRule fillRule () const
 
Color symStroke () const
 
Color symFill () const
 
Fixed symPen () const
 
Fixed opacity () const
 
Fixed strokeOpacity () const
 
Attribute tiling () const
 
Attribute gradient () const
 
const Statestate () const
 
void setState (const State &state)
 

Static Public Member Functions

static void drawColor (Stream &stream, Color color, const char *gray, const char *rgb)
 

Protected Member Functions

virtual void doPush ()
 
virtual void doPop ()
 
virtual void doNewPath ()
 
virtual void doMoveTo (const Vector &v)
 
virtual void doLineTo (const Vector &v)
 
virtual void doCurveTo (const Vector &v1, const Vector &v2, const Vector &v3)
 
virtual void doClosePath ()
 
virtual void doDrawPath (TPathMode mode)
 
virtual void doDrawBitmap (Bitmap bitmap)
 
virtual void doDrawText (const Text *text)
 
virtual void doAddClipPath ()
 
virtual void doDrawSymbol (Attribute symbol)
 
void drawAttributes ()
 
void drawOpacity (bool withStroke)
 
- Protected Member Functions inherited from ipe::Painter
virtual void doDrawArc (const Arc &arc)
 
void drawArcAsBezier (double alpha)
 

Protected Attributes

StreamiStream
 
std::list< StateiActiveState
 
- Protected Attributes inherited from ipe::Painter
std::list< StateiState
 
std::list< MatrixiMatrix
 
const CascadeiCascade
 
int iInPath
 

Constructor & Destructor Documentation

◆ PdfPainter()

◆ ~PdfPainter()

Member Function Documentation

◆ drawColor()

void PdfPainter::drawColor ( Stream stream,
Color  color,
const char *  gray,
const char *  rgb 
)
static

◆ doPush()

void PdfPainter::doPush ( )
protectedvirtual

Perform graphics state push on output medium.

Reimplemented from ipe::Painter.

References iActiveState, iStream, and ipe::Painter::state().

Referenced by ~PdfPainter().

◆ doPop()

void PdfPainter::doPop ( )
protectedvirtual

Perform graphics state pop on output medium.

Reimplemented from ipe::Painter.

References iActiveState, and iStream.

Referenced by ~PdfPainter().

◆ doNewPath()

void PdfPainter::doNewPath ( )
protectedvirtual

Perform new path operator.

Reimplemented from ipe::Painter.

Reimplemented in ipe::PsPainter.

References drawAttributes().

Referenced by ~PdfPainter().

◆ doMoveTo()

void PdfPainter::doMoveTo ( const Vector v)
protectedvirtual

Perform moveto operator.

The transformation matrix has already been applied.

Reimplemented from ipe::Painter.

References iStream.

Referenced by ~PdfPainter().

◆ doLineTo()

void PdfPainter::doLineTo ( const Vector v)
protectedvirtual

Perform lineto operator.

The transformation matrix has already been applied.

Reimplemented from ipe::Painter.

References iStream.

Referenced by ~PdfPainter().

◆ doCurveTo()

void PdfPainter::doCurveTo ( const Vector v1,
const Vector v2,
const Vector v3 
)
protectedvirtual

Perform curveto operator.

The transformation matrix has already been applied.

Reimplemented from ipe::Painter.

References iStream.

Referenced by ~PdfPainter().

◆ doClosePath()

void PdfPainter::doClosePath ( )
protectedvirtual

Perform closepath operator.

Reimplemented from ipe::Painter.

References iStream.

Referenced by ~PdfPainter().

◆ doDrawPath()

◆ doDrawBitmap()

void PdfPainter::doDrawBitmap ( Bitmap  bitmap)
protectedvirtual

Draw a bitmap.

Reimplemented from ipe::Painter.

Reimplemented in ipe::PsPainter.

References drawOpacity(), iStream, ipe::Painter::matrix(), and ipe::Bitmap::objNum().

Referenced by ~PdfPainter().

◆ doDrawText()

◆ doAddClipPath()

void PdfPainter::doAddClipPath ( )
protectedvirtual

Add a clip path.

Reimplemented from ipe::Painter.

Reimplemented in ipe::PsPainter.

References iStream.

Referenced by ~PdfPainter().

◆ doDrawSymbol()

◆ drawAttributes()

◆ drawOpacity()

void PdfPainter::drawOpacity ( bool  withStroke)
protected

Member Data Documentation

◆ iStream

◆ iActiveState

std::list<State> ipe::PdfPainter::iActiveState
protected

The documentation for this class was generated from the following files:
  • ipepdfwriter.h
  • ipepdfwriter.cpp

ipe-7.2.13/build/doc/manual_34.html0000644000175000017500000000572313561570220016560 0ustar otfriedotfried Ipe Manual -- 8 Advanced topics ipe-7.2.13/build/doc/manual_42.html0000644000175000017500000000742613561570220016561 0ustar otfriedotfried Ipe Manual -- 8.8 Ipe on a USB-stick
8.9 Running Ipe under Wine on Linux8 Advanced topics8.7 Environment variables8.8 Ipe on a USB-stick

8.8 Ipe on a USB-stick

To prepare a USB-stick from which you can run Ipe without installing anything to a Windows computer, you first need to install texlive. Download install-tl-windows.exe and run it, selecting the option for Custom install. When the full installer starts, change Portable setup to Yes, and change the TEXDIR directory to X:\texlive, where X is the drive letter of the USB-stick. You can also decrease the size of your installation by unselecting unnecessary packages and languages.

Installing texlive will take quite a while. When it is done, unzip the Ipe package for Windows onto the root of the USB-stick. You should have the Ipe binary in X:\ipe-7.x.y\bin\ipe.exe.

Now create a directory X:\latexrun (it will be used by Ipe to run Latex).

Finally, you need to create a small configuration file as X:\ipe-7.x.y\ipe.conf. The contents of the file should be:

IPELATEXPATH=\texlive\bin
IPELATEXDIR=\latexrun

It should now work to run Ipe from the USB-stick, whenever you plug it into a Windows computer.

ipe-7.2.13/build/doc/namespacemembers_eval.html0000644000175000017500000003022713561570220021310 0ustar otfriedotfried Ipelib: Namespace Members
Ipelib
 

- e -

  • EAlignBaseline : ipe
  • EAlignBottom : ipe
  • EAlignHCenter : ipe
  • EAlignLeft : ipe
  • EAlignRight : ipe
  • EAlignTop : ipe
  • EAlignVCenter : ipe
  • EAngleSize : ipe
  • EArrowSize : ipe
  • EBevelJoin : ipe
  • EButtCap : ipe
  • EColor : ipe
  • EDashStyle : ipe
  • EDefaultCap : ipe
  • EDefaultJoin : ipe
  • EDefaultRule : ipe
  • EEffect : ipe
  • EEvenOddRule : ipe
  • EFilledOnly : ipe
  • EFixedPin : ipe
  • EGradient : ipe
  • EGridSize : ipe
  • EHorizontalPin : ipe
  • ELabelStyle : ipe
  • EMiterJoin : ipe
  • ENoPin : ipe
  • ENotSelected : ipe
  • EOpacity : ipe
  • EPen : ipe
  • EPrimarySelected : ipe
  • EPropDashStyle : ipe
  • EPropDecoration : ipe
  • EPropFArrow : ipe
  • EPropFArrowShape : ipe
  • EPropFArrowSize : ipe
  • EPropFillColor : ipe
  • EPropFillRule : ipe
  • EPropGradient : ipe
  • EPropHorizontalAlignment : ipe
  • EPropLabelStyle : ipe
  • EPropLineCap : ipe
  • EPropLineJoin : ipe
  • EPropMarkShape : ipe
  • EPropMinipage : ipe
  • EPropOpacity : ipe
  • EPropPathMode : ipe
  • EPropPen : ipe
  • EPropPinned : ipe
  • EPropRArrow : ipe
  • EPropRArrowShape : ipe
  • EPropRArrowSize : ipe
  • EPropStrokeColor : ipe
  • EPropStrokeOpacity : ipe
  • EPropSymbolSize : ipe
  • EPropTextSize : ipe
  • EPropTextStyle : ipe
  • EPropTiling : ipe
  • EPropTransformableText : ipe
  • EPropTransformations : ipe
  • EPropVerticalAlignment : ipe
  • EPropWidth : ipe
  • ERoundCap : ipe
  • ERoundJoin : ipe
  • ESecondarySelected : ipe
  • ESquareCap : ipe
  • EStrokedAndFilled : ipe
  • EStrokedOnly : ipe
  • ESymbol : ipe
  • ESymbolSize : ipe
  • ETextSize : ipe
  • ETextStretch : ipe
  • ETextStyle : ipe
  • ETiling : ipe
  • ETransformationsAffine : ipe
  • ETransformationsRigidMotions : ipe
  • ETransformationsTranslations : ipe
  • EVerticalPin : ipe
  • EWindRule : ipe

ipe-7.2.13/build/doc/modules.html0000644000175000017500000000733613561570220016447 0ustar otfriedotfried Ipelib: Modules
Ipelib
Modules
Here is a list of all modules:
 Ipe AttributesAttributes for Ipe objects
 Ipe BaseBasic classes for Ipe
 Ipe DocumentThe classes managing an Ipe document
 Ipe GeometryGeometric primitives for Ipe
 Ipe ObjectsThe Ipe object model
 Ipe UtilitiesClasses to manage Ipe documents and objects
 The Ipelet interfaceImplementation of Ipe plugins
 Ipe Cairo interfaceDrawing Ipe objects using the Cairo library
 Ipe canvasA widget (control) that displays an Ipe document page

ipe-7.2.13/build/doc/manual_15.html0000644000175000017500000000675513561570220016565 0ustar otfriedotfried Ipe Manual -- 4 Object types
5 SnappingTop3 General Concepts4 Object types

4 Object types

Ipe supports five different types of objects that can be placed on a page, namely path objects (which includes all objects with a stroked contour and filled interior, such as (poly)lines, polygons, splines, splinegons, circles and ellipses, circular and elliptic arcs, and rectangles), text objects, image objects, group objects, and reference objects (which means that a symbol is used at a certain spot on the page).

Path and text objects are created by clicking the left mouse button somewhere on the canvas using the correct Ipe mode. Group objects are created using the Group function in the Edit menu. Image objects are added to the document using Insert image in the File menu. Reference objects can be created either using mark mode, or using the Symbols ipelet.

ipe-7.2.13/build/doc/classipe_1_1_canvas-members.html0000644000175000017500000010367413561570220022227 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Canvas Member List

This is the complete list of members for ipe::Canvas, including all inherited members.

additionalModifiers() constipe::CanvasBaseinline
Canvas(GtkWidget *parent)ipe::Canvas
Canvas(QWidget *parent, Qt::WFlags f=0)ipe::Canvas
Canvas(HWND parent, HINSTANCE hInstance=nullptr)ipe::Canvas
CanvasBase()ipe::CanvasBaseprotected
canvasHeight() constipe::CanvasBaseinline
canvasStyle() constipe::CanvasBaseinline
canvasTfm() constipe::CanvasBase
canvasWidth() constipe::CanvasBaseinline
cascade() constipe::CanvasBaseinline
center() constipe::CanvasBaseinline
computeFifi(double x, double y)ipe::CanvasBaseprotected
createBitmap(uint8_t *p, int w, int h)ipe::Canvasstatic
devToUser(const Vector &arg) constipe::CanvasBase
drawAxes(cairo_t *cc)ipe::CanvasBaseprotected
drawFifi(QPainter &q)ipe::Canvasprotected
ipe::CanvasBase::drawFifi(cairo_t *cr)ipe::CanvasBaseprotected
drawFrame(cairo_t *cc)ipe::CanvasBaseprotected
drawGrid(cairo_t *cc)ipe::CanvasBaseprotected
drawObjects(cairo_t *cc)ipe::CanvasBaseprotected
drawPaper(cairo_t *cc)ipe::CanvasBaseprotected
drawTool(Painter &painter)ipe::CanvasBaseprotected
EAlt enum valueipe::CanvasBase
ECommand enum valueipe::CanvasBase
EControl enum valueipe::CanvasBase
ECrossCursor enum valueipe::CanvasBase
EDotCursor enum valueipe::CanvasBase
EHandCursor enum valueipe::CanvasBase
EMeta enum valueipe::CanvasBase
EShift enum valueipe::CanvasBase
EStandardCursor enum valueipe::CanvasBase
finishTool()ipe::CanvasBase
getDpiForWindow(HWND hwnd)ipe::Canvasstatic
globalPos() constipe::CanvasBaseinline
iAdditionalModifiersipe::CanvasBaseprotected
iAutoOriginipe::CanvasBaseprotected
iAutoSnapipe::CanvasBaseprotected
iBHeightipe::CanvasBaseprotected
iBWidthipe::CanvasBaseprotected
iCascadeipe::CanvasBaseprotected
iDimmedipe::CanvasBaseprotected
iFifiModeipe::CanvasBaseprotected
iFifiVisibleipe::CanvasBaseprotected
iFontsipe::CanvasBaseprotected
iGlobalPosipe::CanvasBaseprotected
iHeightipe::CanvasBaseprotected
iMousePosipe::CanvasBaseprotected
init(HINSTANCE hInstance)ipe::Canvasstatic
invalidate()ipe::Canvasprotectedvirtual
invalidate(int x, int y, int w, int h)ipe::Canvasprotectedvirtual
iObserveripe::CanvasBaseprotected
iOldFifiipe::CanvasBaseprotected
iPageipe::CanvasBaseprotected
iPageNumberipe::CanvasBaseprotected
iPanipe::CanvasBaseprotected
iRepaintObjectsipe::CanvasBaseprotected
iResourcesipe::CanvasBaseprotected
iSelectionVisibleipe::CanvasBaseprotected
isInkModeipe::CanvasBaseprotected
iSnapipe::CanvasBaseprotected
iStyleipe::CanvasBaseprotected
iSurfaceipe::CanvasBaseprotected
iToolipe::CanvasBaseprotected
iUnsnappedMousePosipe::CanvasBaseprotected
iViewipe::CanvasBaseprotected
iWidthipe::CanvasBaseprotected
iZoomipe::CanvasBaseprotected
keyPressEvent(QKeyEvent *ev)ipe::Canvasprotectedvirtual
mouseButton(QMouseEvent *ev, int button, bool press)ipe::Canvasprotected
mouseDoubleClickEvent(QMouseEvent *ev)ipe::Canvasprotectedvirtual
mouseMoveEvent(QMouseEvent *ev)ipe::Canvasprotectedvirtual
mousePressEvent(QMouseEvent *ev)ipe::Canvasprotectedvirtual
mouseReleaseEvent(QMouseEvent *ev)ipe::Canvasprotectedvirtual
paintEvent(QPaintEvent *ev)ipe::Canvasprotectedvirtual
pan() constipe::CanvasBaseinline
pos() constipe::CanvasBaseinline
refreshSurface()ipe::CanvasBaseprotected
selectPageOrView(Document *doc, int page=-1, int startIndex=0, int pageWidth=240, int width=600, int height=480)ipe::CanvasBasestatic
setAdditionalModifiers(int mod)ipe::CanvasBase
setAutoOrigin(const Vector &v)ipe::CanvasBase
setCanvasStyle(const Style &style)ipe::CanvasBase
setCursor(TCursor cursor, double w=1.0, Color *color=nullptr)ipe::Canvasvirtual
setDimmed(bool dimmed)ipe::CanvasBase
setFifiVisible(bool visible)ipe::CanvasBase
setInkMode(bool ink)ipe::CanvasBaseinline
setObserver(CanvasObserver *observer)ipe::CanvasBase
setPage(const Page *page, int pno, int view, const Cascade *sheet)ipe::CanvasBase
setPan(const Vector &v)ipe::CanvasBase
setResources(const PdfResources *resources)ipe::CanvasBase
setSelectionVisible(bool visible)ipe::CanvasBase
setSnap(const Snap &s)ipe::CanvasBase
setTool(Tool *tool)ipe::CanvasBase
setZoom(double zoom)ipe::CanvasBase
simpleSnapPos() constipe::CanvasBase
sizeHint() constipe::Canvasprotectedvirtual
snap() constipe::CanvasBaseinline
snapToPaperAndFrame()ipe::CanvasBaseprotected
tabletEvent(QTabletEvent *ev)ipe::Canvasprotectedvirtual
TCursor enum nameipe::CanvasBase
TModifiers enum nameipe::CanvasBase
tool()ipe::CanvasBaseinline
unsnappedPos() constipe::CanvasBaseinline
update()ipe::CanvasBase
updateTool()ipe::CanvasBase
userToDev(const Vector &arg) constipe::CanvasBase
wheelEvent(QWheelEvent *ev)ipe::Canvasprotectedvirtual
window() constipe::Canvasinline
windowId() constipe::Canvasinline
zoom() constipe::CanvasBaseinline
~Canvas()ipe::Canvas
~CanvasBase()ipe::CanvasBasevirtual

ipe-7.2.13/build/doc/functions_func_t.html0000644000175000017500000001610013561570220020332 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- t -


ipe-7.2.13/build/doc/functions_func_c.html0000644000175000017500000003037413561570220020322 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- c -


ipe-7.2.13/build/doc/structipe_1_1_gradient_1_1_stop.html0000644000175000017500000001100613561570220023030 0ustar otfriedotfried Ipelib: ipe::Gradient::Stop Struct Reference
Ipelib
ipe::Gradient::Stop Struct Reference

#include <ipeattributes.h>

Public Attributes

double offset
 
Color color
 

Detailed Description

A color stop.

Member Data Documentation

◆ offset

double ipe::Gradient::Stop::offset

Offset between 0.0 and 1.0.

Referenced by ipe::ImlParser::parseStyle().

◆ color

Color ipe::Gradient::Stop::color

The color at this offset.

Referenced by ipe::ImlParser::parseStyle().


The documentation for this struct was generated from the following file:
  • ipeattributes.h

ipe-7.2.13/build/doc/manual_10.html0000644000175000017500000000743113561570220016550 0ustar otfriedotfried Ipe Manual -- 3.7 Symbolic and absolute attributes
3.8 Zoom and pan3 General Concepts3.6 Transparency3.7 Symbolic and absolute attributes

3.7 Symbolic and absolute attributes

Attributes such as color, line width, pen, mark size, or text size, can be either absolute (a number, or a set of numbers specifying a color) or symbolic (a name). Symbolic attributes must be translated to absolute values by a stylesheet for rendering.

One purpose of stylesheets is to be able to reuse figures from articles in presentations. Obviously, the figure has to use much larger fonts, markers, arrows, and fatter lines in the presentation. If the original figure used symbolic attributes, this can be achieved by simply swapping the stylesheet for another one.

The Ipe user interface is tuned for using symbolic attribute values. You can use absolute colors, pen width, text size, and mark size by clicking the button to the left of the selector for the symbolic names.

When creating an object, it takes its attributes from the current user interface settings, so if you have selected an absolute value, it will get an absolute attribute. Absolute attributes have the advantage that you are free to choose any value you wish, including picking arbitrary colors using a color chooser. In symbolic mode, you can only use the choices provided by the current stylesheet.

The choices for symbolic attributes provided in the Ipe user interface are taken from your stylesheet.

ipe-7.2.13/build/doc/classipe_1_1_pdf_view_base-members.html0000644000175000017500000002730613561570220023546 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PdfViewBase Member List

This is the complete list of members for ipe::PdfViewBase, including all inherited members.

canvasTfm() constipe::PdfViewBase
center() constipe::PdfViewBaseinline
devToUser(const Vector &arg) constipe::PdfViewBase
drawPaper(cairo_t *cc)ipe::PdfViewBaseprotected
iBHeightipe::PdfViewBaseprotected
iBWidthipe::PdfViewBaseprotected
iCascadeipe::PdfViewBaseprotected
iFontsipe::PdfViewBaseprotected
iHeightipe::PdfViewBaseprotected
invalidate(int x, int y, int w, int h)=0ipe::PdfViewBasepure virtual
invalidate()=0ipe::PdfViewBasepure virtual
iPageipe::PdfViewBaseprotected
iPanipe::PdfViewBaseprotected
iPaperBoxipe::PdfViewBaseprotected
iPdfipe::PdfViewBaseprotected
iRepaintipe::PdfViewBaseprotected
iResourcesipe::PdfViewBaseprotected
iStreamipe::PdfViewBaseprotected
iSurfaceipe::PdfViewBaseprotected
iWidthipe::PdfViewBaseprotected
iZoomipe::PdfViewBaseprotected
pan() constipe::PdfViewBaseinline
PdfViewBase()ipe::PdfViewBaseprotected
refreshSurface()ipe::PdfViewBaseprotected
setPage(const PdfDict *page, const Rect &paper)ipe::PdfViewBase
setPan(const Vector &v)ipe::PdfViewBase
setPdf(const PdfFile *pdf)ipe::PdfViewBase
setZoom(double zoom)ipe::PdfViewBase
updatePdf()ipe::PdfViewBase
userToDev(const Vector &arg) constipe::PdfViewBase
viewHeight() constipe::PdfViewBaseinline
viewWidth() constipe::PdfViewBaseinline
zoom() constipe::PdfViewBaseinline
~PdfViewBase()ipe::PdfViewBasevirtual

ipe-7.2.13/build/doc/classipe_1_1_inflate_source.html0000644000175000017500000001764513561570220022330 0ustar otfriedotfried Ipelib: ipe::InflateSource Class Reference
Ipelib
ipe::InflateSource Class Reference

#include <ipeutils.h>

Inherits ipe::DataSource.

Public Member Functions

 InflateSource (DataSource &source)
 
virtual ~InflateSource ()
 
virtual int getChar ()
 
- Public Member Functions inherited from ipe::DataSource
virtual ~DataSource ()=0
 

Detailed Description

Filter source adding flate decompression.

Constructor & Destructor Documentation

◆ InflateSource()

InflateSource::InflateSource ( DataSource source)

References ipe::Buffer::data().

◆ ~InflateSource()

InflateSource::~InflateSource ( )
virtual

Member Function Documentation

◆ getChar()

int InflateSource::getChar ( )
virtual

The documentation for this class was generated from the following files:
  • ipeutils.h
  • ipeutils.cpp

ipe-7.2.13/build/doc/classipe_1_1_lex-members.html0000644000175000017500000001354213561570220021536 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Lex Member List

This is the complete list of members for ipe::Lex, including all inherited members.

eos() constipe::Lexinline
fromMark()ipe::Lexinline
getChar()ipe::Lexinline
getDouble()ipe::Lex
getFixed()ipe::Lex
getHexByte()ipe::Lex
getHexNumber()ipe::Lex
getInt()ipe::Lex
Lex(String str)ipe::Lexexplicit
mark()ipe::Lexinline
nextToken()ipe::Lex
operator>>(int &i)ipe::Lexinline
operator>>(double &d)ipe::Lexinline
operator>>(Fixed &d)ipe::Lexinline
skipWhitespace()ipe::Lex
token()ipe::Lex

ipe-7.2.13/build/doc/manual_43.html0000644000175000017500000000710513561570220016554 0ustar otfriedotfried Ipe Manual -- 8.9 Running Ipe under Wine on Linux
8.10 Using cygwin latex on Windows8 Advanced topics8.8 Ipe on a USB-stick8.9 Running Ipe under Wine on Linux

8.9 Running Ipe under Wine on Linux

Ipe itself works fine under Wine, but there is an issue: We don't want to create a new tex installation for Windows under Wine, we want to reuse the Linux tex installation!

So first we need to make the pdflatex program available to Wine, by putting a symbolic link in the simulated C: drive.

$ cd ~/.wine/drive_c/windows/
$ ln -s /usr/bin/pdflatex pdflatex.exe

The second problem is that Ipe is not able to wait for the completion of the pdflatex call—it starts pdflatex, and then immediately tries to read the pdflatex output, which of course fails. The solution is to make Ipe wait for a specified number of milliseconds before trying to read the pdflatex output.

You achieve this by creating a small text file called ipe.conf and placing it in the top-level Ipe directory (that is, the directory that contains readme.txt and gpl.txt). The contents of the file should be:

IPEWINE=1000
IPELATEXPATH=c:\windows

(You can define any other environment variable in the same file.)

ipe-7.2.13/build/doc/manual_6.html0000644000175000017500000001045513561570220016475 0ustar otfriedotfried Ipe Manual -- 3.3 Moving and scaling objects
3.4 Stroke and fill colors3 General Concepts3.2 The current selection3.3 Moving and scaling objects

3.3 Moving and scaling objects

There are four modes for transforming objects: translate, stretch, rotate, and shear. If you hold the shift key while pressing the left mouse button, the stretch function keeps the aspect ratio of the objects (an operation we call scaling), and the translate function is restricted to horizontal and vertical translations.

Normally, the transformation functions work on the current selection. However, to make it more convenient to move around many different objects, there is an exception: When the mouse button is pressed while the cursor is not near the current selection, but there is some other object close to the cursor, that object is moved, rotated, scaled, or sheared instead.

By default, the rotate function rotates around the center of the bounding box for the selected objects. This behavior can be overridden by specifying an axis system. If an axis system is set, then the origin is used as the center.

The scale, stretch, and shear functions use a corner of the bounding box for the selected objects as the fix-point of the transformation. Again, if an axis system is set, the origin of the system is used instead. In this case, the shear function will use your x-axis as the fixed axis of the shear operation (rather than a horizontal line).

It is often convenient to rotate or scale around a vertex of an object. This is easy to achieve by setting the origin of the axis system to that vertex, using the Snap to vertex function for setting the axis system.

ipe-7.2.13/build/doc/classipe_1_1_painter-members.html0000644000175000017500000005435313561570220022415 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Painter Member List

This is the complete list of members for ipe::Painter, including all inherited members.

addClipPath()ipe::Painter
cascade() constipe::Painterinline
closePath()ipe::Painter
curveTo(const Vector &v1, const Vector &v2, const Vector &v3)ipe::Painter
curveTo(const Bezier &bezier)ipe::Painterinline
dashStyle() constipe::Painterinline
dashStyle(std::vector< double > &dashes, double &offset) constipe::Painter
doAddClipPath()ipe::Painterprotectedvirtual
doClosePath()ipe::Painterprotectedvirtual
doCurveTo(const Vector &v1, const Vector &v2, const Vector &v3)ipe::Painterprotectedvirtual
doDrawArc(const Arc &arc)ipe::Painterprotectedvirtual
doDrawBitmap(Bitmap bitmap)ipe::Painterprotectedvirtual
doDrawPath(TPathMode mode)ipe::Painterprotectedvirtual
doDrawSymbol(Attribute symbol)ipe::Painterprotectedvirtual
doDrawText(const Text *text)ipe::Painterprotectedvirtual
doLineTo(const Vector &v)ipe::Painterprotectedvirtual
doMoveTo(const Vector &v)ipe::Painterprotectedvirtual
doNewPath()ipe::Painterprotectedvirtual
doPop()ipe::Painterprotectedvirtual
doPush()ipe::Painterprotectedvirtual
drawArc(const Arc &arc)ipe::Painter
drawArcAsBezier(double alpha)ipe::Painterprotected
drawBitmap(Bitmap bitmap)ipe::Painter
drawEllipse()ipe::Painter
drawPath(TPathMode mode)ipe::Painter
drawSymbol(Attribute symbol)ipe::Painter
drawText(const Text *text)ipe::Painter
fill() constipe::Painterinline
fillRule() constipe::Painterinline
gradient() constipe::Painterinline
iCascadeipe::Painterprotected
iInPathipe::Painterprotected
iMatrixipe::Painterprotected
iStateipe::Painterprotected
lineCap() constipe::Painterinline
lineJoin() constipe::Painterinline
lineTo(const Vector &v)ipe::Painter
matrix() constipe::Painterinline
moveTo(const Vector &v)ipe::Painter
newPath()ipe::Painter
opacity() constipe::Painterinline
Painter(const Cascade *style)ipe::Painter
pen() constipe::Painterinline
pop()ipe::Painter
popMatrix()ipe::Painter
push()ipe::Painter
pushMatrix()ipe::Painter
rect(const Rect &re)ipe::Painter
setDashStyle(Attribute dash)ipe::Painter
setFill(Attribute color)ipe::Painter
setFillRule(TFillRule rule)ipe::Painter
setGradient(Attribute grad)ipe::Painter
setLineCap(TLineCap cap)ipe::Painter
setLineJoin(TLineJoin join)ipe::Painter
setOpacity(Attribute opaq)ipe::Painter
setPen(Attribute pen)ipe::Painter
setState(const State &state)ipe::Painter
setStroke(Attribute color)ipe::Painter
setStrokeOpacity(Attribute opaq)ipe::Painter
setSymFill(Attribute color)ipe::Painter
setSymPen(Attribute wid)ipe::Painter
setSymStroke(Attribute color)ipe::Painter
setTiling(Attribute til)ipe::Painter
state() constipe::Painterinline
stroke() constipe::Painterinline
strokeOpacity() constipe::Painterinline
symFill() constipe::Painterinline
symPen() constipe::Painterinline
symStroke() constipe::Painterinline
tiling() constipe::Painterinline
transform(const Matrix &m)ipe::Painter
translate(const Vector &v)ipe::Painter
untransform(TTransformations trans)ipe::Painter
~Painter()ipe::Paintervirtual

ipe-7.2.13/build/doc/functions_func_q.html0000644000175000017500000000307313561570220020334 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- q -


ipe-7.2.13/build/doc/classipe_1_1_deflate_stream.html0000644000175000017500000004322513561570220022276 0ustar otfriedotfried Ipelib: ipe::DeflateStream Class Reference
Ipelib

#include <ipeutils.h>

Inherits ipe::Stream.

Public Member Functions

 DeflateStream (Stream &stream, int level)
 
virtual ~DeflateStream ()
 
virtual void putChar (char ch)
 
virtual void close ()
 
- Public Member Functions inherited from ipe::Stream
virtual ~Stream ()
 
virtual void putString (String s)
 
virtual void putCString (const char *s)
 
virtual void putRaw (const char *data, int size)
 
Streamoperator<< (char ch)
 
Streamoperator<< (const String &s)
 
Streamoperator<< (const char *s)
 
Streamoperator<< (int i)
 
Streamoperator<< (double d)
 
void putHexByte (char b)
 
void putXmlString (String s)
 

Static Public Member Functions

static Buffer deflate (const char *data, int size, int &deflatedSize, int compressLevel)
 

Detailed Description

Filter stream adding flate compression.

Constructor & Destructor Documentation

◆ DeflateStream()

DeflateStream::DeflateStream ( Stream stream,
int  level 
)

◆ ~DeflateStream()

DeflateStream::~DeflateStream ( )
virtual

Member Function Documentation

◆ putChar()

void DeflateStream::putChar ( char  ch)
virtual

Output character.

Implements ipe::Stream.

References ipe::Buffer::data(), deflate(), ipe::Stream::putRaw(), and ipe::Buffer::size().

◆ close()

void DeflateStream::close ( )
virtual

Close the stream. No more writing allowed!

Reimplemented from ipe::Stream.

References ipe::Stream::close(), ipe::Buffer::data(), deflate(), ipe::Stream::putRaw(), and ipe::Buffer::size().

Referenced by ipe::PdfWriter::createPageView(), and ipe::Document::save().

◆ deflate()

Buffer DeflateStream::deflate ( const char *  data,
int  size,
int &  deflatedSize,
int  compressLevel 
)
static

Deflate a buffer in a single run.

The returned buffer may be larger than necessary: deflatedSize is set to the number of bytes actually used.

References ipe::Buffer::data().

Referenced by close(), ipe::Bitmap::embed(), putChar(), and ipe::PdfWriter::~PdfWriter().


The documentation for this class was generated from the following files:
  • ipeutils.h
  • ipeutils.cpp

ipe-7.2.13/build/doc/doxygen.css0000644000175000017500000006647013561570220016304 0ustar otfriedotfried/* The standard CSS for doxygen 1.8.13 */ body, table, div, p, dl { font: 400 14px/22px Roboto,sans-serif; } p.reference, p.definition { font: 400 14px/22px Roboto,sans-serif; } /* @group Heading Levels */ h1.groupheader { font-size: 150%; } .title { font: 400 14px/28px Roboto,sans-serif; font-size: 150%; font-weight: bold; margin: 10px 2px; } h2.groupheader { border-bottom: 1px solid #879ECB; color: #354C7B; font-size: 150%; font-weight: normal; margin-top: 1.75em; padding-top: 8px; padding-bottom: 4px; width: 100%; } h3.groupheader { font-size: 100%; } h1, h2, h3, h4, h5, h6 { -webkit-transition: text-shadow 0.5s linear; -moz-transition: text-shadow 0.5s linear; -ms-transition: text-shadow 0.5s linear; -o-transition: text-shadow 0.5s linear; transition: text-shadow 0.5s linear; margin-right: 15px; } h1.glow, h2.glow, h3.glow, h4.glow, h5.glow, h6.glow { text-shadow: 0 0 15px cyan; } dt { font-weight: bold; } div.multicol { -moz-column-gap: 1em; -webkit-column-gap: 1em; -moz-column-count: 3; -webkit-column-count: 3; } p.startli, p.startdd { margin-top: 2px; } p.starttd { margin-top: 0px; } p.endli { margin-bottom: 0px; } p.enddd { margin-bottom: 4px; } p.endtd { margin-bottom: 2px; } /* @end */ caption { font-weight: bold; } span.legend { font-size: 70%; text-align: center; } h3.version { font-size: 90%; text-align: center; } div.qindex, div.navtab{ background-color: #EBEFF6; border: 1px solid #A3B4D7; text-align: center; } div.qindex, div.navpath { width: 100%; line-height: 140%; } div.navtab { margin-right: 15px; } /* @group Link Styling */ a { color: #3D578C; font-weight: normal; text-decoration: none; } .contents a:visited { color: #4665A2; } a:hover { text-decoration: underline; } a.qindex { font-weight: bold; } a.qindexHL { font-weight: bold; background-color: #9CAFD4; color: #ffffff; border: 1px double #869DCA; } .contents a.qindexHL:visited { color: #ffffff; } a.el { font-weight: bold; } a.elRef { } a.code, a.code:visited, a.line, a.line:visited { color: #4665A2; } a.codeRef, a.codeRef:visited, a.lineRef, a.lineRef:visited { color: #4665A2; } /* @end */ dl.el { margin-left: -1cm; } pre.fragment { border: 1px solid #C4CFE5; background-color: #FBFCFD; padding: 4px 6px; margin: 4px 8px 4px 2px; overflow: auto; word-wrap: break-word; font-size: 9pt; line-height: 125%; font-family: monospace, fixed; font-size: 105%; } div.fragment { padding: 0px; margin: 4px 8px 4px 2px; background-color: #FBFCFD; border: 1px solid #C4CFE5; } div.line { font-family: monospace, fixed; font-size: 13px; min-height: 13px; line-height: 1.0; text-wrap: unrestricted; white-space: -moz-pre-wrap; /* Moz */ white-space: -pre-wrap; /* Opera 4-6 */ white-space: -o-pre-wrap; /* Opera 7 */ white-space: pre-wrap; /* CSS3 */ word-wrap: break-word; /* IE 5.5+ */ text-indent: -53px; padding-left: 53px; padding-bottom: 0px; margin: 0px; -webkit-transition-property: background-color, box-shadow; -webkit-transition-duration: 0.5s; -moz-transition-property: background-color, box-shadow; -moz-transition-duration: 0.5s; -ms-transition-property: background-color, box-shadow; -ms-transition-duration: 0.5s; -o-transition-property: background-color, box-shadow; -o-transition-duration: 0.5s; transition-property: background-color, box-shadow; transition-duration: 0.5s; } div.line:after { content:"\000A"; white-space: pre; } div.line.glow { background-color: cyan; box-shadow: 0 0 10px cyan; } span.lineno { padding-right: 4px; text-align: right; border-right: 2px solid #0F0; background-color: #E8E8E8; white-space: pre; } span.lineno a { background-color: #D8D8D8; } span.lineno a:hover { background-color: #C8C8C8; } .lineno { -webkit-touch-callout: none; -webkit-user-select: none; -khtml-user-select: none; -moz-user-select: none; -ms-user-select: none; user-select: none; } div.ah, span.ah { background-color: black; font-weight: bold; color: #ffffff; margin-bottom: 3px; margin-top: 3px; padding: 0.2em; border: solid thin #333; border-radius: 0.5em; -webkit-border-radius: .5em; -moz-border-radius: .5em; box-shadow: 2px 2px 3px #999; -webkit-box-shadow: 2px 2px 3px #999; -moz-box-shadow: rgba(0, 0, 0, 0.15) 2px 2px 2px; background-image: -webkit-gradient(linear, left top, left bottom, from(#eee), to(#000),color-stop(0.3, #444)); background-image: -moz-linear-gradient(center top, #eee 0%, #444 40%, #000 110%); } div.classindex ul { list-style: none; padding-left: 0; } div.classindex span.ai { display: inline-block; } div.groupHeader { margin-left: 16px; margin-top: 12px; font-weight: bold; } div.groupText { margin-left: 16px; font-style: italic; } body { background-color: white; color: black; margin: 0; } div.contents { margin-top: 10px; margin-left: 12px; margin-right: 8px; } td.indexkey { background-color: #EBEFF6; font-weight: bold; border: 1px solid #C4CFE5; margin: 2px 0px 2px 0; padding: 2px 10px; white-space: nowrap; vertical-align: top; } td.indexvalue { background-color: #EBEFF6; border: 1px solid #C4CFE5; padding: 2px 10px; margin: 2px 0px; } tr.memlist { background-color: #EEF1F7; } p.formulaDsp { text-align: center; } img.formulaDsp { } img.formulaInl { vertical-align: middle; } div.center { text-align: center; margin-top: 0px; margin-bottom: 0px; padding: 0px; } div.center img { border: 0px; } address.footer { text-align: right; padding-right: 12px; } img.footer { border: 0px; vertical-align: middle; } /* @group Code Colorization */ span.keyword { color: #008000 } span.keywordtype { color: #604020 } span.keywordflow { color: #e08000 } span.comment { color: #800000 } span.preprocessor { color: #806020 } span.stringliteral { color: #002080 } span.charliteral { color: #008080 } span.vhdldigit { color: #ff00ff } span.vhdlchar { color: #000000 } span.vhdlkeyword { color: #700070 } span.vhdllogic { color: #ff0000 } blockquote { background-color: #F7F8FB; border-left: 2px solid #9CAFD4; margin: 0 24px 0 4px; padding: 0 12px 0 16px; } /* @end */ /* .search { color: #003399; font-weight: bold; } form.search { margin-bottom: 0px; margin-top: 0px; } input.search { font-size: 75%; color: #000080; font-weight: normal; background-color: #e8eef2; } */ td.tiny { font-size: 75%; } .dirtab { padding: 4px; border-collapse: collapse; border: 1px solid #A3B4D7; } th.dirtab { background: #EBEFF6; font-weight: bold; } hr { height: 0px; border: none; border-top: 1px solid #4A6AAA; } hr.footer { height: 1px; } /* @group Member Descriptions */ table.memberdecls { border-spacing: 0px; padding: 0px; } .memberdecls td, .fieldtable tr { -webkit-transition-property: background-color, box-shadow; -webkit-transition-duration: 0.5s; -moz-transition-property: background-color, box-shadow; -moz-transition-duration: 0.5s; -ms-transition-property: background-color, box-shadow; -ms-transition-duration: 0.5s; -o-transition-property: background-color, box-shadow; -o-transition-duration: 0.5s; transition-property: background-color, box-shadow; transition-duration: 0.5s; } .memberdecls td.glow, .fieldtable tr.glow { background-color: cyan; box-shadow: 0 0 15px cyan; } .mdescLeft, .mdescRight, .memItemLeft, .memItemRight, .memTemplItemLeft, .memTemplItemRight, .memTemplParams { background-color: #F9FAFC; border: none; margin: 4px; padding: 1px 0 0 8px; } .mdescLeft, .mdescRight { padding: 0px 8px 4px 8px; color: #555; } .memSeparator { border-bottom: 1px solid #DEE4F0; line-height: 1px; margin: 0px; padding: 0px; } .memItemLeft, .memTemplItemLeft { white-space: nowrap; } .memItemRight { width: 100%; } .memTemplParams { color: #4665A2; white-space: nowrap; font-size: 80%; } /* @end */ /* @group Member Details */ /* Styles for detailed member documentation */ .memtitle { padding: 8px; border-top: 1px solid #A8B8D9; border-left: 1px solid #A8B8D9; border-right: 1px solid #A8B8D9; border-top-right-radius: 4px; border-top-left-radius: 4px; margin-bottom: -1px; background-image: url('nav_f.png'); background-repeat: repeat-x; background-color: #E2E8F2; line-height: 1.25; font-weight: 300; float:left; } .permalink { font-size: 65%; display: inline-block; vertical-align: middle; } .memtemplate { font-size: 80%; color: #4665A2; font-weight: normal; margin-left: 9px; } .memnav { background-color: #EBEFF6; border: 1px solid #A3B4D7; text-align: center; margin: 2px; margin-right: 15px; padding: 2px; } .mempage { width: 100%; } .memitem { padding: 0; margin-bottom: 10px; margin-right: 5px; -webkit-transition: box-shadow 0.5s linear; -moz-transition: box-shadow 0.5s linear; -ms-transition: box-shadow 0.5s linear; -o-transition: box-shadow 0.5s linear; transition: box-shadow 0.5s linear; display: table !important; width: 100%; } .memitem.glow { box-shadow: 0 0 15px cyan; } .memname { font-weight: 400; margin-left: 6px; } .memname td { vertical-align: bottom; } .memproto, dl.reflist dt { border-top: 1px solid #A8B8D9; border-left: 1px solid #A8B8D9; border-right: 1px solid #A8B8D9; padding: 6px 0px 6px 0px; color: #253555; font-weight: bold; text-shadow: 0px 1px 1px rgba(255, 255, 255, 0.9); background-color: #DFE5F1; /* opera specific markup */ box-shadow: 5px 5px 5px rgba(0, 0, 0, 0.15); border-top-right-radius: 4px; /* firefox specific markup */ -moz-box-shadow: rgba(0, 0, 0, 0.15) 5px 5px 5px; -moz-border-radius-topright: 4px; /* webkit specific markup */ -webkit-box-shadow: 5px 5px 5px rgba(0, 0, 0, 0.15); -webkit-border-top-right-radius: 4px; } .overload { font-family: "courier new",courier,monospace; font-size: 65%; } .memdoc, dl.reflist dd { border-bottom: 1px solid #A8B8D9; border-left: 1px solid #A8B8D9; border-right: 1px solid #A8B8D9; padding: 6px 10px 2px 10px; background-color: #FBFCFD; border-top-width: 0; background-image:url('nav_g.png'); background-repeat:repeat-x; background-color: #FFFFFF; /* opera specific markup */ border-bottom-left-radius: 4px; border-bottom-right-radius: 4px; box-shadow: 5px 5px 5px rgba(0, 0, 0, 0.15); /* firefox specific markup */ -moz-border-radius-bottomleft: 4px; -moz-border-radius-bottomright: 4px; -moz-box-shadow: rgba(0, 0, 0, 0.15) 5px 5px 5px; /* webkit specific markup */ -webkit-border-bottom-left-radius: 4px; -webkit-border-bottom-right-radius: 4px; -webkit-box-shadow: 5px 5px 5px rgba(0, 0, 0, 0.15); } dl.reflist dt { padding: 5px; } dl.reflist dd { margin: 0px 0px 10px 0px; padding: 5px; } .paramkey { text-align: right; } .paramtype { white-space: nowrap; } .paramname { color: #602020; white-space: nowrap; } .paramname em { font-style: normal; } .paramname code { line-height: 14px; } .params, .retval, .exception, .tparams { margin-left: 0px; padding-left: 0px; } .params .paramname, .retval .paramname { font-weight: bold; vertical-align: top; } .params .paramtype { font-style: italic; vertical-align: top; } .params .paramdir { font-family: "courier new",courier,monospace; vertical-align: top; } table.mlabels { border-spacing: 0px; } td.mlabels-left { width: 100%; padding: 0px; } td.mlabels-right { vertical-align: bottom; padding: 0px; white-space: nowrap; } span.mlabels { margin-left: 8px; } span.mlabel { background-color: #728DC1; border-top:1px solid #5373B4; border-left:1px solid #5373B4; border-right:1px solid #C4CFE5; border-bottom:1px solid #C4CFE5; text-shadow: none; color: white; margin-right: 4px; padding: 2px 3px; border-radius: 3px; font-size: 7pt; white-space: nowrap; vertical-align: middle; } /* @end */ /* these are for tree view inside a (index) page */ div.directory { margin: 10px 0px; border-top: 1px solid #9CAFD4; border-bottom: 1px solid #9CAFD4; width: 100%; } .directory table { border-collapse:collapse; } .directory td { margin: 0px; padding: 0px; vertical-align: top; } .directory td.entry { white-space: nowrap; padding-right: 6px; padding-top: 3px; } .directory td.entry a { outline:none; } .directory td.entry a img { border: none; } .directory td.desc { width: 100%; padding-left: 6px; padding-right: 6px; padding-top: 3px; border-left: 1px solid rgba(0,0,0,0.05); } .directory tr.even { padding-left: 6px; background-color: #F7F8FB; } .directory img { vertical-align: -30%; } .directory .levels { white-space: nowrap; width: 100%; text-align: right; font-size: 9pt; } .directory .levels span { cursor: pointer; padding-left: 2px; padding-right: 2px; color: #3D578C; } .arrow { color: #9CAFD4; -webkit-user-select: none; -khtml-user-select: none; -moz-user-select: none; -ms-user-select: none; user-select: none; cursor: pointer; font-size: 80%; display: inline-block; width: 16px; height: 22px; } .icon { font-family: Arial, Helvetica; font-weight: bold; font-size: 12px; height: 14px; width: 16px; display: inline-block; background-color: #728DC1; color: white; text-align: center; border-radius: 4px; margin-left: 2px; margin-right: 2px; } .icona { width: 24px; height: 22px; display: inline-block; } .iconfopen { width: 24px; height: 18px; margin-bottom: 4px; background-image:url('folderopen.png'); background-position: 0px -4px; background-repeat: repeat-y; vertical-align:top; display: inline-block; } .iconfclosed { width: 24px; height: 18px; margin-bottom: 4px; background-image:url('folderclosed.png'); background-position: 0px -4px; background-repeat: repeat-y; vertical-align:top; display: inline-block; } .icondoc { width: 24px; height: 18px; margin-bottom: 4px; background-image:url('doc.png'); background-position: 0px -4px; background-repeat: repeat-y; vertical-align:top; display: inline-block; } table.directory { font: 400 14px Roboto,sans-serif; } /* @end */ div.dynheader { margin-top: 8px; -webkit-touch-callout: none; -webkit-user-select: none; -khtml-user-select: none; -moz-user-select: none; -ms-user-select: none; user-select: none; } address { font-style: normal; color: #2A3D61; } table.doxtable caption { caption-side: top; } table.doxtable { border-collapse:collapse; margin-top: 4px; margin-bottom: 4px; } table.doxtable td, table.doxtable th { border: 1px solid #2D4068; padding: 3px 7px 2px; } table.doxtable th { background-color: #374F7F; color: #FFFFFF; font-size: 110%; padding-bottom: 4px; padding-top: 5px; } table.fieldtable { /*width: 100%;*/ margin-bottom: 10px; border: 1px solid #A8B8D9; border-spacing: 0px; -moz-border-radius: 4px; -webkit-border-radius: 4px; border-radius: 4px; -moz-box-shadow: rgba(0, 0, 0, 0.15) 2px 2px 2px; -webkit-box-shadow: 2px 2px 2px rgba(0, 0, 0, 0.15); box-shadow: 2px 2px 2px rgba(0, 0, 0, 0.15); } .fieldtable td, .fieldtable th { padding: 3px 7px 2px; } .fieldtable td.fieldtype, .fieldtable td.fieldname { white-space: nowrap; border-right: 1px solid #A8B8D9; border-bottom: 1px solid #A8B8D9; vertical-align: top; } .fieldtable td.fieldname { padding-top: 3px; } .fieldtable td.fielddoc { border-bottom: 1px solid #A8B8D9; /*width: 100%;*/ } .fieldtable td.fielddoc p:first-child { margin-top: 0px; } .fieldtable td.fielddoc p:last-child { margin-bottom: 2px; } .fieldtable tr:last-child td { border-bottom: none; } .fieldtable th { background-image:url('nav_f.png'); background-repeat:repeat-x; background-color: #E2E8F2; font-size: 90%; color: #253555; padding-bottom: 4px; padding-top: 5px; text-align:left; font-weight: 400; -moz-border-radius-topleft: 4px; -moz-border-radius-topright: 4px; -webkit-border-top-left-radius: 4px; -webkit-border-top-right-radius: 4px; border-top-left-radius: 4px; border-top-right-radius: 4px; border-bottom: 1px solid #A8B8D9; } .tabsearch { top: 0px; left: 10px; height: 36px; background-image: url('tab_b.png'); z-index: 101; overflow: hidden; font-size: 13px; } .navpath ul { font-size: 11px; background-image:url('tab_b.png'); background-repeat:repeat-x; background-position: 0 -5px; height:30px; line-height:30px; color:#8AA0CC; border:solid 1px #C2CDE4; overflow:hidden; margin:0px; padding:0px; } .navpath li { list-style-type:none; float:left; padding-left:10px; padding-right:15px; background-image:url('bc_s.png'); background-repeat:no-repeat; background-position:right; color:#364D7C; } .navpath li.navelem a { height:32px; display:block; text-decoration: none; outline: none; color: #283A5D; font-family: 'Lucida Grande',Geneva,Helvetica,Arial,sans-serif; text-shadow: 0px 1px 1px rgba(255, 255, 255, 0.9); text-decoration: none; } .navpath li.navelem a:hover { color:#6884BD; } .navpath li.footer { list-style-type:none; float:right; padding-left:10px; padding-right:15px; background-image:none; background-repeat:no-repeat; background-position:right; color:#364D7C; font-size: 8pt; } div.summary { float: right; font-size: 8pt; padding-right: 5px; width: 50%; text-align: right; } div.summary a { white-space: nowrap; } table.classindex { margin: 10px; white-space: nowrap; margin-left: 3%; margin-right: 3%; width: 94%; border: 0; border-spacing: 0; padding: 0; } div.ingroups { font-size: 8pt; width: 50%; text-align: left; } div.ingroups a { white-space: nowrap; } div.header { background-image:url('nav_h.png'); background-repeat:repeat-x; background-color: #F9FAFC; margin: 0px; border-bottom: 1px solid #C4CFE5; } div.headertitle { padding: 5px 5px 5px 10px; } dl { padding: 0 0 0 10px; } /* dl.note, dl.warning, dl.attention, dl.pre, dl.post, dl.invariant, dl.deprecated, dl.todo, dl.test, dl.bug */ dl.section { margin-left: 0px; padding-left: 0px; } dl.note { margin-left:-7px; padding-left: 3px; border-left:4px solid; border-color: #D0C000; } dl.warning, dl.attention { margin-left:-7px; padding-left: 3px; border-left:4px solid; border-color: #FF0000; } dl.pre, dl.post, dl.invariant { margin-left:-7px; padding-left: 3px; border-left:4px solid; border-color: #00D000; } dl.deprecated { margin-left:-7px; padding-left: 3px; border-left:4px solid; border-color: #505050; } dl.todo { margin-left:-7px; padding-left: 3px; border-left:4px solid; border-color: #00C0E0; } dl.test { margin-left:-7px; padding-left: 3px; border-left:4px solid; border-color: #3030E0; } dl.bug { margin-left:-7px; padding-left: 3px; border-left:4px solid; border-color: #C08050; } dl.section dd { margin-bottom: 6px; } #projectlogo { text-align: center; vertical-align: bottom; border-collapse: separate; } #projectlogo img { border: 0px none; } #projectalign { vertical-align: middle; } #projectname { font: 300% Tahoma, Arial,sans-serif; margin: 0px; padding: 2px 0px; } #projectbrief { font: 120% Tahoma, Arial,sans-serif; margin: 0px; padding: 0px; } #projectnumber { font: 50% Tahoma, Arial,sans-serif; margin: 0px; padding: 0px; } #titlearea { padding: 0px; margin: 0px; width: 100%; border-bottom: 1px solid #5373B4; } .image { text-align: center; } .dotgraph { text-align: center; } .mscgraph { text-align: center; } .plantumlgraph { text-align: center; } .diagraph { text-align: center; } .caption { font-weight: bold; } div.zoom { border: 1px solid #90A5CE; } dl.citelist { margin-bottom:50px; } dl.citelist dt { color:#334975; float:left; font-weight:bold; margin-right:10px; padding:5px; } dl.citelist dd { margin:2px 0; padding:5px 0; } div.toc { padding: 14px 25px; background-color: #F4F6FA; border: 1px solid #D8DFEE; border-radius: 7px 7px 7px 7px; float: right; height: auto; margin: 0 8px 10px 10px; width: 200px; } div.toc li { background: url("bdwn.png") no-repeat scroll 0 5px transparent; font: 10px/1.2 Verdana,DejaVu Sans,Geneva,sans-serif; margin-top: 5px; padding-left: 10px; padding-top: 2px; } div.toc h3 { font: bold 12px/1.2 Arial,FreeSans,sans-serif; color: #4665A2; border-bottom: 0 none; margin: 0; } div.toc ul { list-style: none outside none; border: medium none; padding: 0px; } div.toc li.level1 { margin-left: 0px; } div.toc li.level2 { margin-left: 15px; } div.toc li.level3 { margin-left: 30px; } div.toc li.level4 { margin-left: 45px; } .inherit_header { font-weight: bold; color: gray; cursor: pointer; -webkit-touch-callout: none; -webkit-user-select: none; -khtml-user-select: none; -moz-user-select: none; -ms-user-select: none; user-select: none; } .inherit_header td { padding: 6px 0px 2px 5px; } .inherit { display: none; } tr.heading h2 { margin-top: 12px; margin-bottom: 4px; } /* tooltip related style info */ .ttc { position: absolute; display: none; } #powerTip { cursor: default; white-space: nowrap; background-color: white; border: 1px solid gray; border-radius: 4px 4px 4px 4px; box-shadow: 1px 1px 7px gray; display: none; font-size: smaller; max-width: 80%; opacity: 0.9; padding: 1ex 1em 1em; position: absolute; z-index: 2147483647; } #powerTip div.ttdoc { color: grey; font-style: italic; } #powerTip div.ttname a { font-weight: bold; } #powerTip div.ttname { font-weight: bold; } #powerTip div.ttdeci { color: #006318; } #powerTip div { margin: 0px; padding: 0px; font: 12px/16px Roboto,sans-serif; } #powerTip:before, #powerTip:after { content: ""; position: absolute; margin: 0px; } #powerTip.n:after, #powerTip.n:before, #powerTip.s:after, #powerTip.s:before, #powerTip.w:after, #powerTip.w:before, #powerTip.e:after, #powerTip.e:before, #powerTip.ne:after, #powerTip.ne:before, #powerTip.se:after, #powerTip.se:before, #powerTip.nw:after, #powerTip.nw:before, #powerTip.sw:after, #powerTip.sw:before { border: solid transparent; content: " "; height: 0; width: 0; position: absolute; } #powerTip.n:after, #powerTip.s:after, #powerTip.w:after, #powerTip.e:after, #powerTip.nw:after, #powerTip.ne:after, #powerTip.sw:after, #powerTip.se:after { border-color: rgba(255, 255, 255, 0); } #powerTip.n:before, #powerTip.s:before, #powerTip.w:before, #powerTip.e:before, #powerTip.nw:before, #powerTip.ne:before, #powerTip.sw:before, #powerTip.se:before { border-color: rgba(128, 128, 128, 0); } #powerTip.n:after, #powerTip.n:before, #powerTip.ne:after, #powerTip.ne:before, #powerTip.nw:after, #powerTip.nw:before { top: 100%; } #powerTip.n:after, #powerTip.ne:after, #powerTip.nw:after { border-top-color: #ffffff; border-width: 10px; margin: 0px -10px; } #powerTip.n:before { border-top-color: #808080; border-width: 11px; margin: 0px -11px; } #powerTip.n:after, #powerTip.n:before { left: 50%; } #powerTip.nw:after, #powerTip.nw:before { right: 14px; } #powerTip.ne:after, #powerTip.ne:before { left: 14px; } #powerTip.s:after, #powerTip.s:before, #powerTip.se:after, #powerTip.se:before, #powerTip.sw:after, #powerTip.sw:before { bottom: 100%; } #powerTip.s:after, #powerTip.se:after, #powerTip.sw:after { border-bottom-color: #ffffff; border-width: 10px; margin: 0px -10px; } #powerTip.s:before, #powerTip.se:before, #powerTip.sw:before { border-bottom-color: #808080; border-width: 11px; margin: 0px -11px; } #powerTip.s:after, #powerTip.s:before { left: 50%; } #powerTip.sw:after, #powerTip.sw:before { right: 14px; } #powerTip.se:after, #powerTip.se:before { left: 14px; } #powerTip.e:after, #powerTip.e:before { left: 100%; } #powerTip.e:after { border-left-color: #ffffff; border-width: 10px; top: 50%; margin-top: -10px; } #powerTip.e:before { border-left-color: #808080; border-width: 11px; top: 50%; margin-top: -11px; } #powerTip.w:after, #powerTip.w:before { right: 100%; } #powerTip.w:after { border-right-color: #ffffff; border-width: 10px; top: 50%; margin-top: -10px; } #powerTip.w:before { border-right-color: #808080; border-width: 11px; top: 50%; margin-top: -11px; } @media print { #top { display: none; } #side-nav { display: none; } #nav-path { display: none; } body { overflow:visible; } h1, h2, h3, h4, h5, h6 { page-break-after: avoid; } .summary { display: none; } .memitem { page-break-inside: avoid; } #doc-content { margin-left:0 !important; height:auto !important; width:auto !important; overflow:inherit; display:inline; } } /* @group Markdown */ /* table.markdownTable { border-collapse:collapse; margin-top: 4px; margin-bottom: 4px; } table.markdownTable td, table.markdownTable th { border: 1px solid #2D4068; padding: 3px 7px 2px; } table.markdownTableHead tr { } table.markdownTableBodyLeft td, table.markdownTable th { border: 1px solid #2D4068; padding: 3px 7px 2px; } th.markdownTableHeadLeft th.markdownTableHeadRight th.markdownTableHeadCenter th.markdownTableHeadNone { background-color: #374F7F; color: #FFFFFF; font-size: 110%; padding-bottom: 4px; padding-top: 5px; } th.markdownTableHeadLeft { text-align: left } th.markdownTableHeadRight { text-align: right } th.markdownTableHeadCenter { text-align: center } */ table.markdownTable { border-collapse:collapse; margin-top: 4px; margin-bottom: 4px; } table.markdownTable td, table.markdownTable th { border: 1px solid #2D4068; padding: 3px 7px 2px; } table.markdownTable tr { } th.markdownTableHeadLeft, th.markdownTableHeadRight, th.markdownTableHeadCenter, th.markdownTableHeadNone { background-color: #374F7F; color: #FFFFFF; font-size: 110%; padding-bottom: 4px; padding-top: 5px; } th.markdownTableHeadLeft, td.markdownTableBodyLeft { text-align: left } th.markdownTableHeadRight, td.markdownTableBodyRight { text-align: right } th.markdownTableHeadCenter, td.markdownTableBodyCenter { text-align: center } /* @end */ ipe-7.2.13/build/doc/manual_26.html0000644000175000017500000001732513561570220016562 0ustar otfriedotfried Ipe Manual -- 5.5 Examples
5 Snapping5.4 Interaction of the snapping modes5.5 Examples

5.5 Examples

It takes some time and practice to feel fully at ease with the different snapping modes, especially angular snapping. Here are some examples showing what can be done with angular snapping.

Example 1:

We are given segments s1, s2, and e, and we want to add the dashed vertical extensions through p and q.

  • set F4 and F5 snapping on, go into line mode, and reset axis orientation with Ctrl+F2,
  • go near p, press F1 and F8 to set origin and to turn on angular snap.
  • go near p', click left, and extend segment to s1.
  • go near q, press F1 to reset origin, and draw second extension in the same way.

Example 2:

We are given the polygon C, and we want to draw the bracket b, indicating its vertical extension.

  • set F4 and F9 snapping on, go into line mode, reset axis orientation with Ctrl+F2, set snap angle to 90 degrees.
  • go near p, press F1 and F8 to set origin and angular snapping
  • go to x, click left, extend segment to y, click left
  • now we want to have z on a horizontal line through q: go near q, and press F1 and F8 to reset origin and to turn on angular snapping. Now both angular snapping modes are on, the snap lines intersect in z.
  • click left at z, goto x and press F1, goto t and finish bracket.

Example 3:

We want to draw the following "skyline". The only problem is to get q horizontally aligned with p.

  • draw the baseline using automatic angular snapping to get it horizontal.
  • place p with boundary snapping, draw the rectilinear curve up to r with automatic angular snapping in 90 degrees mode.
  • now go to p and press F1 and F8. The snap lines intersect in q. Click there, turn off angular snapping with Shift-F2, and finish curve. The last point is placed with boundary snapping.

Example 4:

We want to draw a line through p, tangent to C in q.

  • with vertex snapping on, put origin at p with F1
  • go to q and press F2. This puts the base direction from p to q.
  • set angular snapping with F8 and draw line.

Example 5:

We want to draw the following "windmill". The angle of the sector and between sectors should be 30 degrees.

  • set vertex snapping, snap angle to 30 degrees, reset axis orientation with Ctrl+F2,
  • with automatic angular snapping, draw a horizontal segment pq.
  • go to p, place origin and turn on angular snapping with F1 and F8,
  • duplicate segment with d, go to q and pick up q for rotation (with Alt and the right mouse button, or by switching to rotate mode). Rotate until segment falls on the next snap line.
  • turn off angular snapping with F8. Choose arc mode, variant "center & two points".
  • go to p, click for center. Go to q, click for first endpoint of arc, and at r for the second endpoint. Select all, and group.
  • turn angular snapping on again. Duplicate sector, and rotate by 60 degrees using angular snapping.
  • duplicate and rotate four more times.

Example 6:

We want to draw a c-oriented polygon, where the angles between successive segments are multiples of 30 degrees. The automatic angular snapping mode makes this pretty easy, but there is a little catch: How do we place the ultimate vertex such that it is at the same time properly aligned to the penultimate and to the very first vertex?

  • set snap angle to 30 degrees, and turn on automatic angular snapping.
  • click first vertex p and draw the polygon up to the penultimate vertex q.
  • it remains to place r such that it is in a legal position both with respect to q and p. The automatic angular snapping mode ensures the position with respect to q. We will use angular snapping from p to get it right: Go near p and turn on vertex snapping. Press F1 to place the origin at p and F8 to turn on angular snapping. Now it is trivial to place r.
ipe-7.2.13/build/doc/group__geo.html0000644000175000017500000002604713561570220017124 0ustar otfriedotfried Ipelib: Ipe Geometry
Ipelib
Ipe Geometry

Classes

class  ipe::Angle
 
class  ipe::Vector
 
class  ipe::Rect
 
class  ipe::Line
 
class  ipe::Segment
 
class  ipe::Linear
 
class  ipe::Matrix
 
class  ipe::Bezier
 
class  ipe::Arc
 
class  ipe::CurveSegment
 
class  ipe::Curve
 
class  ipe::SubPath
 
class  ipe::Ellipse
 
class  ipe::ClosedSpline
 
class  ipe::Shape
 

Functions

template<class T >
ipe::max (const T &lhs, const T &rhs)
 
template<class T >
ipe::min (const T &lhs, const T &rhs)
 
double ipe::abs (double val)
 

Detailed Description

Geometric primitives for Ipe.

The IpeGeo module provides a few classes for constant-size geometric primitives, such as vector, axis-aligned rectangles, lines, rays, line segments, etc.

Function Documentation

◆ max()

template<class T >
T ipe::max ( const T &  lhs,
const T &  rhs 
)
inline

Maximum of two values.

Referenced by ipe::PdfThumbnail::PdfThumbnail().

◆ min()

template<class T >
T ipe::min ( const T &  lhs,
const T &  rhs 
)
inline

Minimum of two values.

◆ abs()

double ipe::abs ( double  val)
inline

ipe-7.2.13/build/doc/classipe_1_1_tool.html0000644000175000017500000004453013561570220020274 0ustar otfriedotfried Ipelib: ipe::Tool Class Reference
Ipelib

#include <ipetoolbase.h>

Inherited by ipe::PanTool, ipe::SelectTool, and ipe::TransformTool.

Public Member Functions

virtual ~Tool ()
 
virtual void draw (Painter &painter) const =0
 
virtual void mouseButton (int button, bool press)
 
virtual void mouseMove ()
 
virtual bool key (String text, int modifiers)
 
virtual void snapVtx (const Vector &mouse, Vector &pos, double &bound, bool cp) const
 

Protected Member Functions

 Tool (CanvasBase *canvas)
 

Protected Attributes

CanvasBaseiCanvas
 

Detailed Description

Abstract base class for various canvas tools.

The Canvas doesn't know about the various modes for object creation, editing, and moving, but delegates the handling to a subclass of Tool.

Constructor & Destructor Documentation

◆ ~Tool()

Tool::~Tool ( )
virtual

Virtual destructor.

◆ Tool()

Tool::Tool ( CanvasBase canvas)
protected

Constructor.

Member Function Documentation

◆ draw()

virtual void ipe::Tool::draw ( Painter painter) const
pure virtual

◆ mouseButton()

void Tool::mouseButton ( int  button,
bool  press 
)
virtual

Called when a mouse button is pressed or released on the canvas.

button is 1, 2, or 3, with Shift/Ctrl/Alt/Meta modifiers added in (as defined in CanvasBase::TModifiers. press is true for button-down, and false for button-up.

Reimplemented in ipe::TransformTool, ipe::SelectTool, and ipe::PanTool.

Referenced by Canvas::drawRect(), ipe::Canvas::mouseButton(), and ipe::Canvas::tabletEvent().

◆ mouseMove()

void Tool::mouseMove ( )
virtual

Called when the mouse is moved on the canvas.

Reimplemented in ipe::TransformTool, ipe::SelectTool, and ipe::PanTool.

Referenced by Canvas::mouseMove(), ipe::Canvas::mouseMoveEvent(), and ipe::Canvas::tabletEvent().

◆ key()

bool Tool::key ( String  text,
int  modifiers 
)
virtual

Called when a key is pressed.

modifiers are as defined in CanvasBase::TModifiers.

Reimplemented in ipe::SelectTool.

Referenced by Canvas::key(), and ipe::Canvas::keyPressEvent().

◆ snapVtx()

void Tool::snapVtx ( const Vector mouse,
Vector pos,
double &  bound,
bool  cp 
) const
virtual

Snapping to vertices on object currently being drawn.

Member Data Documentation

◆ iCanvas


The documentation for this class was generated from the following files:
  • ipetoolbase.h
  • ipetoolbase.cpp

ipe-7.2.13/build/doc/classipe_1_1_object-members.html0000644000175000017500000003436513561570220022222 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Object Member List

This is the complete list of members for ipe::Object, including all inherited members.

accept(Visitor &visitor) const =0ipe::Objectpure virtual
addToBBox(Rect &box, const Matrix &m, bool cp) const =0ipe::Objectpure virtual
asGroup()ipe::Objectvirtual
asGroup() constipe::Objectvirtual
asImage()ipe::Objectvirtual
asPath()ipe::Objectvirtual
asReference()ipe::Objectvirtual
asText()ipe::Objectvirtual
checkStyle(const Cascade *sheet, AttributeSeq &seq) constipe::Objectvirtual
checkSymbol(Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq)ipe::Objectprotectedstatic
clone() const =0ipe::Objectpure virtual
distance(const Vector &v, const Matrix &m, double bound) const =0ipe::Objectpure virtual
draw(Painter &painter) const =0ipe::Objectpure virtual
drawSimple(Painter &painter) const =0ipe::Objectpure virtual
EGroup enum valueipe::Object
EImage enum valueipe::Object
EPath enum valueipe::Object
EReference enum valueipe::Object
EText enum valueipe::Object
getAttribute(Property prop) const noexceptipe::Objectvirtual
iMatrixipe::Objectprotected
iPinnedipe::Objectprotected
iTransformationsipe::Objectprotected
matrix() constipe::Objectinline
Object()ipe::Objectexplicitprotected
Object(const AllAttributes &attr)ipe::Objectexplicitprotected
Object(const Object &rhs)ipe::Objectprotected
Object(const XmlAttributes &attr)ipe::Objectexplicitprotected
pinned() constipe::Objectvirtual
saveAsXml(Stream &stream, String layer) const =0ipe::Objectpure virtual
saveAttributesAsXml(Stream &stream, String layer) constipe::Objectprotected
setAttribute(Property prop, Attribute value)ipe::Objectvirtual
setMatrix(const Matrix &matrix)ipe::Object
setPinned(TPinned pin)ipe::Object
setTransformations(TTransformations trans)ipe::Object
snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Objectvirtual
snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Objectvirtual
snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Objectvirtual
transformations() constipe::Objectinline
Type enum nameipe::Object
type() const =0ipe::Objectpure virtual
~Object()=0ipe::Objectpure virtual

ipe-7.2.13/build/doc/classipe_1_1_bezier.html0000644000175000017500000011506613561570220020602 0ustar otfriedotfried Ipelib: ipe::Bezier Class Reference
Ipelib

#include <ipegeo.h>

Public Member Functions

 Bezier ()
 
 Bezier (const Vector &p0, const Vector &p1, const Vector &p2, const Vector &p3)
 
Vector point (double t) const
 
Vector tangent (double t) const
 
double distance (const Vector &v, double bound)
 
bool straight (double precision) const
 
void subdivide (Bezier &l, Bezier &r) const
 
void approximate (double precision, std::vector< Vector > &result) const
 
Rect bbox () const
 
bool snap (const Vector &v, double &t, Vector &pos, double &bound) const
 
void intersect (const Line &l, std::vector< Vector > &result) const
 
void intersect (const Segment &l, std::vector< Vector > &result) const
 
void intersect (const Bezier &b, std::vector< Vector > &result) const
 

Static Public Member Functions

static Bezier quadBezier (const Vector &p0, const Vector &p1, const Vector &p2)
 
static void oldSpline (int n, const Vector *v, std::vector< Bezier > &result)
 
static void spline (int n, const Vector *v, std::vector< Bezier > &result)
 
static void closedSpline (int n, const Vector *v, std::vector< Bezier > &result)
 

Public Attributes

Vector iV [4]
 

Detailed Description

A cubic Bezier spline.

Constructor & Destructor Documentation

◆ Bezier() [1/2]

ipe::Bezier::Bezier ( )
inline

Default constructor, uninitialized curve.

◆ Bezier() [2/2]

ipe::Bezier::Bezier ( const Vector p0,
const Vector p1,
const Vector p2,
const Vector p3 
)
inline

Constructor with four control points.

Member Function Documentation

◆ point()

Vector Bezier::point ( double  t) const

Return point on curve with parameter t (from 0.0 to 1.0).

◆ tangent()

Vector Bezier::tangent ( double  t) const

Return tangent direction of curve at parameter t (from 0.0 to 1.0).

The returned vector is not normalized.

Referenced by ipe::Snap::setEdge().

◆ distance()

double Bezier::distance ( const Vector v,
double  bound 
)

Return distance to Bezier spline.

But may just return bound if actual distance is larger. The Bezier spline is approximated to a precision of 1.0, and the distance to the approximation is returned.

References ipe::Rect::addPoint(), and ipe::Rect::certainClearance().

◆ straight()

bool Bezier::straight ( double  precision) const

Returns true if the Bezier curve is nearly identical to the line segment iV[0]..iV[3].

References ipe::Line::distance(), and ipe::Line::through().

Referenced by ipe::Arc::intersect(), and snap().

◆ subdivide()

void Bezier::subdivide ( Bezier l,
Bezier r 
) const

Subdivide this Bezier curve in the middle.

References iV.

Referenced by ipe::Arc::intersect(), and snap().

◆ approximate()

void Bezier::approximate ( double  precision,
std::vector< Vector > &  result 
) const

Approximate by a polygonal chain.

result must be empty when calling this.

References approximate().

Referenced by approximate().

◆ bbox()

Rect Bezier::bbox ( ) const

Return a tight bounding box (accurate to within 0.5).

References ipe::Rect::addPoint(), ipe::Rect::bottomLeft(), and ipe::Rect::topRight().

Referenced by ipe::BBoxPainter::doCurveTo().

◆ snap()

bool Bezier::snap ( const Vector v,
double &  t,
Vector pos,
double &  bound 
) const

Find (approximately) nearest point on Bezier spline.

Find point on spline nearest to v, but only if it is closer than bound. If a point is found, sets t to the parameter value and pos to the actual point, and returns true.

References ipe::Rect::addPoint(), ipe::Rect::certainClearance(), ipe::Rect::intersects(), ipe::Segment::intersects(), iV, ipe::Segment::project(), ipe::Vector::snap(), snap(), straight(), and subdivide().

Referenced by ipe::Snap::setEdge(), and snap().

◆ quadBezier()

Bezier Bezier::quadBezier ( const Vector p0,
const Vector p1,
const Vector p2 
)
static

Convert a quadratic Bezier-spline to a cubic one.

The quadratic Bezier-spline with control points p0, p1, p2 is identical to the cubic Bezier-spline with control points q0 = p0, q1 = (2p1 + p0)/3, q2 = (2p1 + p2)/3, q3 = p2.

◆ oldSpline()

void Bezier::oldSpline ( int  n,
const Vector v,
std::vector< Bezier > &  result 
)
static

Convert an old-style Ipe B-spline to a series of Bezier splines.

For some reason lost in the mist of time, this was the definition of splines in Ipe for many years. It doesn't use knots. The first and last control point are simply given multiplicity 3.

Bezier splines are appended to result.

Referenced by ipe::CurveSegment::beziers().

◆ spline()

void Bezier::spline ( int  n,
const Vector v,
std::vector< Bezier > &  result 
)
static

Convert a clamped uniform B-spline to a series of Bezier splines.

See Thomas Sederberg, Computer-Aided Geometric Design, Chapter 6.

In polar coordinates, a control point is defined by three knots, so n control points need n + 2 knots. To clamp the spline to the first and last control point, the first and last knot are repeated three times. This leads to k knot intervals and the knot sequence [0, 0, 0, 1, 2, 3, 4, 5, 6, ..., k-2, k-1, k, k, k] There are k + 5 = n + 2 knots in this sequence, so k = n-3 is the number of knot intervals and therefore the number of output Bezier curves.

If n = 4, the knot sequence is [0, 0, 0, 1, 1, 1] and the result is simply the Bezier curve on the four control points.

When n in {2, 3}, returns a single Bezier curve that is a segment or quadratic Bezier spline. This is different from the behaviour of the "old" Ipe splines.

Bezier splines are appended to result.

Referenced by ipe::CurveSegment::beziers().

◆ closedSpline()

void Bezier::closedSpline ( int  n,
const Vector v,
std::vector< Bezier > &  result 
)
static

Convert a closed uniform cubic B-spline to a series of Bezier splines.

Bezier splines are appended to result.

Referenced by ipe::ClosedSpline::beziers().

◆ intersect() [1/3]

void Bezier::intersect ( const Line l,
std::vector< Vector > &  result 
) const

Compute intersection points of Bezier with Line.

References intersect(), ipe::Segment::intersects(), and ipe::Line::side().

Referenced by intersect().

◆ intersect() [2/3]

void Bezier::intersect ( const Segment l,
std::vector< Vector > &  result 
) const

Compute intersection points of Bezier with Segment.

References ipe::Segment::iP, and ipe::Segment::iQ.

◆ intersect() [3/3]

void Bezier::intersect ( const Bezier b,
std::vector< Vector > &  result 
) const

Compute intersection points of Bezier with Bezier.

Member Data Documentation

◆ iV


The documentation for this class was generated from the following files:
  • ipegeo.h
  • ipegeo.cpp

ipe-7.2.13/build/doc/manual_14.html0000644000175000017500000001032013561570220016543 0ustar otfriedotfried Ipe Manual -- 3.11 Mouse shortcuts
3 General Concepts3.10 Layers3.11 Mouse shortcuts

3.11 Mouse shortcuts

For the beginner, choosing a selection or transformation mode and working with the left mouse button is easiest. Frequent Ipe users don't mind to remember the following shortcuts, as they allow you to perform selections and transformations without leaving the current mode:

Left Mouse Right mouse
Plain (*) context menu
Shift (*) pan
Ctrl select stretch
Ctrl+Shift select non-destructively scale
Alt translate rotate
Alt+Shift translate horizontal/vertical rotate

The fields marked (*) depend on the current mode.

The middle mouse button always pans the canvas. The right mouse button brings up the object context menu.

If you have to use Ipe with a two-button mouse, where you would normally use the middle mouse button (for instance, to move a vertex when editing a path object), you can hold the Shift-key and use the right mouse button.

If you are not happy with these shortcuts, they can be changed easily.

ipe-7.2.13/build/doc/manual_50.html0000644000175000017500000001756413561570220016564 0ustar otfriedotfried Ipe Manual -- 10 Using Ipe figures in Latex
11 The command line programsTop9 The Ipe file format10 Using Ipe figures in Latex

10 Using Ipe figures in Latex

If—like many Latex users nowadays—you are a user of Pdflatex you can include Ipe figures in PDF format in your Latex documents directly.

The standard way of including PDF figures is using the graphicx package. If you are not familiar with it, here is a quick overview. In the preamble of your document, add the declaration:

  \usepackage{graphicx}
One useful attribute to this declaration is draft, which stops LaTeX from actually including the figures—instead, a rectangle with the figure filename is shown:
  \usepackage[draft]{graphicx}

To include the figure "figure1.pdf, you use the command:

  \includegraphics{figs/figure1}
Note that it is common not to specify the file extension ".pdf". The command \includegraphics has various options to scale and rotate the figure. For instance, to scale the same figure to 50%, use:
  \includegraphics[scale=0.5]{figs/figure1}
To scale such that the width of the figure becomes 5 cm:
  \includegraphics[width=5cm]{figs/figure1}
Instead, one can specify the required height with height.

Here is an example that scales a figure to 200% and rotates it by 45 degrees counter-clockwise. Note that the scale argument should be given before the angle argument.

  \includegraphics[scale=2,angle=45]{figs/figure1}

Let's stress once again that these commands are the standard commands for including PDF figures in a LaTeX document. Ipe files neither require nor support any special treatment. If you want to know more about the LaTeX packages for including graphics and producing colour, check the grfguide.tex document that is probably somewhere in your TeX installation.


There is a slight complication here: Each page of a PDF document can carry several "bounding boxes", such as the MediaBox (which indicates the paper size), the CropBox (which indicates how the paper will by cut), or the ArtBox (which indicates the extent of the actual contents of the page). Ipe automatically saves, for each page, the paper size in the MediaBox, and a bounding box for the drawing in the ArtBox. Ipe also puts the bounding box in the CropBox unless this has been turned off by the stylesheet.

Now, when including a PDF figure, Pdflatex will (by default) first look at the CropBox, and, if that is not set, fall back on the MediaBox. It does not inspect the ArtBox, and so it is important that you use the correct stylesheet for the kind of figure you are making—with cropping for figures to be included, without cropping for presentations (as otherwise Acrobat Reader will not display full pages—Acrobat Reader actually crops each page to the CropBox).

If you have a recent version of Pdflatex (1.40 or higher), you can actually ask Pdflatex to inspect the ArtBox by saying \pdfpagebox5 in your Latex file's preamble.


If you are still using the "original" Latex, which compiles documents to DVI format, you need figures in Encapsulated Postscript (EPS) format (the "Encapsulated" means that there is only a single Postscript page and that it contains a bounding box of the figure). Some publishers may also require that you submit figures in EPS format, rather than in PDF.

Ipe allows you to export your figure in EPS format, either from the Ipe program (File menu, Export as EPS), or by using the command line tool iperender with the -eps option. Remember to keep a copy of your original Ipe figure! Ipe cannot read the exported EPS figure, you will not be able to edit them any further.

Including EPS figures works exactly like for PDF figures, using \includegraphics. In fact you can save all your figures in both EPS and PDF format, so that you can run both Latex and Pdflatex on your document—when including figures, Latex will look for the EPS variant, while Pdflatex will look for the PDF variant. (Here it comes in handy that you didn't specify the file extension in the \includegraphics command.)

It would be cumbersome to have to export to EPS every time you modify and save an Ipe figure in PDF format. What you should do instead is to write a shell script or batch file that calls iperender to export to EPS.


On the other hand, if you only use Pdflatex, you might opt to exploit a feature of Pdflatex: You can keep all the figures for a document in a single, multi-page Ipe document, with one figure per page. You can then include the figures one by one into your document by using the page argument of \includegraphics.

For example, to include page 3 from the PDF file "figures.pdf" containing several figures, you could use

  \includegraphics[page=3]{figures}

It's a bit annoying that one has to refer to the page by its page number. Ipe comes with a useful script that will allow you to use symbolic names instead.

ipe-7.2.13/build/doc/functions_p.html0000644000175000017500000003200413561570220017314 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- p -


ipe-7.2.13/build/doc/structipe_1_1_style_sheet_1_1_page_number_style-members.html0000644000175000017500000001040613561570220027735 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::StyleSheet::PageNumberStyle Member List

ipe-7.2.13/build/doc/structipe_1_1_gradient.html0000644000175000017500000003243413561570220021333 0ustar otfriedotfried Ipelib: ipe::Gradient Struct Reference
Ipelib

#include <ipeattributes.h>

Classes

struct  Stop
 

Public Types

enum  TType { EAxial = 2, ERadial = 3 }
 

Public Attributes

TType iType
 
Vector iV [2]
 
double iRadius [2]
 
bool iExtend
 
Matrix iMatrix
 
std::vector< StopiStops
 

Detailed Description

A gradient pattern.

Member Enumeration Documentation

◆ TType

There are two types of gradients, along an axis or between two circles.

Enumerator
EAxial 
ERadial 

Member Data Documentation

◆ iType

TType ipe::Gradient::iType

◆ iV

Vector ipe::Gradient::iV[2]

The coordinates of the axis endpoints, or the two circle centers.

Referenced by ipe::CairoPainter::doDrawPath(), ipe::PdfPainter::doDrawSymbol(), ipe::ImlParser::parseStyle(), and ipe::StyleSheet::saveAsXml().

◆ iRadius

double ipe::Gradient::iRadius[2]

The radii of the two circles (not used for axial gradients).

Referenced by ipe::CairoPainter::doDrawPath(), ipe::PdfPainter::doDrawSymbol(), ipe::ImlParser::parseStyle(), and ipe::StyleSheet::saveAsXml().

◆ iExtend

bool ipe::Gradient::iExtend

Whether to extend the gradient beyond the endpoints.

Referenced by ipe::CairoPainter::doDrawPath(), ipe::PdfPainter::doDrawSymbol(), ipe::ImlParser::parseStyle(), and ipe::StyleSheet::saveAsXml().

◆ iMatrix

◆ iStops


The documentation for this struct was generated from the following file:
  • ipeattributes.h

ipe-7.2.13/build/doc/dir_d44c64559bbebec7f509842c48db8b23.html0000644000175000017500000002142613561570220022304 0ustar otfriedotfried Ipelib: include Directory Reference
Ipelib
include Directory Reference

Files

file  ipeattributes.h
 
file  ipebase.h
 
file  ipebitmap.h
 
file  ipedoc.h
 
file  ipefactory.h
 
file  ipegeo.h
 
file  ipegroup.h
 
file  ipeimage.h
 
file  ipeiml.h
 
file  ipelatex.h
 
file  ipelet.h
 
file  ipelib.h
 
file  ipeobject.h
 
file  ipeosx.h
 
file  ipepage.h
 
file  ipepainter.h
 
file  ipepath.h
 
file  ipepdfparser.h
 
file  ipepdfwriter.h
 
file  ipepswriter.h
 
file  ipereference.h
 
file  iperesources.h
 
file  ipeshape.h
 
file  ipesnap.h
 
file  ipestyle.h
 
file  ipetext.h
 
file  ipetoolbase.h
 
file  ipeutils.h
 
file  ipexml.h
 

ipe-7.2.13/build/doc/classipe_1_1_bitmap_finder-members.html0000644000175000017500000001032013561570220023540 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::BitmapFinder Member List

This is the complete list of members for ipe::BitmapFinder, including all inherited members.

iBitmapsipe::BitmapFinder
scanPage(const Page *page)ipe::BitmapFinder
visitGroup(const Group *obj)ipe::BitmapFindervirtual
visitImage(const Image *obj)ipe::BitmapFindervirtual
visitPath(const Path *obj)ipe::Visitorvirtual
visitReference(const Reference *obj)ipe::Visitorvirtual
visitText(const Text *obj)ipe::Visitorvirtual
~Visitor()ipe::Visitorvirtual

ipe-7.2.13/build/doc/structipe_1_1_pdf_resources_1_1_s_page_number-members.html0000644000175000017500000000574013561570220027357 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PdfResources::SPageNumber Member List

ipe-7.2.13/build/doc/classipe_1_1_arc.html0000644000175000017500000010344013561570220020060 0ustar otfriedotfried Ipelib: ipe::Arc Class Reference
Ipelib

#include <ipegeo.h>

Public Member Functions

 Arc ()
 
 Arc (const Matrix &m, Angle alpha, Angle beta)
 
 Arc (const Matrix &m)
 
 Arc (const Matrix &m0, const Vector &begp, const Vector &endp)
 
bool isEllipse () const
 
double distance (const Vector &v, double bound) const
 
double distance (const Vector &v, double bound, Vector &pos, Angle &angle) const
 
Rect bbox () const
 
Vector beginp () const
 
Vector endp () const
 
void intersect (const Line &l, std::vector< Vector > &result) const
 
void intersect (const Segment &s, std::vector< Vector > &result) const
 
void intersect (const Arc &a, std::vector< Vector > &result) const
 
void intersect (const Bezier &b, std::vector< Vector > &result) const
 

Public Attributes

Matrix iM
 
Angle iAlpha
 
Angle iBeta
 

Detailed Description

An arc of an ellipse.

The ellipse is represented using the matrix that transforms the unit circle x^2 + y^2 = 1 to the desired ellipse. The arc coordinate system is the coordinate system of this unit circle.

A full ellipse is described by iAlpha = 0, iBeta = IpeTwoPi.

An elliptic arc is the image of the circular arc from iAlpha to iBeta (in increasing angle in arc coordinate system).

Constructor & Destructor Documentation

◆ Arc() [1/4]

ipe::Arc::Arc ( )
inline

Construct unit circle.

Referenced by ipe::Matrix::operator*().

◆ Arc() [2/4]

ipe::Arc::Arc ( const Matrix m,
Angle  alpha,
Angle  beta 
)
inline

Construct with given parameters.

◆ Arc() [3/4]

ipe::Arc::Arc ( const Matrix m)
inline

Construct an ellipse.

◆ Arc() [4/4]

Arc::Arc ( const Matrix m,
const Vector begp,
const Vector endp 
)

Construct arc for ellipse defined by m, from begp to endp.

This assumes that m has been correctly computed such that begb and endp already lie on the ellipse.

References ipe::Matrix::inverse().

Member Function Documentation

◆ isEllipse()

bool ipe::Arc::isEllipse ( ) const
inline

Is this an entire ellipse?

References iAlpha, and iBeta.

Referenced by ipe::CairoPainter::doDrawArc(), and ipe::Painter::doDrawArc().

◆ distance() [1/2]

double Arc::distance ( const Vector v,
double  bound 
) const

This doesn't really compute the distance, but a reasonable approximation.

Referenced by ipe::Ellipse::distance(), ipe::Snap::setEdge(), ipe::CurveSegment::snapBnd(), and ipe::Ellipse::snapBnd().

◆ distance() [2/2]

double Arc::distance ( const Vector v,
double  bound,
Vector pos,
Angle angle 
) const

Like distance(), but sets pos to point on arc and angle to its angle in arc coordinates. angle and pos are not modified if result is larger than bound.

References ipe::Vector::angle(), ipe::Matrix::inverse(), ipe::Angle::liesBetween(), and ipe::Vector::normalized().

◆ bbox()

Rect Arc::bbox ( ) const

Return a tight bounding box.

References ipe::Rect::addPoint(), ipe::Linear::inverse(), and ipe::Angle::liesBetween().

Referenced by intersect().

◆ beginp()

Vector ipe::Arc::beginp ( ) const
inline

Return begin point of arc.

References iAlpha, and iM.

Referenced by ipe::Path::drawArrow(), and intersect().

◆ endp()

Vector ipe::Arc::endp ( ) const
inline

Return end point of arc.

References iBeta, and iM.

Referenced by ipe::Path::drawArrow(), and intersect().

◆ intersect() [1/4]

void Arc::intersect ( const Line l,
std::vector< Vector > &  result 
) const

Compute intersection points of Arc with Line.

References ipe::Vector::angle(), ipe::Line::dir(), ipe::Line::iP, ipe::Angle::liesBetween(), and ipe::Matrix::linear().

Referenced by intersect().

◆ intersect() [2/4]

void Arc::intersect ( const Segment s,
std::vector< Vector > &  result 
) const

Compute intersection points of Arc with Segment.

References ipe::Segment::iP, ipe::Segment::iQ, ipe::Segment::line(), and ipe::size().

◆ intersect() [3/4]

void Arc::intersect ( const Arc a,
std::vector< Vector > &  result 
) const

Compute intersection points of Arc with Arc.

References bbox(), beginp(), endp(), and intersect().

◆ intersect() [4/4]

void Arc::intersect ( const Bezier b,
std::vector< Vector > &  result 
) const

Member Data Documentation

◆ iM

◆ iAlpha

◆ iBeta


The documentation for this class was generated from the following files:
  • ipegeo.h
  • ipegeo.cpp

ipe-7.2.13/build/doc/manual_17.html0000644000175000017500000001716013561570220016557 0ustar otfriedotfried Ipe Manual -- 4.2 Text objects
4.3 Image objects4 Object types4.1 Path objects4.2 Text objects

4.2 Text objects

Text objects come in two flavors: simple labels, and minipages. There are two variants of these: titles (a label that serves as the title of the page), and textbox (a minipage that spans the entire width of the page).

The position you have to click to start creating a label object is normally the leftmost baseline point (but this can be changed by changing the object's horizontal and vertical alignment). A popup window appears where you can enter Latex source code.

A minipage object is different from a simple text object in that its width is part of its definition. When you create a minipage object, you first have to drag out a horizontal segment for the minipage. This is used as the top edge of the minipage—it will extend downwards as far as necessary to accomodate all the text. Minipages are formatted using, not surprisingly, Latex's minipage environment. Latex tries to fill the given bounding box as nicely as possible. It is possible to include center environments, lemmas, and much more in minipages.

To create a textbox object, simply press F10. Ipe automatically places the object so that it spans the entire width of the page (the layout settings in the stylesheet determine how much space is left on the sides), and places it vertically underneath the textboxes already on the page. This is particularly convenient for creating presentations with a lot of text, or with items that appear one by one.

Title objects are managed by Ipe automatically. They are special labels that are created using Edit title & sections in the Page menu. Their color, size, alignment, and position on the page is determined by the stylesheet.

You can use any LaTeX-command that is legal inside a \makebox (for labels) or inside a minipage (for minipages). You cannot use commands that involve a non-linear translation into PDF, such as commands to generate hyperlinks or to include external images.

You can use color in your text objects, using the \textcolor command, like this:

This is in black. \textcolor{red}{This is in red.} This is in black.
All the symbolic colors of your current stylesheet are also available as arguments to \textcolor. You can also use absolute colors, for instance:
This is in black. \textcolor[rgb]{1,1,0}{This is in yellow.} This is in black.

If you need LaTeX-commands that are defined in additional LaTeX packages, you can include (\usepackage) those in the LaTeX preamble, which can be set in Document properties in the Edit menu.

Note that the |xcolor|-package is loaded automatically by Ipe, without any options. If you need to use package options of the |xcolor|-package, place the command

\ipedefinecolors{options}
in your preamble. It has to go before the first use of |xcolor| commands in your document.

After you have created or edited a text object, the Ipe screen display will show the beginning of the Latex source. You can select Run Latex from the File menu to create the PDF/Postscript representation of the object. This converts all the text objects in your document at once, and Ipe will display a correct rendition of the text afterwards.

If the Latex conversion process results in errors, Ipe will automatically show you the log file created by the Latex run. If you cannot figure out the problem, look in the section on troubleshooting.

You can use Unicode text, such as accented characters, Greek, Cyrillic, Chinese, Japanese, or Korean, in your text objects, once you have set up the necessary style files and fonts.

When Ipe computes the bounding box for a piece of text, it relies entirely on the dimensions that Latex provides. Sometimes glyphs are larger than their "official" dimensions, and as a result this bounding box is too tight. In the following figure, "A" and "G" stick out of the golden rectangle (the bounding box computed by Ipe based on the Latex dimensions) at the top, "y" sticks out at the bottom:

When you experience that text in your figures is clipped, you may have to enlarge the figure's bounding box using a "BBOX" layer.

The opposite problem can occur when you use transformed text. Ipe computes the bounding box for the transformed text by transforming the bounding box for the original text, and the result can be too large:

If this is a problem, you can put the text object inside a group and set a clipping path for the group.
ipe-7.2.13/build/doc/classipe_1_1_text-members.html0000644000175000017500000005772513561570220021745 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Text Member List

This is the complete list of members for ipe::Text, including all inherited members.

accept(Visitor &visitor) constipe::Textvirtual
addToBBox(Rect &box, const Matrix &m, bool) constipe::Textvirtual
align() constipe::Text
asGroup()ipe::Objectvirtual
asGroup() constipe::Objectvirtual
asImage()ipe::Objectvirtual
asPath()ipe::Objectvirtual
asReference()ipe::Objectvirtual
asText()ipe::Textvirtual
checkStyle(const Cascade *sheet, AttributeSeq &seq) constipe::Textvirtual
checkSymbol(Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq)ipe::Objectprotectedstatic
clone() constipe::Textvirtual
depth() constipe::Textinline
distance(const Vector &v, const Matrix &m, double bound) constipe::Textvirtual
draw(Painter &painter) constipe::Textvirtual
drawSimple(Painter &painter) constipe::Textvirtual
EGroup enum valueipe::Object
EImage enum valueipe::Object
ELabel enum valueipe::Text
EMinipage enum valueipe::Text
EPath enum valueipe::Object
EReference enum valueipe::Object
EText enum valueipe::Object
getAttribute(Property prop) const noexceptipe::Textvirtual
getXForm() constipe::Textinline
height() constipe::Textinline
horizontalAlignment() constipe::Textinline
iMatrixipe::Objectprotected
iPinnedipe::Objectprotected
isMinipage() constipe::Textinline
iTransformationsipe::Objectprotected
makeHAlign(String str, THorizontalAlignment def)ipe::Textstatic
makeVAlign(String str, TVerticalAlignment def)ipe::Textstatic
matrix() constipe::Objectinline
Object()ipe::Objectexplicitprotected
Object(const AllAttributes &attr)ipe::Objectexplicitprotected
Object(const Object &rhs)ipe::Objectprotected
Object(const XmlAttributes &attr)ipe::Objectexplicitprotected
opacity() constipe::Textinline
pinned() constipe::Objectvirtual
position() constipe::Textinline
saveAlignment(Stream &stream, THorizontalAlignment h, TVerticalAlignment v)ipe::Textstatic
saveAsXml(Stream &stream, String layer) constipe::Textvirtual
saveAttributesAsXml(Stream &stream, String layer) constipe::Objectprotected
setAttribute(Property prop, Attribute value)ipe::Textvirtual
setHorizontalAlignment(THorizontalAlignment align)ipe::Text
setMatrix(const Matrix &matrix)ipe::Object
setOpacity(Attribute opaq)ipe::Text
setPinned(TPinned pin)ipe::Object
setSize(Attribute size)ipe::Text
setStroke(Attribute stroke)ipe::Text
setStyle(Attribute style)ipe::Text
setText(String text)ipe::Text
setTextType(TextType type)ipe::Text
setTransformations(TTransformations trans)ipe::Object
setVerticalAlignment(TVerticalAlignment align)ipe::Text
setWidth(double width)ipe::Text
setXForm(XForm *xform) constipe::Text
size() constipe::Textinline
snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Objectvirtual
snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Textvirtual
snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Objectvirtual
stroke() constipe::Textinline
style() constipe::Textinline
text() constipe::Textinline
Text()ipe::Textexplicit
Text(const AllAttributes &attr, String data, const Vector &pos, TextType type, double width=10.0)ipe::Textexplicit
Text(const Text &rhs)ipe::Text
Text(const XmlAttributes &attr, String data)ipe::Textexplicit
textType() constipe::Text
TextType enum nameipe::Text
totalHeight() constipe::Textinline
transformations() constipe::Objectinline
type() constipe::Textvirtual
Type enum nameipe::Object
verticalAlignment() constipe::Textinline
width() constipe::Textinline
~Object()=0ipe::Objectpure virtual
~Text()ipe::Text

ipe-7.2.13/build/doc/classipe_1_1_ipelet_helper.html0000644000175000017500000003136313561570220022140 0ustar otfriedotfried Ipelib: ipe::IpeletHelper Class Reference
Ipelib
ipe::IpeletHelper Class Referenceabstract

#include <ipelet.h>

Public Types

enum  {
  EOkButton, EOkCancelButtons, EYesNoCancelButtons, EDiscardCancelButtons,
  ESaveDiscardCancelButtons
}
 

Public Member Functions

virtual ~IpeletHelper ()=0
 
virtual void message (const char *msg)=0
 
virtual int messageBox (const char *text, const char *details, int buttons)=0
 
virtual bool getString (const char *prompt, String &str)=0
 
virtual String getParameter (const char *key)=0
 

Detailed Description

Service provider for Ipelets.

C++ Ipelets can ask Ipe to perform various services and request information using this class.

Member Enumeration Documentation

◆ anonymous enum

anonymous enum
Enumerator
EOkButton 
EOkCancelButtons 
EYesNoCancelButtons 
EDiscardCancelButtons 
ESaveDiscardCancelButtons 

Constructor & Destructor Documentation

◆ ~IpeletHelper()

IpeletHelper::~IpeletHelper ( )
pure virtual

Pure virtual destructor.

Referenced by ipe::InflateSource::getChar().

Member Function Documentation

◆ message()

virtual void ipe::IpeletHelper::message ( const char *  msg)
pure virtual

Show a message in the status bar.

◆ messageBox()

virtual int ipe::IpeletHelper::messageBox ( const char *  text,
const char *  details,
int  buttons 
)
pure virtual

Pop up a modal message box.

The details can be null.

Choose one of EOkButton, EOkCancelButtons, EYesNoCancelButtons, EDiscardCancelButtons, ESaveDiscardCancelButtons for buttons.

Returns 1 for Ok or Yes, 0 for No, -1 for Cancel.

◆ getString()

virtual bool ipe::IpeletHelper::getString ( const char *  prompt,
String str 
)
pure virtual

Pop up a modal dialog asking the user to enter a string. Returns true if the user didn't cancel the dialog.

◆ getParameter()

virtual String ipe::IpeletHelper::getParameter ( const char *  key)
pure virtual

Retrieve a parameter value from a table in the Lua wrapper code. If no table has been passed, or the key is not in the table, or its value is not a string or a number, then an empty string is returned.


The documentation for this class was generated from the following files:
  • ipelet.h
  • ipeutils.cpp

ipe-7.2.13/build/doc/classipe_1_1_tell_stream-members.html0000644000175000017500000001336713561570220023266 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::TellStream Member List

This is the complete list of members for ipe::TellStream, including all inherited members.

close()ipe::Streamvirtual
operator<<(char ch)ipe::Streaminline
operator<<(const String &s)ipe::Streaminline
operator<<(const char *s)ipe::Streaminline
operator<<(int i)ipe::Stream
operator<<(double d)ipe::Stream
putChar(char ch)=0ipe::Streampure virtual
putCString(const char *s)ipe::Streamvirtual
putHexByte(char b)ipe::Stream
putRaw(const char *data, int size)ipe::Streamvirtual
putString(String s)ipe::Streamvirtual
putXmlString(String s)ipe::Stream
tell() const =0ipe::TellStreampure virtual
~Stream()ipe::Streamvirtual

ipe-7.2.13/build/doc/structipe_1_1_symbol.html0000644000175000017500000003774613561570220021056 0ustar otfriedotfried Ipelib: ipe::Symbol Class Reference
Ipelib

#include <ipestyle.h>

Public Member Functions

 Symbol ()
 
 Symbol (Object *object)
 
 Symbol (const Symbol &rhs)
 
Symboloperator= (const Symbol &rhs)
 
 ~Symbol ()
 

Public Attributes

bool iXForm
 
TTransformations iTransformations
 
ObjectiObject
 
std::vector< VectoriSnap
 

Detailed Description

A symbol is a named object defined in an ipe::StyleSheet.

Constructor & Destructor Documentation

◆ Symbol() [1/3]

Symbol::Symbol ( )

Default constructor.

◆ Symbol() [2/3]

Symbol::Symbol ( Object object)

Create symbol for object (takes ownership).

References ipe::ETransformationsAffine, iObject, iTransformations, and iXForm.

◆ Symbol() [3/3]

Symbol::Symbol ( const Symbol rhs)

Copy constructor.

References ipe::Object::clone(), iObject, iSnap, iTransformations, and iXForm.

◆ ~Symbol()

Symbol::~Symbol ( )

Destructor.

References iObject.

Member Function Documentation

◆ operator=()

Symbol & Symbol::operator= ( const Symbol rhs)

Assignment operator.

References ipe::Object::clone(), iObject, iSnap, iTransformations, and iXForm.

Member Data Documentation

◆ iXForm

bool ipe::Symbol::iXForm

◆ iTransformations

◆ iObject

◆ iSnap


The documentation for this class was generated from the following files:
  • ipestyle.h
  • ipestyle.cpp

ipe-7.2.13/build/doc/classipe_1_1_repository.html0000644000175000017500000002261613561570220021537 0ustar otfriedotfried Ipelib: ipe::Repository Class Reference
Ipelib

#include <ipeattributes.h>

Public Member Functions

String toString (int index) const
 
int toIndex (String str)
 

Static Public Member Functions

static Repositoryget ()
 
static void cleanup ()
 

Detailed Description

Repository of strings.

Ipe documents can use symbolic attributes, such as 'normal', 'fat', or 'thin' for line thickness, or 'red', 'navy', 'turquoise' for color, as well as absolute attributes such as "[3 1] 0" for a dash pattern. To avoid storing these common strings hundreds of times, Repository keeps a repository of strings. Inside an Object, strings are replaced by indices into the repository.

The Repository is a singleton object. It is created the first time it is used. You obtain access to the repository using get().

Member Function Documentation

◆ get()

Repository * Repository::get ( )
static

◆ cleanup()

void Repository::cleanup ( )
static

Destroy repository object.

Referenced by ipe::Platform::libVersion().

◆ toString()

String Repository::toString ( int  index) const

Return string with given index.

Referenced by ipe::StyleSheet::saveAsXml(), and ipe::Attribute::string().

◆ toIndex()

int Repository::toIndex ( String  str)

Return index of given string.

The string is added to the repository if it doesn't exist yet.

References ipe::String::empty().

Referenced by ipe::Attribute::Attribute().


The documentation for this class was generated from the following files:
  • ipeattributes.h
  • ipeattributes.cpp

ipe-7.2.13/build/doc/classipe_1_1_pdf_file-members.html0000644000175000017500000000775513561570220022527 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PdfFile Member List

This is the complete list of members for ipe::PdfFile, including all inherited members.

catalog() const noexceptipe::PdfFile
countPages() constipe::PdfFileinline
mediaBox(const PdfDict *page) constipe::PdfFile
object(int num) const noexceptipe::PdfFile
page(int pno=0) const noexceptipe::PdfFile
parse(DataSource &source)ipe::PdfFile
parseObjectStream(const PdfDict *d)ipe::PdfFile
take(int num)ipe::PdfFile

ipe-7.2.13/build/doc/radgrad2.svg0000644000175000017500000000237113561570220016312 0ustar otfriedotfried ipe-7.2.13/build/doc/manual_ipe_copyright.html0000644000175000017500000003000213561570220021163 0ustar otfriedotfried Ipe Manual -- Contents
FootnotesTop13 CopyrightContents

Contents

ipe-7.2.13/build/doc/functions_func_n.html0000644000175000017500000000647613561570220020343 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- n -


ipe-7.2.13/build/doc/classipe_1_1_save_flag-members.html0000644000175000017500000000651313561570220022675 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::SaveFlag Member List

This is the complete list of members for ipe::SaveFlag, including all inherited members.

Export enum valueipe::SaveFlag
KeepNotes enum valueipe::SaveFlag
MarkedView enum valueipe::SaveFlag
NoZip enum valueipe::SaveFlag
SaveNormal enum valueipe::SaveFlag

ipe-7.2.13/build/doc/luaipe.html0000644000175000017500000001152613561570220016252 0ustar otfriedotfried Ipelib: Lua bindings for Ipe
Ipelib
Lua bindings for Ipe

These are the Lua methods provided by the Ipe program itself. They are only available to Lua code running inside Ipe.

Application user interface

The application user interface object provides the GUI for the Ipe program.

-- model is a Lua table containing methods that will be called 
-- by the ui when events occur
ui = AppUi(model)

-- returns window id of window
-- (to be used as parent for dialogs)
id = ui:win()

ui:close()         -- close window

ui:setActionState(name, t) -- set whether action is checked 
t = ui:actionState(name)   -- is action checked?
-- return info about action: id, and whether it's always on 
id, alwaysOn = actionInfo(name)       

ui:explain(text)     -- show message in status bar for a few seconds
ui:setWindowTitle(caption)

-- make a tool visible or invisible
-- tool is one of "layers", "properties", "bookmarks", "notes"
-- t is true or false
ui:showTool(tool, t)

ui:setNotes(n)       -- set string for Notes tool


-- set contents of attribute selectors from style sheet
ui:setupSymbolicNames(styleSheet)

-- set attribute values displayed in user interface
-- 'attributes' table see below
ui:setAttributes(styleSheet, attributes)

-- set layer list from page
ui:setLayers(page, view)  

ui:setNumbers(?)
ui:setBookmarks(?)

-- page/view selector tool:
-- select one page and return page number (or nil if canceled)
pno = ui:selectPage(doc) 
-- select one view and return view number (or nil if canceled)
vno = ui:selectPage(doc, page_no)

ui:pageSorter(?)

ui:setClipboard(text)     -- store text on system clipboard
-- get text or bitmap property from system clipboard
-- if t is false, only text is retrieved
-- returns either a string or an image object.
obj = ipeui.clipboard(t)  

The following methods work on the canvas inside the UI:

ui:setPage(page, pgno, view, styleSheet) -- set page shown on canvas
ui:setSnap(snap)                    -- for 'snap' table see below
ui:setFontPool(p)       -- an opaque object obtained from an ipe.Document

-- 'pan' is a vector indicating the user coordinates at canvas center
v = ui:pan()       
ui:setPan(v)

zoom = ui:zoom()        -- a number
ui:setZoom(zoom)

v = ui:pos()            -- current mouse position, after snapping
v = ui:unsnappedPos()   -- current mouse position, before snapping
v = ui:simpleSnapPos()  -- same, but ignoring angular snap
v = ui:globalPos()      -- mouse position on screen

v = ui:canvasSize()     -- size of canvas in pixels

ui:setNumbering(t)      -- true or false
ui:setFifiVisible(t)    -- true or false
ui:setSelectionVisible(t) -- true or false
ui:setPretty(t)         -- true or false

-- setCursor only implemented on Qt.
-- Windows 8 switches to a dot cursor automatically when using the pen.
ui:setCursor(name)         -- name in "standard", "hand", "cross"
ui:setCursor(width, color) -- sets a colored dot cursor (on Qt)

ui:update()             -- update canvas and tool
ui:update(false)        -- update tool only
ui:finishTool()

ui:panTool()
ui:selectTool()
ui:transformTool()
ui:shapeTool()

ipe-7.2.13/build/doc/functions_func_g.html0000644000175000017500000001423513561570220020324 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- g -


ipe-7.2.13/build/doc/functions_type.html0000644000175000017500000000340413561570220020040 0ustar otfriedotfried Ipelib: Class Members - Typedefs
Ipelib
 

ipe-7.2.13/build/doc/manual_25.html0000644000175000017500000001102413561570220016547 0ustar otfriedotfried Ipe Manual -- 5.4 Interaction of the snapping modes
5.5 Examples5 Snapping5.3 Angular snapping5.4 Interaction of the snapping modes

5.4 Interaction of the snapping modes

Not all the snapping modes can be active at the same time, even if all buttons are pressed. Here we have a close look at the possible interactions, and the priorities of snapping.

The two angular snapping modes restrict the possible mouse positions to a one-dimensional subspace of the canvas. Therefore, they are incompatible with the modes that try to snap to a zero-dimensional subspace, namely vertex snapping, intersection snapping, and grid snapping. Consequently, when one of the angular snapping modes is on, vertex snapping, intersection snapping, and grid snapping are ineffective.

On the other hand, it is reasonable to snap to boundaries while in an angular snapping mode, and this function is actually implemented correctly. When both angular and boundary snapping are on, Ipe will compute intersections between the snap lines with the boundaries of your objects, and whenever the mouse position on the snap line comes close enough to an intersection, the mouse is snapped to that intersection.

The two angular snapping modes themselves can also coexist in the same fashion. If both angular and automatic angular snapping are enabled, Ipe computes the intersection point between the snap lines defined by the two origins and snaps there. It the snap lines are parallel or coincide, automatic angular snapping is used.

When no angular snapping mode is active, Ipe has three priorities. First, Ipe checks whether the closest vertex or intersection point is close enough. If that is not the case, the closest boundary edge is determined. If even that is too far away, Ipe uses grid snapping (assuming all these modes are enabled).

Note that this can actually mean that snapping is not to the closest point on an object. Especially for intersections of two straight edges, the closest point can never be the intersection point, as in the figure below!

ipe-7.2.13/build/doc/classipe_1_1_snap.html0000644000175000017500000007474313561570220020271 0ustar otfriedotfried Ipelib: ipe::Snap Class Reference
Ipelib

#include <ipesnap.h>

Public Types

enum  TSnapModes {
  ESnapNone = 0, ESnapVtx = 1, ESnapCtl = 2, ESnapBd = 4,
  ESnapInt = 8, ESnapGrid = 0x10, ESnapAngle = 0x20, ESnapAuto = 0x40
}
 

Public Member Functions

void intersectionSnap (const Vector &pos, Vector &fifi, const Page *page, int view, double &snapDist) const noexcept
 
bool snapAngularIntersection (Vector &pos, const Line &l, const Page *page, int view, double snapDist) const noexcept
 
TSnapModes simpleSnap (Vector &pos, const Page *page, int view, double snapDist, Tool *tool=nullptr) const noexcept
 
TSnapModes snap (Vector &pos, const Page *page, int view, double snapDist, Tool *tool=nullptr, Vector *autoOrg=nullptr) const noexcept
 
Line getLine (const Vector &mouse, const Vector &base) const noexcept
 
bool setEdge (const Vector &pos, const Page *page, int view) noexcept
 

Public Attributes

int iSnap
 
bool iGridVisible
 
int iGridSize
 
double iAngleSize
 
int iSnapDistance
 
bool iWithAxes
 
Vector iOrigin
 
Angle iDir
 

Detailed Description

Performs snapping operations, and stores snapping state.

Member Enumeration Documentation

◆ TSnapModes

The different snap modes as bitmasks.

Enumerator
ESnapNone 
ESnapVtx 
ESnapCtl 
ESnapBd 
ESnapInt 
ESnapGrid 
ESnapAngle 
ESnapAuto 

Member Function Documentation

◆ intersectionSnap()

void Snap::intersectionSnap ( const Vector pos,
Vector fifi,
const Page page,
int  view,
double &  snapDist 
) const
noexcept

Perform intersection snapping.

References ipe::size().

◆ snapAngularIntersection()

bool Snap::snapAngularIntersection ( Vector pos,
const Line l,
const Page page,
int  view,
double  snapDist 
) const
noexcept

Perform snapping to intersection of angular line and pos.

◆ simpleSnap()

Snap::TSnapModes Snap::simpleSnap ( Vector pos,
const Page page,
int  view,
double  snapDist,
Tool tool = nullptr 
) const
noexcept

Tries vertex, intersection, boundary, and grid snapping.

If snapping occurred, pos is set to the new user space position.

References ipe::Page::count(), ipe::Page::objSnapsInView(), ipe::Page::snapBnd(), ipe::Page::snapCtl(), ipe::Page::snapVtx(), ipe::Vector::x, and ipe::Vector::y.

◆ snap()

Snap::TSnapModes Snap::snap ( Vector pos,
const Page page,
int  view,
double  snapDist,
Tool tool = nullptr,
Vector autoOrg = nullptr 
) const
noexcept

Performs snapping of position pos.

Returns true if snapping occurred. In that case pos is set to the new user space position.

Automatic angular snapping occurs if autoOrg is not null — the value is then used as the origin for automatic angular snapping.

References ipe::Line::intersects(), ipe::Line::project(), and ipe::Vector::sqLen().

◆ getLine()

Line Snap::getLine ( const Vector mouse,
const Vector base 
) const
noexcept

Find line through base with slope determined by angular snap size and direction.

References ipe::Vector::angle(), ipe::Vector::len(), and ipe::Angle::normalize().

◆ setEdge()

bool Snap::setEdge ( const Vector pos,
const Page page,
int  view 
)
noexcept

Member Data Documentation

◆ iSnap

int ipe::Snap::iSnap

Activated snapping modes (TSnapModes)

◆ iGridVisible

bool ipe::Snap::iGridVisible

Is the grid visible?

◆ iGridSize

int ipe::Snap::iGridSize

Snap grid spacing.

◆ iAngleSize

double ipe::Snap::iAngleSize

Angle for angular snapping.

◆ iSnapDistance

int ipe::Snap::iSnapDistance

Snap distance (in pixels).

◆ iWithAxes

bool ipe::Snap::iWithAxes

Show coordinate system?

Referenced by ipe::TransformTool::TransformTool().

◆ iOrigin

Vector ipe::Snap::iOrigin

Origin of coordinate system.

Referenced by ipe::TransformTool::TransformTool().

◆ iDir

Angle ipe::Snap::iDir

Direction of x-axis.

Referenced by ipe::TransformTool::TransformTool().


The documentation for this class was generated from the following files:
  • ipesnap.h
  • ipesnap.cpp

ipe-7.2.13/build/doc/classipe_1_1_canvas.html0000644000175000017500000025570513561570220020602 0ustar otfriedotfried Ipelib: ipe::Canvas Class Reference
Ipelib

#include <ipecanvas_win.h>

Inherits ipe::CanvasBase, QWidget, ipe::CanvasBase, and ipe::CanvasBase.

Public Member Functions

 Canvas (GtkWidget *parent)
 
 ~Canvas ()
 
GtkWidget * window () const
 
 Canvas (QWidget *parent, Qt::WFlags f=0)
 
virtual void setCursor (TCursor cursor, double w=1.0, Color *color=nullptr)
 
 Canvas (HWND parent, HINSTANCE hInstance=nullptr)
 
HWND windowId () const
 
- Public Member Functions inherited from ipe::CanvasBase
virtual ~CanvasBase ()
 
void setPage (const Page *page, int pno, int view, const Cascade *sheet)
 
void setResources (const PdfResources *resources)
 
Vector pan () const
 
double zoom () const
 
const Cascadecascade () const
 
Vector center () const
 
Vector pos () const
 
Vector unsnappedPos () const
 
Vector globalPos () const
 
Vector simpleSnapPos () const
 
const Snapsnap () const
 
void setInkMode (bool ink)
 
int additionalModifiers () const
 
void setAdditionalModifiers (int mod)
 
Vector devToUser (const Vector &arg) const
 
Vector userToDev (const Vector &arg) const
 
void setCanvasStyle (const Style &style)
 
Style canvasStyle () const
 
void setPan (const Vector &v)
 
void setZoom (double zoom)
 
void setSnap (const Snap &s)
 
void setDimmed (bool dimmed)
 
void setAutoOrigin (const Vector &v)
 
Matrix canvasTfm () const
 
void setObserver (CanvasObserver *observer)
 
void setFifiVisible (bool visible)
 
void setSelectionVisible (bool visible)
 
void setTool (Tool *tool)
 
void finishTool ()
 
Tooltool ()
 
void update ()
 
void updateTool ()
 
int canvasWidth () const
 
int canvasHeight () const
 

Static Public Member Functions

static void init (HINSTANCE hInstance)
 
static UINT getDpiForWindow (HWND hwnd)
 
static HBITMAP createBitmap (uint8_t *p, int w, int h)
 
- Static Public Member Functions inherited from ipe::CanvasBase
static int selectPageOrView (Document *doc, int page=-1, int startIndex=0, int pageWidth=240, int width=600, int height=480)
 

Protected Member Functions

virtual void invalidate ()
 
virtual void invalidate (int x, int y, int w, int h)
 
void drawFifi (QPainter &q)
 
virtual void paintEvent (QPaintEvent *ev)
 
void mouseButton (QMouseEvent *ev, int button, bool press)
 
virtual void mouseDoubleClickEvent (QMouseEvent *ev)
 
virtual void mousePressEvent (QMouseEvent *ev)
 
virtual void mouseReleaseEvent (QMouseEvent *ev)
 
virtual void mouseMoveEvent (QMouseEvent *ev)
 
virtual void tabletEvent (QTabletEvent *ev)
 
virtual void wheelEvent (QWheelEvent *ev)
 
virtual void keyPressEvent (QKeyEvent *ev)
 
virtual QSize sizeHint () const
 
- Protected Member Functions inherited from ipe::CanvasBase
 CanvasBase ()
 
void drawPaper (cairo_t *cc)
 
void drawFrame (cairo_t *cc)
 
void drawAxes (cairo_t *cc)
 
void drawGrid (cairo_t *cc)
 
void drawObjects (cairo_t *cc)
 
void drawTool (Painter &painter)
 
void snapToPaperAndFrame ()
 
void refreshSurface ()
 
void computeFifi (double x, double y)
 
void drawFifi (cairo_t *cr)
 

Additional Inherited Members

- Public Types inherited from ipe::CanvasBase
enum  TModifiers {
  EShift = 0x100, EControl = 0x200, EAlt = 0x400, EMeta = 0x800,
  ECommand = 0x1000
}
 
enum  TCursor { EStandardCursor, EHandCursor, ECrossCursor, EDotCursor }
 
- Protected Attributes inherited from ipe::CanvasBase
CanvasObserveriObserver
 
TooliTool
 
const PageiPage
 
int iPageNumber
 
int iView
 
const CascadeiCascade
 
Style iStyle
 
Vector iPan
 
double iZoom
 
Snap iSnap
 
bool iDimmed
 
bool iAutoSnap
 
Vector iAutoOrigin
 
int iAdditionalModifiers
 
bool isInkMode
 
bool iRepaintObjects
 
double iWidth
 
double iHeight
 
double iBWidth
 
double iBHeight
 
cairo_surface_t * iSurface
 
Vector iUnsnappedMousePos
 
Vector iMousePos
 
Vector iGlobalPos
 
Vector iOldFifi
 
bool iFifiVisible
 
Snap::TSnapModes iFifiMode
 
bool iSelectionVisible
 
const PdfResourcesiResources
 
std::unique_ptr< FontsiFonts
 

Detailed Description

A widget (control) that displays an Ipe document page.

Constructor & Destructor Documentation

◆ Canvas() [1/3]

Canvas::Canvas ( GtkWidget *  parent)

References ~Canvas().

Referenced by ipe::IpeQ(), and Canvas::scrollWheel().

◆ ~Canvas()

◆ Canvas() [2/3]

Canvas::Canvas ( QWidget *  parent,
Qt::WFlags  f = 0 
)

Construct a new canvas.

◆ Canvas() [3/3]

Canvas::Canvas ( HWND  parent,
HINSTANCE  hInstance = nullptr 
)

Member Function Documentation

◆ window()

GtkWidget* ipe::Canvas::window ( ) const
inline

Referenced by Canvas::drawRect().

◆ setCursor()

virtual void ipe::Canvas::setCursor ( TCursor  cursor,
double  w = 1.0,
Color color = nullptr 
)
virtual

Implements ipe::CanvasBase.

◆ invalidate() [1/2]

virtual void ipe::Canvas::invalidate ( )
protectedvirtual

Implements ipe::CanvasBase.

◆ invalidate() [2/2]

virtual void ipe::Canvas::invalidate ( int  x,
int  y,
int  w,
int  h 
)
protectedvirtual

Implements ipe::CanvasBase.

◆ drawFifi()

◆ paintEvent()

◆ mouseButton()

◆ mouseDoubleClickEvent()

void Canvas::mouseDoubleClickEvent ( QMouseEvent *  ev)
protectedvirtual

References mouseButton().

Referenced by ipe::IpeQ().

◆ mousePressEvent()

void Canvas::mousePressEvent ( QMouseEvent *  ev)
protectedvirtual

References mouseButton().

Referenced by ipe::IpeQ().

◆ mouseReleaseEvent()

void Canvas::mouseReleaseEvent ( QMouseEvent *  ev)
protectedvirtual

References mouseButton().

Referenced by ipe::IpeQ().

◆ mouseMoveEvent()

void Canvas::mouseMoveEvent ( QMouseEvent *  ev)
protectedvirtual

◆ tabletEvent()

◆ wheelEvent()

void Canvas::wheelEvent ( QWheelEvent *  ev)
protectedvirtual

◆ keyPressEvent()

void Canvas::keyPressEvent ( QKeyEvent *  ev)
protectedvirtual

◆ sizeHint()

◆ init()

void Canvas::init ( HINSTANCE  hInstance)
static

◆ getDpiForWindow()

UINT Canvas::getDpiForWindow ( HWND  hwnd)
static

◆ windowId()

HWND ipe::Canvas::windowId ( ) const
inline

References createBitmap(), and mouseButton().

◆ createBitmap()

static HBITMAP ipe::Canvas::createBitmap ( uint8_t *  p,
int  w,
int  h 
)
static

Referenced by windowId().


The documentation for this class was generated from the following files:
  • ipecanvas_gtk.h
  • ipecanvas_win.h
  • ipecanvas_qt.h
  • ipecanvas_cocoa.cpp
  • ipecanvas_gtk.cpp
  • ipecanvas_qt.cpp
  • ipecanvas_win.cpp

ipe-7.2.13/build/doc/manual_54.html0000644000175000017500000000605413561570220016560 0ustar otfriedotfried Ipe Manual -- 11.3 Iperender: exporting to a bitmap, EPS, or SVG
11.4 Ipeextract: extract XML stream from Ipe file11 The command line programs11.2 Ipetoipe: converting Ipe file formats11.3 Iperender: exporting to a bitmap, EPS, or SVG

11.3 Iperender: exporting to a bitmap, EPS, or SVG

The program iperender exports a page of the document to a bitmap in PNG format, to a figure in Encapsulated Postscript (EPS), or to scalable vector graphics in SVG format. (Of course the result contains no Ipe markup, so make sure you keep your original!) For instance, the following command line

  iperender -png -page 3 -resolution 150 presentation.pdf pres3.png
converts page 3 of the Ipe document presentation.pdf to a bitmap, with resolution 150 pixels per inch.
ipe-7.2.13/build/doc/classipe_1_1_platform-members.html0000644000175000017500000001511313561570220022566 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Platform Member List

This is the complete list of members for ipe::Platform, including all inherited members.

currentDirectory()ipe::Platformstatic
DebugHandler typedefipe::Platform
fileExists(String fname)ipe::Platformstatic
fopen(const char *fname, const char *mode)ipe::Platforminlinestatic
initLib(int version)ipe::Platformstatic
ipeDrive()ipe::Platformstatic
latexDirectory()ipe::Platformstatic
latexPath()ipe::Platformstatic
libVersion()ipe::Platformstatic
listDirectory(String path, std::vector< String > &files)ipe::Platformstatic
readFile(String fname)ipe::Platformstatic
realPath(String fname)ipe::Platformstatic
runLatex(String dir, LatexType engine, String docname) noexceptipe::Platformstatic
setDebug(bool debug)ipe::Platformstatic
toDouble(String s)ipe::Platformstatic
toNumber(String s, int &iValue, double &dValue)ipe::Platformstatic

ipe-7.2.13/build/doc/classipe_1_1_buffer_source-members.html0000644000175000017500000000605313561570220023576 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::BufferSource Member List

This is the complete list of members for ipe::BufferSource, including all inherited members.

BufferSource(const Buffer &buffer)ipe::BufferSource
getChar()ipe::BufferSourcevirtual
setPosition(int pos)ipe::BufferSource
~DataSource()=0ipe::DataSourcepure virtual

ipe-7.2.13/build/doc/classipe_1_1_fixed.html0000644000175000017500000005740713561570220020425 0ustar otfriedotfried Ipelib: ipe::Fixed Class Reference
Ipelib

#include <ipebase.h>

Public Member Functions

 Fixed (int val)
 
 Fixed ()
 
int toInt () const
 
double toDouble () const
 
int internal () const
 
Fixed mult (int a, int b) const
 
bool operator== (const Fixed &rhs) const
 
bool operator!= (const Fixed &rhs) const
 
bool operator< (const Fixed &rhs) const
 
bool isInteger () const
 

Static Public Member Functions

static Fixed fromInternal (int32_t val)
 
static Fixed fromDouble (double val)
 

Friends

Streamoperator<< (Stream &stream, const Fixed &f)
 

Related Functions

(Note that these are not member functions.)

Streamoperator<< (Stream &stream, const Fixed &f)
 

Detailed Description

Fixed point number with three (decimal) fractional digits.

Constructor & Destructor Documentation

◆ Fixed() [1/2]

ipe::Fixed::Fixed ( int  val)
inlineexplicit

◆ Fixed() [2/2]

ipe::Fixed::Fixed ( )
inlineexplicit

Member Function Documentation

◆ fromInternal()

Fixed ipe::Fixed::fromInternal ( int32_t  val)
inlinestatic

◆ fromDouble()

Fixed Fixed::fromDouble ( double  val)
static

References fromInternal().

Referenced by ipe::Text::getAttribute().

◆ toInt()

int ipe::Fixed::toInt ( ) const
inline

◆ toDouble()

◆ internal()

int ipe::Fixed::internal ( ) const
inline

◆ mult()

Fixed Fixed::mult ( int  a,
int  b 
) const

Return value times (a/b)

Referenced by ipe::Latex::createLatexSource(), and ipe::String::unicode().

◆ operator==()

bool ipe::Fixed::operator== ( const Fixed rhs) const
inline

◆ operator!=()

bool ipe::Fixed::operator!= ( const Fixed rhs) const
inline

◆ operator<()

bool ipe::Fixed::operator< ( const Fixed rhs) const
inline

◆ isInteger()

bool ipe::Fixed::isInteger ( ) const
inline

Friends And Related Function Documentation

◆ operator<< [1/2]

Stream& operator<< ( Stream stream,
const Fixed f 
)
friend

◆ operator<<() [2/2]

Stream & operator<< ( Stream stream,
const Fixed f 
)
related

References ipe::Lex::Lex().


The documentation for this class was generated from the following files:
  • ipebase.h
  • ipebase.cpp

ipe-7.2.13/build/doc/functions_func_h.html0000644000175000017500000000573413561570220020331 0ustar otfriedotfried Ipelib: Class Members - Functions
Ipelib
 

- h -


ipe-7.2.13/build/doc/manual_62.html0000644000175000017500000000613513561570220016557 0ustar otfriedotfried Ipe Manual -- Footnotes
TopContentsFootnotes

Footnotes

 (1)
The line width can be set to zero to get the thinnest line the device can produce (i.e. approximately the same as 0.15 for a 600 dpi printer or 0.3 for a 300 dpi printer). The PDF and Postscript authorities discourage using this feature, since it makes your Postscript files device-dependent.
 (2)
J. D. Foley, A. Van Dam, S. K. Feiner, and J. F. Hughes, Computer Graphics: Principles and Practice, Addison-Wesley, 1990.
 (3)
Fifi is called after the dog in the rogue computer game installed on most Unix systems in the 1980's, because it also keeps running around your feet.
ipe-7.2.13/build/doc/sync_on.png0000644000175000017500000000151513561570220016260 0ustar otfriedotfried‰PNG  IHDRàw=øIDATxíÝ_HTYÀñï8ã¤ó§i§4-g6ÆËÕ&kQ)¨Ô!Š0ÒURKÚ…„ê¡/»PEÁ>ìK-+KÁ²Ñ.Y”¾dEPaA‰ø°¥¶›ZSÓïÜ;3wºŠ–¯—߯gfîïœsçœWKÇñ.€ÉøD­¨a‘'¬âq_ôˆk¢ÀŒ ÀDŽøQ´ÄïC¨¶åñÏÿgÅ ñ 0„Y‚:qZ¦Á)~õâ€èLý0HVñ× žz-¿‰C“%¨g¦˜6€é8%Úõ¬ëwêÙUÏ¿˜ª³Ä }? ?€·3ÀÀž©Š À”K• @hà a±ðaÇæUe‹ sù~ë2²ì“&Ú&B*AÄljæºììi*˨,Ëçí»÷oÆ£T”,d[˜¼3-*ÁÀ…>å‡Ë çLÉŸçfk˜Ò éw#*AEjKUy>ûšËÉõ&{µ¢8—m5Ki¬ jjƒD*¿NŽÖigwÃ7Dª’mz骹úKÛ¾±ˆ¶M!æ¤ÍkÐ?šoý¬_åÓlXí#Ò~–¸¬ê×ÒÑXŠÓ‘ùRÙ*Eû‚ՂדðEÜ;6«e"Q(²Ù=–¿Ezæ5Kؼָ_ 1òzBªJë ±XŒì96åªjL^7{ùãJÑ÷1½i@%8'7M©_\Qœ#ÓUŒËñýÿyõ Wo Éx8¼s¥v¯ªì|×SnÜ q_m Ýé î>bèÕí[JX,½4[Tú{R£ë¼ôˆ¾þa€tÝjjzzÅ'ÅìȶiIžŽòwÏs ¡€—ÕKøõâC^ŽŒ˜Y­¨µÉ%6¨´êˆº]vÛðhâ½iWv–hôëê°Ò¨¾'æÌ‚·ñ|[ßìúÅ^€YrD=<ýDû]äÇ÷s€Ïõ‹8™ºCì? À ¨—t4õᩎ¡Jã‡W‹É± îr¼cjMɘìx| šE©øNÔ‰œøA¢þ«–€Z¼ñ‡jó î#™§¢¢4gIEND®B`‚ipe-7.2.13/build/doc/classipe_1_1_reference-members.html0000644000175000017500000005041213561570220022701 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Reference Member List

This is the complete list of members for ipe::Reference, including all inherited members.

accept(Visitor &visitor) constipe::Referencevirtual
addToBBox(Rect &box, const Matrix &m, bool cp) constipe::Referencevirtual
asGroup()ipe::Objectvirtual
asGroup() constipe::Objectvirtual
asImage()ipe::Objectvirtual
asPath()ipe::Objectvirtual
asReference()ipe::Referencevirtual
asText()ipe::Objectvirtual
checkStyle(const Cascade *sheet, AttributeSeq &seq) constipe::Referencevirtual
checkSymbol(Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq)ipe::Objectprotectedstatic
clone() constipe::Referencevirtual
distance(const Vector &v, const Matrix &m, double bound) constipe::Referencevirtual
draw(Painter &painter) constipe::Referencevirtual
drawSimple(Painter &painter) constipe::Referencevirtual
EGroup enum valueipe::Object
EHasFill enum valueipe::Reference
EHasPen enum valueipe::Reference
EHasSize enum valueipe::Reference
EHasStroke enum valueipe::Reference
EImage enum valueipe::Object
EIsArrow enum valueipe::Reference
EIsMark enum valueipe::Reference
EPath enum valueipe::Object
EReference enum valueipe::Object
EText enum valueipe::Object
fill() constipe::Referenceinline
flags() constipe::Referenceinline
flagsFromName(String name)ipe::Referencestatic
getAttribute(Property prop) const noexceptipe::Referencevirtual
iMatrixipe::Objectprotected
iPinnedipe::Objectprotected
iTransformationsipe::Objectprotected
matrix() constipe::Objectinline
name() constipe::Referenceinline
Object()ipe::Objectexplicitprotected
Object(const AllAttributes &attr)ipe::Objectexplicitprotected
Object(const Object &rhs)ipe::Objectprotected
Object(const XmlAttributes &attr)ipe::Objectexplicitprotected
pen() constipe::Referenceinline
pinned() constipe::Objectvirtual
position() constipe::Referenceinline
Reference(const AllAttributes &attr, Attribute name, Vector pos)ipe::Referenceexplicit
Reference(const XmlAttributes &attr, String data)ipe::Referenceexplicit
saveAsXml(Stream &stream, String layer) constipe::Referencevirtual
saveAttributesAsXml(Stream &stream, String layer) constipe::Objectprotected
setAttribute(Property prop, Attribute value)ipe::Referencevirtual
setFill(Attribute color)ipe::Reference
setMatrix(const Matrix &matrix)ipe::Object
setName(Attribute name)ipe::Reference
setPen(Attribute pen)ipe::Reference
setPinned(TPinned pin)ipe::Object
setSize(Attribute size)ipe::Reference
setStroke(Attribute color)ipe::Reference
setTransformations(TTransformations trans)ipe::Object
size() constipe::Referenceinline
snapBnd(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Referencevirtual
snapCtl(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Objectvirtual
snapVtx(const Vector &mouse, const Matrix &m, Vector &pos, double &bound) constipe::Referencevirtual
stroke() constipe::Referenceinline
transformations() constipe::Objectinline
Type enum nameipe::Object
type() constipe::Referencevirtual
~Object()=0ipe::Objectpure virtual

ipe-7.2.13/build/doc/group__canvas.html0000644000175000017500000000775413561570220017631 0ustar otfriedotfried Ipelib: Ipe canvas
Ipelib
Ipe canvas

Classes

class  ipe::Tool
 
class  ipe::Canvas
 
class  ipe::PdfViewBase
 
class  ipe::PageSelector
 
class  ipe::PanTool
 
class  ipe::SelectTool
 
class  ipe::TransformTool
 

Detailed Description

A widget (control) that displays an Ipe document page.

This module contains the classes needed to display and edit Ipe objects using the selected toolkit.

These classes are not in Ipelib, but in a separate library libipecanvas.


ipe-7.2.13/build/doc/classipe_1_1_group.html0000644000175000017500000023453713561570220020463 0ustar otfriedotfried Ipelib: ipe::Group Class Reference
Ipelib

#include <ipegroup.h>

Inherits ipe::Object.

Public Types

typedef List::const_iterator const_iterator
 
- Public Types inherited from ipe::Object
enum  Type {
  EGroup, EPath, EText, EImage,
  EReference
}
 

Public Member Functions

 Group ()
 
 Group (const Group &rhs)
 
virtual ~Group ()
 
 Group (const XmlAttributes &attr)
 
Groupoperator= (const Group &rhs)
 
virtual Objectclone () const
 
virtual GroupasGroup ()
 
virtual const GroupasGroup () const
 
virtual Type type () const
 
virtual TPinned pinned () const
 
virtual void accept (Visitor &visitor) const
 
virtual void saveAsXml (Stream &stream, String layer) const
 
virtual void draw (Painter &painter) const
 
virtual void drawSimple (Painter &painter) const
 
virtual void addToBBox (Rect &box, const Matrix &m, bool cp) const
 
virtual double distance (const Vector &v, const Matrix &m, double bound) const
 
virtual void snapVtx (const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const
 
virtual void snapCtl (const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const
 
virtual void snapBnd (const Vector &mouse, const Matrix &m, Vector &pos, double &bound) const
 
const Shapeclip () const
 
void setClip (const Shape &clip)
 
String url () const
 
void setUrl (String url)
 
int count () const
 
const Objectobject (int i) const
 
const_iterator begin () const
 
const_iterator end () const
 
void push_back (Object *)
 
void saveComponentsAsXml (Stream &stream) const
 
virtual void checkStyle (const Cascade *sheet, AttributeSeq &seq) const
 
virtual Attribute getAttribute (Property prop) const noexcept
 
virtual bool setAttribute (Property prop, Attribute value)
 
- Public Member Functions inherited from ipe::Object
virtual ~Object ()=0
 
virtual TextasText ()
 
virtual PathasPath ()
 
virtual ImageasImage ()
 
virtual ReferenceasReference ()
 
void setPinned (TPinned pin)
 
TTransformations transformations () const
 
void setTransformations (TTransformations trans)
 
void setMatrix (const Matrix &matrix)
 
const Matrixmatrix () const
 

Additional Inherited Members

- Protected Member Functions inherited from ipe::Object
 Object ()
 
 Object (const AllAttributes &attr)
 
 Object (const Object &rhs)
 
 Object (const XmlAttributes &attr)
 
void saveAttributesAsXml (Stream &stream, String layer) const
 
- Static Protected Member Functions inherited from ipe::Object
static void checkSymbol (Kind kind, Attribute attr, const Cascade *sheet, AttributeSeq &seq)
 
- Protected Attributes inherited from ipe::Object
Matrix iMatrix
 
TPinned iPinned: 8
 
TTransformations iTransformations: 8
 

Detailed Description

The group object.

Ipe objects can be grouped together, and the resulting composite can be used like any Ipe object.

This is an application of the "Composite" pattern.

Member Typedef Documentation

◆ const_iterator

typedef List::const_iterator ipe::Group::const_iterator

Constructor & Destructor Documentation

◆ Group() [1/3]

Group::Group ( )
explicit

Create empty group (objects can be added later).

Referenced by clone().

◆ Group() [2/3]

Group::Group ( const Group rhs)

Copy constructor. Constant time — components are not copied!

◆ ~Group()

Group::~Group ( )
virtual

Destructor.

◆ Group() [3/3]

Group::Group ( const XmlAttributes attr)
explicit

Create empty group with these attributes (objects can be added later).

References clip(), ipe::ENoPin, ipe::XmlAttributes::has(), ipe::Shape::load(), and ipe::Attribute::NORMAL().

Member Function Documentation

◆ operator=()

Group & Group::operator= ( const Group rhs)

Assignment operator (constant-time).

◆ clone()

Object * Group::clone ( ) const
virtual

Clone a group object (constant-time).

Implements ipe::Object.

References Group().

◆ asGroup() [1/2]

Group * Group::asGroup ( )
virtual

Return pointer to this object.

Reimplemented from ipe::Object.

◆ asGroup() [2/2]

const Group * Group::asGroup ( ) const
virtual

Return pointer to this object.

Reimplemented from ipe::Object.

◆ type()

Object::Type Group::type ( ) const
virtual

Implements ipe::Object.

References ipe::Object::EGroup.

◆ pinned()

TPinned Group::pinned ( ) const
virtual

Return total pinning status of group and its elements.

Reimplemented from ipe::Object.

References ipe::Object::pinned().

◆ accept()

void Group::accept ( Visitor visitor) const
virtual

Call visitGroup of visitor.

Implements ipe::Object.

References ipe::Visitor::visitGroup().

◆ saveAsXml()

◆ draw()

◆ drawSimple()

◆ addToBBox()

void Group::addToBBox ( Rect box,
const Matrix m,
bool  cp 
) const
virtual

Extend box to include the object transformed by m.

For objects in a page, don't call this directly. The Page caches the bounding box of each object, so it is far more efficient to call Page::bbox.

Control points that lie outside the visual object are included if cp is true.

If called with an empty box and cp == false, the result of this function is a tight bounding box for the object, with a little leeway in case the boundary is determined by a spline (it has to be approximated to perform this operation).

Implements ipe::Object.

References ipe::Rect::addRect(), begin(), ipe::Rect::clipTo(), end(), and ipe::Object::matrix().

Referenced by draw().

◆ distance()

double Group::distance ( const Vector v,
const Matrix m,
double  bound 
) const
virtual

Return distance of transformed object to point v. If larger than bound, can just return bound.

Implements ipe::Object.

References begin(), end(), and ipe::Object::matrix().

◆ snapVtx()

void Group::snapVtx ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound 
) const
virtual

Compute vertex snapping position for transformed object.

Looks only for positions closer than bound. If successful, modify pos and bound. The default implementation does nothing.

Reimplemented from ipe::Object.

References begin(), end(), and ipe::Object::matrix().

◆ snapCtl()

void Group::snapCtl ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound 
) const
virtual

Compute control point snapping position for transformed object.

Looks only for positions closer than bound. If successful, modify pos and bound. The default implementation does nothing.

Reimplemented from ipe::Object.

References begin(), end(), and ipe::Object::matrix().

◆ snapBnd()

void Group::snapBnd ( const Vector mouse,
const Matrix m,
Vector pos,
double &  bound 
) const
virtual

Compute boundary snapping position for transformed object.

Looks only for positions closer than bound. If successful, modify pos and bound. The default implementation does nothing.

Reimplemented from ipe::Object.

References begin(), end(), and ipe::Object::matrix().

◆ clip()

const Shape& ipe::Group::clip ( ) const
inline

References setClip().

Referenced by Group(), and setClip().

◆ setClip()

void Group::setClip ( const Shape clip)

Set clip path for this group.

Any previously set clip path is deleted.

References clip().

Referenced by clip().

◆ url()

String ipe::Group::url ( ) const
inline

References setUrl().

Referenced by ipe::PdfWriter::createPageView(), and setUrl().

◆ setUrl()

void Group::setUrl ( String  url)

Set link destination to use this group as a hyperlink.

References url().

Referenced by url().

◆ count()

int ipe::Group::count ( ) const
inline

Return number of component objects.

◆ object()

const Object* ipe::Group::object ( int  i) const
inline

Return object at index i.

◆ begin()

◆ end()

◆ push_back()

void Group::push_back ( Object obj)

Add an object.

Takes ownership of the object. This will panic if the object shares its implementation! The method is only useful right after construction of the group.

References ipe::Object::pinned().

Referenced by end(), and ipe::ImlParser::parseObject().

◆ saveComponentsAsXml()

void Group::saveComponentsAsXml ( Stream stream) const

Save all the components, one by one, in XML format.

References begin(), and end().

Referenced by end(), and saveAsXml().

◆ checkStyle()

void Group::checkStyle ( const Cascade sheet,
AttributeSeq seq 
) const
virtual

Check all symbolic attributes.

Reimplemented from ipe::Object.

References begin(), and end().

Referenced by end().

◆ getAttribute()

Attribute Group::getAttribute ( Property  prop) const
virtualnoexcept

Get setting of an attribute of this object.

If object does not have this attribute, returnes "undefined" attribute.

Reimplemented from ipe::Object.

References ipe::EPropDecoration, and ipe::Object::getAttribute().

Referenced by end().

◆ setAttribute()

bool Group::setAttribute ( Property  prop,
Attribute  value 
)
virtual

Set attribute on all children.

Reimplemented from ipe::Object.

References ipe::EPropDecoration, ipe::EPropPinned, ipe::EPropTransformations, and ipe::Object::setAttribute().

Referenced by end().


The documentation for this class was generated from the following files:
  • ipegroup.h
  • ipegroup.cpp

ipe-7.2.13/build/doc/classipe_1_1_fonts-members.html0000644000175000017500000000633413561570220022100 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Fonts Member List

This is the complete list of members for ipe::Fonts, including all inherited members.

Fonts(const PdfResourceBase *resources)ipe::Fonts
freetypeVersion()ipe::Fontsstatic
getFace(const PdfDict *d)ipe::Fonts
resources() const noexceptipe::Fontsinline
screenFont()ipe::Fontsstatic

ipe-7.2.13/build/doc/structipe_1_1_symbol-members.html0000644000175000017500000001011713561570220022465 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::Symbol Member List

This is the complete list of members for ipe::Symbol, including all inherited members.

iObjectipe::Symbol
iSnapipe::Symbol
iTransformationsipe::Symbol
iXFormipe::Symbol
operator=(const Symbol &rhs)ipe::Symbol
Symbol()ipe::Symbol
Symbol(Object *object)ipe::Symbol
Symbol(const Symbol &rhs)ipe::Symbol
~Symbol()ipe::Symbol

ipe-7.2.13/build/doc/previous.png0000644000175000017500000000212513561570220016462 0ustar otfriedotfried‰PNG  IHDR D¤ŠÆsRGB®ÎégAMA± üa cHRMz&€„ú€èu0ê`:˜pœºQ<PLTEÿÿÿ™ÌÿÂõ†¹ì|¯âs¦ÙiœÏ_’ÅV‰¼L²Cv©:m 0c–&YŒPƒFy =p3f sx pHYsÄÄ•+²IDAT8O͓˃ EyµXÅÿÿÙB.P…@·fåLŽÌÉ%ù§ÄÓë©^W¯«äv¦ ææý”£þ~ïË èú^5sÀêo],°è/}lèY&VXý G@A­#Na&ýÓI¡ 7¨O<Á΀w j†’DÆA³»“€<ÆÞ¦L?P¢Ž;Ih¬£$e…ɺÜ&Fi–¥:¤¢­ £íc§ñ¸‡3NròÄ¿?q-L¢ÚIEND®B`‚ipe-7.2.13/build/doc/functions.html0000644000175000017500000002513613561570220017005 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- a -


ipe-7.2.13/build/doc/manual_48.html0000644000175000017500000003562113561570220016565 0ustar otfriedotfried Ipe Manual -- 9.3 Ipe object elements
9.4 The <ipestyle> element9 The Ipe file format9.2 The <page> element9.3 Ipe object elements

9.3 Ipe object elements

Common attributes

layer
(optional) Only allowed on "top-level" objects, that is, objects directly inside a <page> element. The value indicates into which layer the object goes. If the attribute is missing, the object goes into the same layer as the preceding object. If the first object has no layer attribute, it goes into the layer defined first in the page, or the default "alpha" layer.
matrix
(optional) A sequence of six real numbers, separated by white space, indicating a transformation matrix for all coordinates inside the element (including embedded elements if this is a <group> element). A missing matrix attribute is interpreted as the identity matrix.
pin
(optional) Possible values are yes (object is fixed on the page), h (object is pinned horizontally, but can move in the vertical direction), and v (the opposite). The default is no pinning.
transformations
(optional) This attribute determines how objects can be deformed by transformations. Possible values are affine (the default), rigid, and translations.

Color attribute values

A color attribute value is either a symbolic name defined in one of the style sheets of the document, one of the predefined names "black" or "white", a single real number between 0 (black) and 1 (white) indicating a gray level, or three real numbers in the range [0,1] indicating the red, green, and blue component (in this order), separated by white space.

Path construction operators

Graphical shapes in Ipe are described using a series of "path construction operators" with arguments. This generalizes the PDF path construction syntax.

Each operator follows its arguments. The operators are

  • m (moveto) (1 point argument): begin new subpath.
  • l (lineto) (1 point argument): add straight segment to subpath.
  • c (cubic B-spline) (n point arguments): add a uniform cubic B-spline with n+1 control points (the current position plus the n arguments). If n = 3, this is equivalent to a single cubic Bézier spline, if n = 2 it is equivalent to a single quadratic Bézier spline.
  • q (deprecated) (2 point arguments): identical to 'c'.
  • e (ellipse) (1 matrix argument): add a closed subpath consisting of an ellipse, the ellipse is the image of the unit circle under the transformation described by the matrix.
  • a (arcto) (1 matrix argument, 1 point argument): add an elliptic arc, on the ellipse describe by the matrix, from current position to given point.
  • s (deprecated) (n point arguments): add an "old style" uniform cubic B-spline as used by Ipe up to version 7.1.6.
  • u (closed spline) (n point arguments): add a closed subpath consisting of a closed uniform B-spline with n control points,
  • h (closepath) (no arguments): close the current subpath. No more segments can be added to this subpath, so the next operator (if there is one) must start a new subpath.
Paths consisting of more than one closed loop are allowed. A subpath can consist of any mix of straight segments, elliptic arcs, and B-splines.

9.3.1 The <group> element

The <group> element allows to group objects together, so that they appear as one in the user interface.

Attributes

clip
(optional) The value is a sequence of path construction operators, forming a clipping path for the objects inside the group.
url
(optional) The value is a link action (and the attribute name is somewhat of a misnomer, as actions do not need to be URLs—see the description of group objects).
decoration
(optional) The name of a decoration symbol. The default is normal, meaning no decoration.

The contents of the <group> element is a series of Ipe object elements.

9.3.2 The <image> element

Attributes

bitmap
(required) Value is an integer referring to a bitmap defined in a <bitmap> element in the document,
rect
(required) Four real coordinates separated by white space, in the order x1, y1, x2, y2, indicating two opposite corners of the image in Ipe coordinates).

The image element is normally empty. However, it is allowed to omit the bitmap attribute. In this case, the <image> must carry all the attributes of the <bitmap> element, with the exception of id. The element contents is then the bitmap data, as described for <bitmap>.

9.3.3 The <use> element

The <use> element refers to a symbol (an Ipe object) defined in the style sheet. The attributes stroke, fill, pen, and size make sense only when the symbol accepts these parameters.

Attributes

name
(required) The name of a symbol defined in a style sheet of the document.
pos
(optional) Position of the symbol on the page (two real numbers, separated by white space). This is the location of the origin of the symbol coordinate system. The default is the origin.
stroke
(optional) A stroke color (used whereever the symbol uses the symbolic color "sym-stroke"). The default is black.
fill
(optional) A fill color (used whereever the symbol uses the symbolic color "sym-fill"). The default is white.
pen
(optional) A line width (used whereever the symbol uses the symbolic value "sym-pen"). The default is "normal".
size
(optional) The size of the symbol, either a symbolic size (of type "symbol size"), or an absolute scaling factor. The default is 1.0.

The <use> element must be empty.

9.3.4 The <text> element

Attributes

stroke
(optional) The stroke color. If the attribute is missing, black will be used.
type
(optional) Possible values are label (the default) and minipage.
size
(optional) The font size—either a symbolic name defined in a style sheet, or a real number. The default is "normal".
pos
(required) Two real numbers separated by white space, defining the position of the text on the paper.
width
(required for minipage objects, optional for label objects) The width of the object in points.
height
(optional) The total height of the object in points.
depth
(optional) The depth of the object in points.
valign
(optional) Possible values are top (default for a minipage object), bottom (default for a label object), center, and baseline.
halign
(optional, label only) Possible values are left, right, and center. left is the default. This determines the position of the reference point with respect to the text box.
style
(optional, minipage only) Selects a LaTeX "style" to be used for formatting the text, and must be a symbolic name defined in a style sheet. The standard style sheet defines the styles "normal", "center", "itemize", and "item". If the attribute is not present, the "normal" style is applied.
opacity
(optional) Opacity of the element. This must be a symbolic name. The default is "normal", meaning fully opaque.

The dimensions are recomputed by Ipe when running LaTeX, with the exception of width for minipage objects whose width is fixed.

The contents of the <text> element must be a legal LaTeX fragment that can be interpreted by LaTeX inside \hbox, possibly using the macros or packages defined in the preamble.

9.3.5 The <path> element

Attributes

stroke
(optional) The stroke color. If the attribute is missing, the shape will not be stroked.
fill
(optional) The fill color. If the attribute is missing, the shape will not be filled.
dash
(optional) Either a symbolic name defined in a style sheet, or a dash pattern in PDF format, such as "[3 1] 0" for "three pixels on, one off, starting with the first pixel". If the attribute is missing, a solid line is drawn.
pen
(optional) The line width, either symbolic (defined in a style sheet), or as a single real number. The default value is "normal".
cap
(optional) The line cap setting of PDF as an integer. If the argument is missing, the setting from the style sheet is used.
join
(optional) The line join setting of PDF as an integer. If the argument is missing, the setting from the style sheet is used.
fillrule
(optional) Possible values are wind and eofill, selecting one of two algorithms for determining whether a point lies inside a filled object. If the argument is missing, the setting from the style sheet is used.
arrow
(optional) The value consists of a symbolic name, say "triangle" for an arrow type (a symbol with name "arrow/triangle(spx)"), followed by a slash and the size of the arrow. The size is either a symbolic name (of type "arrowsize") defined in a style sheet, or a real number. If the attribute is missing, no arrow is drawn.
rarrow
(optional) Same for an arrow in the reverse direction (at the beginning of the first subpath).
opacity
(optional) Opacity of the element. This must be a symbolic name. The default is "normal", meaning fully opaque.
tiling
(optional) A tiling pattern to be used to fill the element. The default is not to tile the element. If the element is not filled, then the tiling pattern is ignored.
gradient
(optional) A gradient pattern to be used to fill the element. If the element is not filled, then the gradient pattern is ignored. (The fill color is only used for rendering where gradients are not available, for instance currently in Postscript.) If gradient is set, then tiling is ignored.

The contents of the <path> element is a sequence of path construction operators. The entire shape will be stroked and/or filled with a single stroke and fill operation.

ipe-7.2.13/build/doc/manual_44.html0000644000175000017500000000640513561570220016557 0ustar otfriedotfried Ipe Manual -- 8.10 Using cygwin latex on Windows
8 Advanced topics8.9 Running Ipe under Wine on Linux8.10 Using cygwin latex on Windows

8.10 Using cygwin latex on Windows

If you have cygwin on your Windows computer and wish to use the cygwin installation of Latex (rather than MikTeX or texlive), create a small text file called ipe.conf and place it in the top-level Ipe directory (that is, the directory that contains readme.txt and gpl.txt). The contents of the file should be:

IPETEXFORMAT=1
IPELATEXPATH=c:\cygwin\bin
(You'll need to check the exact path containing your cygwin binaries. On 64 bit cygwin, it's probably c:\cygwin64\bin.)

You can define any other environment variable in the same file.

You need the cygwin packages texlive-collection-latex and texlive-collection-latexrecommended.

Note that it's not necessary to add the cygwin path to your general Windows path.

ipe-7.2.13/build/doc/classipe_1_1_string-members.html0000644000175000017500000002662513561570220022262 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::String Member List

This is the complete list of members for ipe::String, including all inherited members.

append(const String &rhs) noexceptipe::String
append(const char *rhs) noexceptipe::String
append(char ch) noexceptipe::String
data() const noexceptipe::Stringinline
empty() const noexceptipe::Stringinline
erase() noexceptipe::String
find(char ch) const noexceptipe::String
find(const char *rhs) const noexceptipe::String
getLine(int &index) const noexceptipe::String
hasPrefix(const char *rhs) const noexceptipe::String
left(int i) const noexceptipe::Stringinline
operator!=(const String &rhs) const noexceptipe::Stringinline
operator!=(const char *rhs) const noexceptipe::Stringinline
operator+(const String &rhs) const noexceptipe::String
operator+=(const String &rhs) noexceptipe::Stringinline
operator+=(const char *rhs) noexceptipe::Stringinline
operator+=(char ch) noexceptipe::Stringinline
operator<(const String &rhs) const noexceptipe::String
operator=(const String &rhs) noexceptipe::String
operator==(const String &rhs) const noexceptipe::String
operator==(const char *rhs) const noexceptipe::String
operator[](int i) const noexceptipe::Stringinline
rfind(char ch) const noexceptipe::String
right(int i) const noexceptipe::String
size() const noexceptipe::Stringinline
String() noexceptipe::String
String(const char *str) noexceptipe::String
String(const char *str, int len) noexceptipe::String
String(const String &rhs) noexceptipe::String
String(const String &rhs, int index, int len) noexceptipe::String
substr(int i, int len=-1) const noexceptipe::Stringinline
unicode(int &index) const noexceptipe::String
withData(char *data, int len=0) noexceptipe::Stringstatic
z() const noexceptipe::String
~String() noexceptipe::String

ipe-7.2.13/build/doc/functions_f.html0000644000175000017500000001625213561570220017311 0ustar otfriedotfried Ipelib: Class Members
Ipelib
Here is a list of all class members with links to the classes they belong to:

- f -


ipe-7.2.13/build/doc/classipe_1_1_pdf_parser.html0000644000175000017500000004640213561570220021444 0ustar otfriedotfried Ipelib: ipe::PdfParser Class Reference
Ipelib
ipe::PdfParser Class Reference

#include <ipepdfparser.h>

Public Member Functions

 PdfParser (DataSource &source)
 
void getChar ()
 
bool eos () const noexcept
 
PdfToken token () const noexcept
 
void getToken ()
 
PdfObjgetObject ()
 
PdfObjgetObjectDef ()
 
PdfDictgetTrailer ()
 
void skipXRef ()
 

Detailed Description

PDF parser.

The parser understands the syntax of PDF files, but very little of its semantics. It is meant to be able to parse PDF documents created by Ipe for loading, and to extract information from PDF files created by Pdflatex or Xelatex.

The parser reads a PDF file sequentially from front to back, ignores the contents of 'xref' sections, stores only generation 0 objects, and stops after reading the first 'trailer' section (so it cannot deal with files with incremental updates). It cannot handle stream objects whose /Length entry has been deferred (using an indirect object).

Constructor & Destructor Documentation

◆ PdfParser()

PdfParser::PdfParser ( DataSource source)

Construct with a data source.

Referenced by ipe::PdfDict::inflate().

Member Function Documentation

◆ getChar()

void ipe::PdfParser::getChar ( )
inline

◆ eos()

bool ipe::PdfParser::eos ( ) const
inlinenoexcept

◆ token()

PdfToken ipe::PdfParser::token ( ) const
inlinenoexcept

◆ getToken()

◆ getObject()

◆ getObjectDef()

PdfObj * PdfParser::getObjectDef ( )

Parse an object definition (current token is object number).

References ipe::PdfToken::ENumber, and ipe::PdfToken::EOp.

Referenced by ipe::PdfFile::parse().

◆ getTrailer()

PdfDict * PdfParser::getTrailer ( )

Parse trailer dictionary (current token is 'trailer')

References ipe::PdfToken::EDictBg.

Referenced by ipe::PdfFile::parse().

◆ skipXRef()

void PdfParser::skipXRef ( )

Skip xref table (current token is 'xref')

Referenced by ipe::PdfFile::parse().


The documentation for this class was generated from the following files:
  • ipepdfparser.h
  • ipepdfparser.cpp

ipe-7.2.13/build/doc/manual_24.html0000644000175000017500000001353613561570220016560 0ustar otfriedotfried Ipe Manual -- 5.3 Angular snapping
5.4 Interaction of the snapping modes5 Snapping5.2 Context snapping5.3 Angular snapping

5.3 Angular snapping

When angular snapping is enabled, the mouse position is restricted to lie on a set of lines through the origin of your current axis system. The lines are the lines whose angle with the base direction is an integer multiple of the snap angle. The snap angle can be set in the second box in the Snap toolbar. The values are indicated in degrees.

For a snap angle of 180 degrees, snapping is to a single line through the current origin.

In order to use angular snapping, it is important to set the axis system correctly. To set the origin, move the mouse to the correct position, and press the F1-key. Note that angular snapping is disabled while setting the origin. This way you can set a new origin for angular snapping without leaving the mode first. Once the origin has been set, the base direction is set by moving to a point on the desired base line, and pressing the F2-key. Again, angular snapping is disabled. Together, origin and base direction determine the current axis system. Remember that the origin is also used as the fix-point of scale, stretch, and rotate operations, if it is set.

You can hide the current axis system by pressing Ctrl+F1. This also turns off angular snapping, but preserves origin and orientation of the axes. To reset the orientation (such that the x-axis is horizontal, use Ctrl+F2).

You can set origin and base direction at the same time by pressing F3 when the mouse is very near (or snapped to) an edge of a polygonal object. The origin is set to an endpoint of the edge, and the base direction is aligned with it. This is useful to make objects parallel to a given edge.

For drawing rectilinear or c-oriented polygons, the origin should be set to the previous vertex at every step. This can be done by pressing F1 every time you click the left mouse button, but that would not be very convenient. Therefore, Ipe offers a second angular snap mode, called automatic angular snapping. This mode uses an independent origin, which is automatically set every time you add a vertex when creating a polygonal object. Note that while the origin is independent of the origin set by F1, the base direction and the snap angle used by automatic angular snapping is the same as for angular snapping. Hence, you can align the axis system with some edge of your drawing using F3, and then use automatic angular snapping to draw a new object that is parallel or orthogonal to this edge.

This snapping mode has another advantage: It remains silent and ineffective until you start creating a polygonal object. So, even with automatic angular snapping already turned on, you can still freely place the first point of a polygon, and then the remaining vertices will be properly aligned to make a c-oriented polygon.

The automatic angular snapping mode is never active for any non-polygonal object. In particular, to move an object in a prescribed direction, you have to use normal angular snapping.

A final note: Many things that can be done with angular snapping can also be done by drawing auxiliary lines and using context snapping. It is mostly a matter of taste and exercise to figure out which mode suits you best.

ipe-7.2.13/build/doc/manual_56.html0000644000175000017500000000677113561570220016570 0ustar otfriedotfried Ipe Manual -- 11.5 Ipe6upgrade: convert Ipe 6 files to Ipe 7 file format
11.6 Ipescript: running Ipe scripts11 The command line programs11.4 Ipeextract: extract XML stream from Ipe file11.5 Ipe6upgrade: convert Ipe 6 files to Ipe 7 file format

11.5 Ipe6upgrade: convert Ipe 6 files to Ipe 7 file format

Ipe6upgrade takes as input a file created by any version of Ipe 6, and saves in the format of Ipe 7.0.0.

ipe6upgrade infile [ outfile ]
If not provided, the outfile is guessed by adding the extension "ipe" to the infile's basename.

To reuse an Ipe 6 document in EPS or PDF format, you first run "ipeextract", which extracts the XML stream inside the document and saves it as an XML file. The Ipe 6 XML document can then be converted to Ipe 7 format using "ipe6upgrade".

If your old figure is figure.pdf, then the command

ipeextract figure.pdf
will save the XML stream as figure.xml. Then run
ipe6upgrade figure.xml
which will save your document in Ipe 7 format as figure.ipe. All contents of the original document should have been preserved.
ipe-7.2.13/build/doc/classipe_1_1_pdf_name-members.html0000644000175000017500000001324513561570220022517 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::PdfName Member List

This is the complete list of members for ipe::PdfName, including all inherited members.

array() const noexceptipe::PdfObjvirtual
boolean() const noexceptipe::PdfObjvirtual
dict() const noexceptipe::PdfObjvirtual
name() const noexceptipe::PdfNamevirtual
null() const noexceptipe::PdfObjvirtual
number() const noexceptipe::PdfObjvirtual
PdfName(const String &val)ipe::PdfNameinlineexplicit
ref() const noexceptipe::PdfObjvirtual
repr() const noexceptipe::PdfObj
string() const noexceptipe::PdfObjvirtual
value() const noexceptipe::PdfNameinline
write(Stream &stream, const PdfRenumber *renumber, bool inflate) const noexceptipe::PdfNamevirtual
~PdfObj()=0ipe::PdfObjpure virtual

ipe-7.2.13/build/doc/classipe_1_1_ipelet_helper-members.html0000644000175000017500000001206713561570220023570 0ustar otfriedotfried Ipelib: Member List
Ipelib
ipe::IpeletHelper Member List

This is the complete list of members for ipe::IpeletHelper, including all inherited members.

EDiscardCancelButtons enum valueipe::IpeletHelper
EOkButton enum valueipe::IpeletHelper
EOkCancelButtons enum valueipe::IpeletHelper
ESaveDiscardCancelButtons enum valueipe::IpeletHelper
EYesNoCancelButtons enum valueipe::IpeletHelper
getParameter(const char *key)=0ipe::IpeletHelperpure virtual
getString(const char *prompt, String &str)=0ipe::IpeletHelperpure virtual
message(const char *msg)=0ipe::IpeletHelperpure virtual
messageBox(const char *text, const char *details, int buttons)=0ipe::IpeletHelperpure virtual
~IpeletHelper()=0ipe::IpeletHelperpure virtual

ipe-7.2.13/build/doc/manual_33.html0000644000175000017500000000645113561570220016556 0ustar otfriedotfried Ipe Manual -- 7.5 Ipe symbols used from text objects
7 Presentations7.4 Gradient patterns7.5 Ipe symbols used from text objects

7.5 Ipe symbols used from text objects

Presentations often make use of itemize environments. You can make these prettier in a number of ways:

You can color your bullets:

<preamble>
\def\labelitemi{\LARGE\textcolor{red}{$\bullet$}}
</preamble>

Enumeration numbers could be put in a colored box:

<preamble>
\newcommand{\labelenumi}{\fbox{\Roman{enumi}}}
</preamble>

You could use the Dingbats font for nice enumerations, for instance by putting \usepackage{pifont} in your preamble, and then having text objects with \begin{dinglist}{43} or \begin{dingautolist}{172} (or use 182, 192, 202 for various circled numbers).

You can mark items as "good" and "bad" using these "bullets":

Bad item: \textcolor{red}{\ding{55}}
Good item: \textcolor{green}{\ding{52}}

ipe-7.2.13/build/doc/classipe_1_1_iml_parser.html0000644000175000017500000014412113561570220021451 0ustar otfriedotfried Ipelib: ipe::ImlParser Class Reference
Ipelib

#include <ipeiml.h>

Inherits ipe::XmlParser.

Inherited by PdfStreamParser, and PsStreamParser.

Public Types

enum  Errors { ESuccess = 0, EVersionTooOld, EVersionTooRecent, ESyntaxError }
 

Public Member Functions

 ImlParser (DataSource &source)
 
int parseDocument (Document &doc)
 
bool parsePage (Page &page)
 
ObjectparseObject (String tag, Page *page=nullptr, int *currentLayer=nullptr)
 
StyleSheetparseStyleSheet ()
 
bool parseStyle (StyleSheet &sheet)
 
PageparsePageSelection ()
 
virtual Buffer pdfStream (int objNum)
 
bool parseBitmap ()
 
- Public Member Functions inherited from ipe::XmlParser
 XmlParser (DataSource &source)
 
virtual ~XmlParser ()
 
int parsePosition () const
 
String parseToTag ()
 
bool parseAttributes (XmlAttributes &attr, bool qm=false)
 
bool parsePCDATA (String tag, String &pcdata)
 
bool isTagChar (int ch)
 
void getChar ()
 
bool eos ()
 
void skipWhitespace ()
 

Additional Inherited Members

- Protected Member Functions inherited from ipe::XmlParser
String parseToTagX ()
 
- Protected Attributes inherited from ipe::XmlParser
DataSourceiSource
 
String iTopElement
 
int iCh
 
int iPos
 

Detailed Description

XML Parser for Ipe documents and style sheets.

A recursive descent parser for the XML streams.

After experimenting with various XML parsing frameworks, this turned out to work best for Ipe.

Member Enumeration Documentation

◆ Errors

Enumerator
ESuccess 
EVersionTooOld 
EVersionTooRecent 
ESyntaxError 

Constructor & Destructor Documentation

◆ ImlParser()

ImlParser::ImlParser ( DataSource source)
explicit

Member Function Documentation

◆ parseDocument()

◆ parsePage()

◆ parseObject()

◆ parseStyleSheet()

StyleSheet * ImlParser::parseStyleSheet ( )

parse a complete style sheet.

On calling, stream must be before the 'ipestyle' tag. A <?xml> tag is allowed.

References ipe::XmlParser::parseAttributes(), parseStyle(), and ipe::XmlParser::parseToTag().

Referenced by ipe::Document::setResources(), and ipe::StyleSheet::standard().

◆ parseStyle()

bool ImlParser::parseStyle ( StyleSheet sheet)

Parse a style sheet.

On calling, stream must be just past the style tag.

References ipe::StyleSheet::add(), ipe::StyleSheet::addEffect(), ipe::StyleSheet::addGradient(), ipe::StyleSheet::addSymbol(), ipe::StyleSheet::addTiling(), ipe::Attribute::BLACK(), ipe::Gradient::Stop::color, ipe::Angle::Degrees(), ipe::EAlignBaseline, ipe::EAlignLeft, ipe::EAngleSize, ipe::EArrowSize, ipe::Gradient::EAxial, ipe::EColor, ipe::EDashStyle, ipe::EEvenOddRule, ipe::EGridSize, ipe::Reference::EHasFill, ipe::Reference::EHasPen, ipe::Reference::EHasSize, ipe::Reference::EHasStroke, ipe::ELabelStyle, ipe::String::empty(), ipe::EOpacity, ipe::Lex::eos(), ipe::EPen, ipe::Gradient::ERadial, ipe::ESymbolSize, ipe::ETextSize, ipe::ETextStretch, ipe::ETextStyle, ipe::ETransformationsRigidMotions, ipe::ETransformationsTranslations, ipe::EWindRule, ipe::Reference::flagsFromName(), ipe::Lex::getDouble(), ipe::Lex::getInt(), ipe::XmlAttributes::has(), ipe::Tiling::iAngle, ipe::TextPadding::iBottom, ipe::StyleSheet::TitleStyle::iColor, ipe::StyleSheet::PageNumberStyle::iColor, ipe::Layout::iCrop, ipe::StyleSheet::TitleStyle::iDefined, ipe::StyleSheet::PageNumberStyle::iDefined, ipe::Effect::iDuration, ipe::Effect::iEffect, ipe::Gradient::iExtend, ipe::Layout::iFrameSize, ipe::StyleSheet::TitleStyle::iHorizontalAlignment, ipe::StyleSheet::PageNumberStyle::iHorizontalAlignment, ipe::TextPadding::iLeft, ipe::Gradient::iMatrix, ipe::Layout::iOrigin, ipe::Layout::iPaperSize, ipe::Layout::iParagraphSkip, ipe::StyleSheet::TitleStyle::iPos, ipe::StyleSheet::PageNumberStyle::iPos, ipe::Gradient::iRadius, ipe::TextPadding::iRight, ipe::Attribute::isColor(), ipe::Fixed::isInteger(), ipe::StyleSheet::TitleStyle::iSize, ipe::StyleSheet::PageNumberStyle::iSize, ipe::Symbol::iSnap, ipe::Attribute::isNumber(), ipe::Attribute::isSymbolic(), ipe::Tiling::iStep, ipe::Gradient::iStops, ipe::StyleSheet::PageNumberStyle::iText, ipe::TextPadding::iTop, ipe::Symbol::iTransformations, ipe::Effect::iTransitionTime, ipe::Gradient::iType, ipe::Gradient::iV, ipe::StyleSheet::TitleStyle::iVerticalAlignment, ipe::StyleSheet::PageNumberStyle::iVerticalAlignment, ipe::Tiling::iWidth, ipe::Symbol::iXForm, ipe::Attribute::makeColor(), ipe::Attribute::makeDashStyle(), ipe::Text::makeHAlign(), ipe::Attribute::makeScalar(), ipe::Attribute::makeTextSize(), ipe::Text::makeVAlign(), ipe::Attribute::NORMAL(), ipe::Attribute::number(), ipe::Gradient::Stop::offset, ipe::XmlParser::parseAttributes(), parseBitmap(), parseObject(), ipe::XmlParser::parsePCDATA(), ipe::XmlParser::parseToTag(), ipe::StyleSheet::setFillRule(), ipe::StyleSheet::setLayout(), ipe::StyleSheet::setLineCap(), ipe::StyleSheet::setLineJoin(), ipe::StyleSheet::setName(), ipe::StyleSheet::setPageNumberStyle(), ipe::StyleSheet::setPreamble(), ipe::StyleSheet::setTextPadding(), ipe::StyleSheet::setTitleStyle(), ipe::size(), ipe::Lex::skipWhitespace(), ipe::XmlAttributes::slash(), ipe::Vector::x, and ipe::Vector::y.

Referenced by parseDocument(), and parseStyleSheet().

◆ parsePageSelection()

Page * ImlParser::parsePageSelection ( )

◆ pdfStream()

Buffer ImlParser::pdfStream ( int  objNum)
virtual

XML contents can refer to data in PDF.

If the XML stream is embedded in a PDF file, XML contents can refer to PDF objects. A derived parser must implement this method to access PDF data.

It is assumed that PDF object objNum is a stream. Its contents (uncompressed!) is returned in a buffer.

Referenced by parseBitmap().

◆ parseBitmap()


The documentation for this class was generated from the following files:
  • ipeiml.h
  • ipeiml.cpp

ipe-7.2.13/build/doc/jquery.js0000644000175000017500000052151113561570220015762 0ustar otfriedotfried/*! * jQuery JavaScript Library v1.7.1 * http://jquery.com/ * * Copyright 2011, John Resig * Dual licensed under the MIT or GPL Version 2 licenses. * http://jquery.org/license * * Includes Sizzle.js * http://sizzlejs.com/ * Copyright 2011, The Dojo Foundation * Released under the MIT, BSD, and GPL Licenses. * * Date: Mon Nov 21 21:11:03 2011 -0500 */ (function(bb,L){var av=bb.document,bu=bb.navigator,bl=bb.location;var b=(function(){var bF=function(b0,b1){return new bF.fn.init(b0,b1,bD)},bU=bb.jQuery,bH=bb.$,bD,bY=/^(?:[^#<]*(<[\w\W]+>)[^>]*$|#([\w\-]*)$)/,bM=/\S/,bI=/^\s+/,bE=/\s+$/,bA=/^<(\w+)\s*\/?>(?:<\/\1>)?$/,bN=/^[\],:{}\s]*$/,bW=/\\(?:["\\\/bfnrt]|u[0-9a-fA-F]{4})/g,bP=/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g,bJ=/(?:^|:|,)(?:\s*\[)+/g,by=/(webkit)[ \/]([\w.]+)/,bR=/(opera)(?:.*version)?[ \/]([\w.]+)/,bQ=/(msie) ([\w.]+)/,bS=/(mozilla)(?:.*? rv:([\w.]+))?/,bB=/-([a-z]|[0-9])/ig,bZ=/^-ms-/,bT=function(b0,b1){return(b1+"").toUpperCase()},bX=bu.userAgent,bV,bC,e,bL=Object.prototype.toString,bG=Object.prototype.hasOwnProperty,bz=Array.prototype.push,bK=Array.prototype.slice,bO=String.prototype.trim,bv=Array.prototype.indexOf,bx={};bF.fn=bF.prototype={constructor:bF,init:function(b0,b4,b3){var b2,b5,b1,b6;if(!b0){return this}if(b0.nodeType){this.context=this[0]=b0;this.length=1;return this}if(b0==="body"&&!b4&&av.body){this.context=av;this[0]=av.body;this.selector=b0;this.length=1;return this}if(typeof b0==="string"){if(b0.charAt(0)==="<"&&b0.charAt(b0.length-1)===">"&&b0.length>=3){b2=[null,b0,null]}else{b2=bY.exec(b0)}if(b2&&(b2[1]||!b4)){if(b2[1]){b4=b4 instanceof bF?b4[0]:b4;b6=(b4?b4.ownerDocument||b4:av);b1=bA.exec(b0);if(b1){if(bF.isPlainObject(b4)){b0=[av.createElement(b1[1])];bF.fn.attr.call(b0,b4,true)}else{b0=[b6.createElement(b1[1])]}}else{b1=bF.buildFragment([b2[1]],[b6]);b0=(b1.cacheable?bF.clone(b1.fragment):b1.fragment).childNodes}return bF.merge(this,b0)}else{b5=av.getElementById(b2[2]);if(b5&&b5.parentNode){if(b5.id!==b2[2]){return b3.find(b0)}this.length=1;this[0]=b5}this.context=av;this.selector=b0;return this}}else{if(!b4||b4.jquery){return(b4||b3).find(b0)}else{return this.constructor(b4).find(b0)}}}else{if(bF.isFunction(b0)){return b3.ready(b0)}}if(b0.selector!==L){this.selector=b0.selector;this.context=b0.context}return bF.makeArray(b0,this)},selector:"",jquery:"1.7.1",length:0,size:function(){return this.length},toArray:function(){return bK.call(this,0)},get:function(b0){return b0==null?this.toArray():(b0<0?this[this.length+b0]:this[b0])},pushStack:function(b1,b3,b0){var b2=this.constructor();if(bF.isArray(b1)){bz.apply(b2,b1)}else{bF.merge(b2,b1)}b2.prevObject=this;b2.context=this.context;if(b3==="find"){b2.selector=this.selector+(this.selector?" ":"")+b0}else{if(b3){b2.selector=this.selector+"."+b3+"("+b0+")"}}return b2},each:function(b1,b0){return bF.each(this,b1,b0)},ready:function(b0){bF.bindReady();bC.add(b0);return this},eq:function(b0){b0=+b0;return b0===-1?this.slice(b0):this.slice(b0,b0+1)},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},slice:function(){return this.pushStack(bK.apply(this,arguments),"slice",bK.call(arguments).join(","))},map:function(b0){return this.pushStack(bF.map(this,function(b2,b1){return b0.call(b2,b1,b2)}))},end:function(){return this.prevObject||this.constructor(null)},push:bz,sort:[].sort,splice:[].splice};bF.fn.init.prototype=bF.fn;bF.extend=bF.fn.extend=function(){var b9,b2,b0,b1,b6,b7,b5=arguments[0]||{},b4=1,b3=arguments.length,b8=false;if(typeof b5==="boolean"){b8=b5;b5=arguments[1]||{};b4=2}if(typeof b5!=="object"&&!bF.isFunction(b5)){b5={}}if(b3===b4){b5=this;--b4}for(;b40){return}bC.fireWith(av,[bF]);if(bF.fn.trigger){bF(av).trigger("ready").off("ready")}}},bindReady:function(){if(bC){return}bC=bF.Callbacks("once memory");if(av.readyState==="complete"){return setTimeout(bF.ready,1)}if(av.addEventListener){av.addEventListener("DOMContentLoaded",e,false);bb.addEventListener("load",bF.ready,false)}else{if(av.attachEvent){av.attachEvent("onreadystatechange",e);bb.attachEvent("onload",bF.ready);var b0=false;try{b0=bb.frameElement==null}catch(b1){}if(av.documentElement.doScroll&&b0){bw()}}}},isFunction:function(b0){return bF.type(b0)==="function"},isArray:Array.isArray||function(b0){return bF.type(b0)==="array"},isWindow:function(b0){return b0&&typeof b0==="object"&&"setInterval" in b0},isNumeric:function(b0){return !isNaN(parseFloat(b0))&&isFinite(b0)},type:function(b0){return b0==null?String(b0):bx[bL.call(b0)]||"object"},isPlainObject:function(b2){if(!b2||bF.type(b2)!=="object"||b2.nodeType||bF.isWindow(b2)){return false}try{if(b2.constructor&&!bG.call(b2,"constructor")&&!bG.call(b2.constructor.prototype,"isPrototypeOf")){return false}}catch(b1){return false}var b0;for(b0 in b2){}return b0===L||bG.call(b2,b0)},isEmptyObject:function(b1){for(var b0 in b1){return false}return true},error:function(b0){throw new Error(b0)},parseJSON:function(b0){if(typeof b0!=="string"||!b0){return null}b0=bF.trim(b0);if(bb.JSON&&bb.JSON.parse){return bb.JSON.parse(b0)}if(bN.test(b0.replace(bW,"@").replace(bP,"]").replace(bJ,""))){return(new Function("return "+b0))()}bF.error("Invalid JSON: "+b0)},parseXML:function(b2){var b0,b1;try{if(bb.DOMParser){b1=new DOMParser();b0=b1.parseFromString(b2,"text/xml")}else{b0=new ActiveXObject("Microsoft.XMLDOM");b0.async="false";b0.loadXML(b2)}}catch(b3){b0=L}if(!b0||!b0.documentElement||b0.getElementsByTagName("parsererror").length){bF.error("Invalid XML: "+b2)}return b0},noop:function(){},globalEval:function(b0){if(b0&&bM.test(b0)){(bb.execScript||function(b1){bb["eval"].call(bb,b1)})(b0)}},camelCase:function(b0){return b0.replace(bZ,"ms-").replace(bB,bT)},nodeName:function(b1,b0){return b1.nodeName&&b1.nodeName.toUpperCase()===b0.toUpperCase()},each:function(b3,b6,b2){var b1,b4=0,b5=b3.length,b0=b5===L||bF.isFunction(b3);if(b2){if(b0){for(b1 in b3){if(b6.apply(b3[b1],b2)===false){break}}}else{for(;b40&&b0[0]&&b0[b1-1])||b1===0||bF.isArray(b0));if(b3){for(;b21?aJ.call(arguments,0):bG;if(!(--bw)){bC.resolveWith(bC,bx)}}}function bz(bF){return function(bG){bB[bF]=arguments.length>1?aJ.call(arguments,0):bG;bC.notifyWith(bE,bB)}}if(e>1){for(;bv
a";bI=bv.getElementsByTagName("*");bF=bv.getElementsByTagName("a")[0];if(!bI||!bI.length||!bF){return{}}bG=av.createElement("select");bx=bG.appendChild(av.createElement("option"));bE=bv.getElementsByTagName("input")[0];bJ={leadingWhitespace:(bv.firstChild.nodeType===3),tbody:!bv.getElementsByTagName("tbody").length,htmlSerialize:!!bv.getElementsByTagName("link").length,style:/top/.test(bF.getAttribute("style")),hrefNormalized:(bF.getAttribute("href")==="/a"),opacity:/^0.55/.test(bF.style.opacity),cssFloat:!!bF.style.cssFloat,checkOn:(bE.value==="on"),optSelected:bx.selected,getSetAttribute:bv.className!=="t",enctype:!!av.createElement("form").enctype,html5Clone:av.createElement("nav").cloneNode(true).outerHTML!=="<:nav>",submitBubbles:true,changeBubbles:true,focusinBubbles:false,deleteExpando:true,noCloneEvent:true,inlineBlockNeedsLayout:false,shrinkWrapBlocks:false,reliableMarginRight:true};bE.checked=true;bJ.noCloneChecked=bE.cloneNode(true).checked;bG.disabled=true;bJ.optDisabled=!bx.disabled;try{delete bv.test}catch(bC){bJ.deleteExpando=false}if(!bv.addEventListener&&bv.attachEvent&&bv.fireEvent){bv.attachEvent("onclick",function(){bJ.noCloneEvent=false});bv.cloneNode(true).fireEvent("onclick")}bE=av.createElement("input");bE.value="t";bE.setAttribute("type","radio");bJ.radioValue=bE.value==="t";bE.setAttribute("checked","checked");bv.appendChild(bE);bD=av.createDocumentFragment();bD.appendChild(bv.lastChild);bJ.checkClone=bD.cloneNode(true).cloneNode(true).lastChild.checked;bJ.appendChecked=bE.checked;bD.removeChild(bE);bD.appendChild(bv);bv.innerHTML="";if(bb.getComputedStyle){bA=av.createElement("div");bA.style.width="0";bA.style.marginRight="0";bv.style.width="2px";bv.appendChild(bA);bJ.reliableMarginRight=(parseInt((bb.getComputedStyle(bA,null)||{marginRight:0}).marginRight,10)||0)===0}if(bv.attachEvent){for(by in {submit:1,change:1,focusin:1}){bB="on"+by;bw=(bB in bv);if(!bw){bv.setAttribute(bB,"return;");bw=(typeof bv[bB]==="function")}bJ[by+"Bubbles"]=bw}}bD.removeChild(bv);bD=bG=bx=bA=bv=bE=null;b(function(){var bM,bU,bV,bT,bN,bO,bL,bS,bR,e,bP,bQ=av.getElementsByTagName("body")[0];if(!bQ){return}bL=1;bS="position:absolute;top:0;left:0;width:1px;height:1px;margin:0;";bR="visibility:hidden;border:0;";e="style='"+bS+"border:5px solid #000;padding:0;'";bP="
";bM=av.createElement("div");bM.style.cssText=bR+"width:0;height:0;position:static;top:0;margin-top:"+bL+"px";bQ.insertBefore(bM,bQ.firstChild);bv=av.createElement("div");bM.appendChild(bv);bv.innerHTML="
t
";bz=bv.getElementsByTagName("td");bw=(bz[0].offsetHeight===0);bz[0].style.display="";bz[1].style.display="none";bJ.reliableHiddenOffsets=bw&&(bz[0].offsetHeight===0);bv.innerHTML="";bv.style.width=bv.style.paddingLeft="1px";b.boxModel=bJ.boxModel=bv.offsetWidth===2;if(typeof bv.style.zoom!=="undefined"){bv.style.display="inline";bv.style.zoom=1;bJ.inlineBlockNeedsLayout=(bv.offsetWidth===2);bv.style.display="";bv.innerHTML="
";bJ.shrinkWrapBlocks=(bv.offsetWidth!==2)}bv.style.cssText=bS+bR;bv.innerHTML=bP;bU=bv.firstChild;bV=bU.firstChild;bN=bU.nextSibling.firstChild.firstChild;bO={doesNotAddBorder:(bV.offsetTop!==5),doesAddBorderForTableAndCells:(bN.offsetTop===5)};bV.style.position="fixed";bV.style.top="20px";bO.fixedPosition=(bV.offsetTop===20||bV.offsetTop===15);bV.style.position=bV.style.top="";bU.style.overflow="hidden";bU.style.position="relative";bO.subtractsBorderForOverflowNotVisible=(bV.offsetTop===-5);bO.doesNotIncludeMarginInBodyOffset=(bQ.offsetTop!==bL);bQ.removeChild(bM);bv=bM=null;b.extend(bJ,bO)});return bJ})();var aS=/^(?:\{.*\}|\[.*\])$/,aA=/([A-Z])/g;b.extend({cache:{},uuid:0,expando:"jQuery"+(b.fn.jquery+Math.random()).replace(/\D/g,""),noData:{embed:true,object:"clsid:D27CDB6E-AE6D-11cf-96B8-444553540000",applet:true},hasData:function(e){e=e.nodeType?b.cache[e[b.expando]]:e[b.expando];return !!e&&!S(e)},data:function(bx,bv,bz,by){if(!b.acceptData(bx)){return}var bG,bA,bD,bE=b.expando,bC=typeof bv==="string",bF=bx.nodeType,e=bF?b.cache:bx,bw=bF?bx[bE]:bx[bE]&&bE,bB=bv==="events";if((!bw||!e[bw]||(!bB&&!by&&!e[bw].data))&&bC&&bz===L){return}if(!bw){if(bF){bx[bE]=bw=++b.uuid}else{bw=bE}}if(!e[bw]){e[bw]={};if(!bF){e[bw].toJSON=b.noop}}if(typeof bv==="object"||typeof bv==="function"){if(by){e[bw]=b.extend(e[bw],bv)}else{e[bw].data=b.extend(e[bw].data,bv)}}bG=bA=e[bw];if(!by){if(!bA.data){bA.data={}}bA=bA.data}if(bz!==L){bA[b.camelCase(bv)]=bz}if(bB&&!bA[bv]){return bG.events}if(bC){bD=bA[bv];if(bD==null){bD=bA[b.camelCase(bv)]}}else{bD=bA}return bD},removeData:function(bx,bv,by){if(!b.acceptData(bx)){return}var bB,bA,bz,bC=b.expando,bD=bx.nodeType,e=bD?b.cache:bx,bw=bD?bx[bC]:bC;if(!e[bw]){return}if(bv){bB=by?e[bw]:e[bw].data;if(bB){if(!b.isArray(bv)){if(bv in bB){bv=[bv]}else{bv=b.camelCase(bv);if(bv in bB){bv=[bv]}else{bv=bv.split(" ")}}}for(bA=0,bz=bv.length;bA-1){return true}}return false},val:function(bx){var e,bv,by,bw=this[0];if(!arguments.length){if(bw){e=b.valHooks[bw.nodeName.toLowerCase()]||b.valHooks[bw.type];if(e&&"get" in e&&(bv=e.get(bw,"value"))!==L){return bv}bv=bw.value;return typeof bv==="string"?bv.replace(aU,""):bv==null?"":bv}return}by=b.isFunction(bx);return this.each(function(bA){var bz=b(this),bB;if(this.nodeType!==1){return}if(by){bB=bx.call(this,bA,bz.val())}else{bB=bx}if(bB==null){bB=""}else{if(typeof bB==="number"){bB+=""}else{if(b.isArray(bB)){bB=b.map(bB,function(bC){return bC==null?"":bC+""})}}}e=b.valHooks[this.nodeName.toLowerCase()]||b.valHooks[this.type];if(!e||!("set" in e)||e.set(this,bB,"value")===L){this.value=bB}})}});b.extend({valHooks:{option:{get:function(e){var bv=e.attributes.value;return !bv||bv.specified?e.value:e.text}},select:{get:function(e){var bA,bv,bz,bx,by=e.selectedIndex,bB=[],bC=e.options,bw=e.type==="select-one";if(by<0){return null}bv=bw?by:0;bz=bw?by+1:bC.length;for(;bv=0});if(!e.length){bv.selectedIndex=-1}return e}}},attrFn:{val:true,css:true,html:true,text:true,data:true,width:true,height:true,offset:true},attr:function(bA,bx,bB,bz){var bw,e,by,bv=bA.nodeType;if(!bA||bv===3||bv===8||bv===2){return}if(bz&&bx in b.attrFn){return b(bA)[bx](bB)}if(typeof bA.getAttribute==="undefined"){return b.prop(bA,bx,bB)}by=bv!==1||!b.isXMLDoc(bA);if(by){bx=bx.toLowerCase();e=b.attrHooks[bx]||(ao.test(bx)?aY:be)}if(bB!==L){if(bB===null){b.removeAttr(bA,bx);return}else{if(e&&"set" in e&&by&&(bw=e.set(bA,bB,bx))!==L){return bw}else{bA.setAttribute(bx,""+bB);return bB}}}else{if(e&&"get" in e&&by&&(bw=e.get(bA,bx))!==null){return bw}else{bw=bA.getAttribute(bx);return bw===null?L:bw}}},removeAttr:function(bx,bz){var by,bA,bv,e,bw=0;if(bz&&bx.nodeType===1){bA=bz.toLowerCase().split(af);e=bA.length;for(;bw=0)}}})});var bd=/^(?:textarea|input|select)$/i,n=/^([^\.]*)?(?:\.(.+))?$/,J=/\bhover(\.\S+)?\b/,aO=/^key/,bf=/^(?:mouse|contextmenu)|click/,T=/^(?:focusinfocus|focusoutblur)$/,U=/^(\w*)(?:#([\w\-]+))?(?:\.([\w\-]+))?$/,Y=function(e){var bv=U.exec(e);if(bv){bv[1]=(bv[1]||"").toLowerCase();bv[3]=bv[3]&&new RegExp("(?:^|\\s)"+bv[3]+"(?:\\s|$)")}return bv},j=function(bw,e){var bv=bw.attributes||{};return((!e[1]||bw.nodeName.toLowerCase()===e[1])&&(!e[2]||(bv.id||{}).value===e[2])&&(!e[3]||e[3].test((bv["class"]||{}).value)))},bt=function(e){return b.event.special.hover?e:e.replace(J,"mouseenter$1 mouseleave$1")};b.event={add:function(bx,bC,bJ,bA,by){var bD,bB,bK,bI,bH,bF,e,bG,bv,bz,bw,bE;if(bx.nodeType===3||bx.nodeType===8||!bC||!bJ||!(bD=b._data(bx))){return}if(bJ.handler){bv=bJ;bJ=bv.handler}if(!bJ.guid){bJ.guid=b.guid++}bK=bD.events;if(!bK){bD.events=bK={}}bB=bD.handle;if(!bB){bD.handle=bB=function(bL){return typeof b!=="undefined"&&(!bL||b.event.triggered!==bL.type)?b.event.dispatch.apply(bB.elem,arguments):L};bB.elem=bx}bC=b.trim(bt(bC)).split(" ");for(bI=0;bI=0){bG=bG.slice(0,-1);bw=true}if(bG.indexOf(".")>=0){bx=bG.split(".");bG=bx.shift();bx.sort()}if((!bA||b.event.customEvent[bG])&&!b.event.global[bG]){return}bv=typeof bv==="object"?bv[b.expando]?bv:new b.Event(bG,bv):new b.Event(bG);bv.type=bG;bv.isTrigger=true;bv.exclusive=bw;bv.namespace=bx.join(".");bv.namespace_re=bv.namespace?new RegExp("(^|\\.)"+bx.join("\\.(?:.*\\.)?")+"(\\.|$)"):null;by=bG.indexOf(":")<0?"on"+bG:"";if(!bA){e=b.cache;for(bC in e){if(e[bC].events&&e[bC].events[bG]){b.event.trigger(bv,bD,e[bC].handle.elem,true)}}return}bv.result=L;if(!bv.target){bv.target=bA}bD=bD!=null?b.makeArray(bD):[];bD.unshift(bv);bF=b.event.special[bG]||{};if(bF.trigger&&bF.trigger.apply(bA,bD)===false){return}bB=[[bA,bF.bindType||bG]];if(!bJ&&!bF.noBubble&&!b.isWindow(bA)){bI=bF.delegateType||bG;bH=T.test(bI+bG)?bA:bA.parentNode;bz=null;for(;bH;bH=bH.parentNode){bB.push([bH,bI]);bz=bH}if(bz&&bz===bA.ownerDocument){bB.push([bz.defaultView||bz.parentWindow||bb,bI])}}for(bC=0;bCbA){bH.push({elem:this,matches:bz.slice(bA)})}for(bC=0;bC0?this.on(e,null,bx,bw):this.trigger(e)};if(b.attrFn){b.attrFn[e]=true}if(aO.test(e)){b.event.fixHooks[e]=b.event.keyHooks}if(bf.test(e)){b.event.fixHooks[e]=b.event.mouseHooks}}); /*! * Sizzle CSS Selector Engine * Copyright 2011, The Dojo Foundation * Released under the MIT, BSD, and GPL Licenses. * More information: http://sizzlejs.com/ */ (function(){var bH=/((?:\((?:\([^()]+\)|[^()]+)+\)|\[(?:\[[^\[\]]*\]|['"][^'"]*['"]|[^\[\]'"]+)+\]|\\.|[^ >+~,(\[\\]+)+|[>+~])(\s*,\s*)?((?:.|\r|\n)*)/g,bC="sizcache"+(Math.random()+"").replace(".",""),bI=0,bL=Object.prototype.toString,bB=false,bA=true,bK=/\\/g,bO=/\r\n/g,bQ=/\W/;[0,0].sort(function(){bA=false;return 0});var by=function(bV,e,bY,bZ){bY=bY||[];e=e||av;var b1=e;if(e.nodeType!==1&&e.nodeType!==9){return[]}if(!bV||typeof bV!=="string"){return bY}var bS,b3,b6,bR,b2,b5,b4,bX,bU=true,bT=by.isXML(e),bW=[],b0=bV;do{bH.exec("");bS=bH.exec(b0);if(bS){b0=bS[3];bW.push(bS[1]);if(bS[2]){bR=bS[3];break}}}while(bS);if(bW.length>1&&bD.exec(bV)){if(bW.length===2&&bE.relative[bW[0]]){b3=bM(bW[0]+bW[1],e,bZ)}else{b3=bE.relative[bW[0]]?[e]:by(bW.shift(),e);while(bW.length){bV=bW.shift();if(bE.relative[bV]){bV+=bW.shift()}b3=bM(bV,b3,bZ)}}}else{if(!bZ&&bW.length>1&&e.nodeType===9&&!bT&&bE.match.ID.test(bW[0])&&!bE.match.ID.test(bW[bW.length-1])){b2=by.find(bW.shift(),e,bT);e=b2.expr?by.filter(b2.expr,b2.set)[0]:b2.set[0]}if(e){b2=bZ?{expr:bW.pop(),set:bF(bZ)}:by.find(bW.pop(),bW.length===1&&(bW[0]==="~"||bW[0]==="+")&&e.parentNode?e.parentNode:e,bT);b3=b2.expr?by.filter(b2.expr,b2.set):b2.set;if(bW.length>0){b6=bF(b3)}else{bU=false}while(bW.length){b5=bW.pop();b4=b5;if(!bE.relative[b5]){b5=""}else{b4=bW.pop()}if(b4==null){b4=e}bE.relative[b5](b6,b4,bT)}}else{b6=bW=[]}}if(!b6){b6=b3}if(!b6){by.error(b5||bV)}if(bL.call(b6)==="[object Array]"){if(!bU){bY.push.apply(bY,b6)}else{if(e&&e.nodeType===1){for(bX=0;b6[bX]!=null;bX++){if(b6[bX]&&(b6[bX]===true||b6[bX].nodeType===1&&by.contains(e,b6[bX]))){bY.push(b3[bX])}}}else{for(bX=0;b6[bX]!=null;bX++){if(b6[bX]&&b6[bX].nodeType===1){bY.push(b3[bX])}}}}}else{bF(b6,bY)}if(bR){by(bR,b1,bY,bZ);by.uniqueSort(bY)}return bY};by.uniqueSort=function(bR){if(bJ){bB=bA;bR.sort(bJ);if(bB){for(var e=1;e0};by.find=function(bX,e,bY){var bW,bS,bU,bT,bV,bR;if(!bX){return[]}for(bS=0,bU=bE.order.length;bS":function(bW,bR){var bV,bU=typeof bR==="string",bS=0,e=bW.length;if(bU&&!bQ.test(bR)){bR=bR.toLowerCase();for(;bS=0)){if(!bS){e.push(bV)}}else{if(bS){bR[bU]=false}}}}return false},ID:function(e){return e[1].replace(bK,"")},TAG:function(bR,e){return bR[1].replace(bK,"").toLowerCase()},CHILD:function(e){if(e[1]==="nth"){if(!e[2]){by.error(e[0])}e[2]=e[2].replace(/^\+|\s*/g,"");var bR=/(-?)(\d*)(?:n([+\-]?\d*))?/.exec(e[2]==="even"&&"2n"||e[2]==="odd"&&"2n+1"||!/\D/.test(e[2])&&"0n+"+e[2]||e[2]);e[2]=(bR[1]+(bR[2]||1))-0;e[3]=bR[3]-0}else{if(e[2]){by.error(e[0])}}e[0]=bI++;return e},ATTR:function(bU,bR,bS,e,bV,bW){var bT=bU[1]=bU[1].replace(bK,"");if(!bW&&bE.attrMap[bT]){bU[1]=bE.attrMap[bT]}bU[4]=(bU[4]||bU[5]||"").replace(bK,"");if(bU[2]==="~="){bU[4]=" "+bU[4]+" "}return bU},PSEUDO:function(bU,bR,bS,e,bV){if(bU[1]==="not"){if((bH.exec(bU[3])||"").length>1||/^\w/.test(bU[3])){bU[3]=by(bU[3],null,null,bR)}else{var bT=by.filter(bU[3],bR,bS,true^bV);if(!bS){e.push.apply(e,bT)}return false}}else{if(bE.match.POS.test(bU[0])||bE.match.CHILD.test(bU[0])){return true}}return bU},POS:function(e){e.unshift(true);return e}},filters:{enabled:function(e){return e.disabled===false&&e.type!=="hidden"},disabled:function(e){return e.disabled===true},checked:function(e){return e.checked===true},selected:function(e){if(e.parentNode){e.parentNode.selectedIndex}return e.selected===true},parent:function(e){return !!e.firstChild},empty:function(e){return !e.firstChild},has:function(bS,bR,e){return !!by(e[3],bS).length},header:function(e){return(/h\d/i).test(e.nodeName)},text:function(bS){var e=bS.getAttribute("type"),bR=bS.type;return bS.nodeName.toLowerCase()==="input"&&"text"===bR&&(e===bR||e===null)},radio:function(e){return e.nodeName.toLowerCase()==="input"&&"radio"===e.type},checkbox:function(e){return e.nodeName.toLowerCase()==="input"&&"checkbox"===e.type},file:function(e){return e.nodeName.toLowerCase()==="input"&&"file"===e.type},password:function(e){return e.nodeName.toLowerCase()==="input"&&"password"===e.type},submit:function(bR){var e=bR.nodeName.toLowerCase();return(e==="input"||e==="button")&&"submit"===bR.type},image:function(e){return e.nodeName.toLowerCase()==="input"&&"image"===e.type},reset:function(bR){var e=bR.nodeName.toLowerCase();return(e==="input"||e==="button")&&"reset"===bR.type},button:function(bR){var e=bR.nodeName.toLowerCase();return e==="input"&&"button"===bR.type||e==="button"},input:function(e){return(/input|select|textarea|button/i).test(e.nodeName)},focus:function(e){return e===e.ownerDocument.activeElement}},setFilters:{first:function(bR,e){return e===0},last:function(bS,bR,e,bT){return bR===bT.length-1},even:function(bR,e){return e%2===0},odd:function(bR,e){return e%2===1},lt:function(bS,bR,e){return bRe[3]-0},nth:function(bS,bR,e){return e[3]-0===bR},eq:function(bS,bR,e){return e[3]-0===bR}},filter:{PSEUDO:function(bS,bX,bW,bY){var e=bX[1],bR=bE.filters[e];if(bR){return bR(bS,bW,bX,bY)}else{if(e==="contains"){return(bS.textContent||bS.innerText||bw([bS])||"").indexOf(bX[3])>=0}else{if(e==="not"){var bT=bX[3];for(var bV=0,bU=bT.length;bV=0)}}},ID:function(bR,e){return bR.nodeType===1&&bR.getAttribute("id")===e},TAG:function(bR,e){return(e==="*"&&bR.nodeType===1)||!!bR.nodeName&&bR.nodeName.toLowerCase()===e},CLASS:function(bR,e){return(" "+(bR.className||bR.getAttribute("class"))+" ").indexOf(e)>-1},ATTR:function(bV,bT){var bS=bT[1],e=by.attr?by.attr(bV,bS):bE.attrHandle[bS]?bE.attrHandle[bS](bV):bV[bS]!=null?bV[bS]:bV.getAttribute(bS),bW=e+"",bU=bT[2],bR=bT[4];return e==null?bU==="!=":!bU&&by.attr?e!=null:bU==="="?bW===bR:bU==="*="?bW.indexOf(bR)>=0:bU==="~="?(" "+bW+" ").indexOf(bR)>=0:!bR?bW&&e!==false:bU==="!="?bW!==bR:bU==="^="?bW.indexOf(bR)===0:bU==="$="?bW.substr(bW.length-bR.length)===bR:bU==="|="?bW===bR||bW.substr(0,bR.length+1)===bR+"-":false},POS:function(bU,bR,bS,bV){var e=bR[2],bT=bE.setFilters[e];if(bT){return bT(bU,bS,bR,bV)}}}};var bD=bE.match.POS,bx=function(bR,e){return"\\"+(e-0+1)};for(var bz in bE.match){bE.match[bz]=new RegExp(bE.match[bz].source+(/(?![^\[]*\])(?![^\(]*\))/.source));bE.leftMatch[bz]=new RegExp(/(^(?:.|\r|\n)*?)/.source+bE.match[bz].source.replace(/\\(\d+)/g,bx))}var bF=function(bR,e){bR=Array.prototype.slice.call(bR,0);if(e){e.push.apply(e,bR);return e}return bR};try{Array.prototype.slice.call(av.documentElement.childNodes,0)[0].nodeType}catch(bP){bF=function(bU,bT){var bS=0,bR=bT||[];if(bL.call(bU)==="[object Array]"){Array.prototype.push.apply(bR,bU)}else{if(typeof bU.length==="number"){for(var e=bU.length;bS";e.insertBefore(bR,e.firstChild);if(av.getElementById(bS)){bE.find.ID=function(bU,bV,bW){if(typeof bV.getElementById!=="undefined"&&!bW){var bT=bV.getElementById(bU[1]);return bT?bT.id===bU[1]||typeof bT.getAttributeNode!=="undefined"&&bT.getAttributeNode("id").nodeValue===bU[1]?[bT]:L:[]}};bE.filter.ID=function(bV,bT){var bU=typeof bV.getAttributeNode!=="undefined"&&bV.getAttributeNode("id");return bV.nodeType===1&&bU&&bU.nodeValue===bT}}e.removeChild(bR);e=bR=null})();(function(){var e=av.createElement("div");e.appendChild(av.createComment(""));if(e.getElementsByTagName("*").length>0){bE.find.TAG=function(bR,bV){var bU=bV.getElementsByTagName(bR[1]);if(bR[1]==="*"){var bT=[];for(var bS=0;bU[bS];bS++){if(bU[bS].nodeType===1){bT.push(bU[bS])}}bU=bT}return bU}}e.innerHTML="";if(e.firstChild&&typeof e.firstChild.getAttribute!=="undefined"&&e.firstChild.getAttribute("href")!=="#"){bE.attrHandle.href=function(bR){return bR.getAttribute("href",2)}}e=null})();if(av.querySelectorAll){(function(){var e=by,bT=av.createElement("div"),bS="__sizzle__";bT.innerHTML="

";if(bT.querySelectorAll&&bT.querySelectorAll(".TEST").length===0){return}by=function(b4,bV,bZ,b3){bV=bV||av;if(!b3&&!by.isXML(bV)){var b2=/^(\w+$)|^\.([\w\-]+$)|^#([\w\-]+$)/.exec(b4);if(b2&&(bV.nodeType===1||bV.nodeType===9)){if(b2[1]){return bF(bV.getElementsByTagName(b4),bZ)}else{if(b2[2]&&bE.find.CLASS&&bV.getElementsByClassName){return bF(bV.getElementsByClassName(b2[2]),bZ)}}}if(bV.nodeType===9){if(b4==="body"&&bV.body){return bF([bV.body],bZ)}else{if(b2&&b2[3]){var bY=bV.getElementById(b2[3]);if(bY&&bY.parentNode){if(bY.id===b2[3]){return bF([bY],bZ)}}else{return bF([],bZ)}}}try{return bF(bV.querySelectorAll(b4),bZ)}catch(b0){}}else{if(bV.nodeType===1&&bV.nodeName.toLowerCase()!=="object"){var bW=bV,bX=bV.getAttribute("id"),bU=bX||bS,b6=bV.parentNode,b5=/^\s*[+~]/.test(b4);if(!bX){bV.setAttribute("id",bU)}else{bU=bU.replace(/'/g,"\\$&")}if(b5&&b6){bV=bV.parentNode}try{if(!b5||b6){return bF(bV.querySelectorAll("[id='"+bU+"'] "+b4),bZ)}}catch(b1){}finally{if(!bX){bW.removeAttribute("id")}}}}}return e(b4,bV,bZ,b3)};for(var bR in e){by[bR]=e[bR]}bT=null})()}(function(){var e=av.documentElement,bS=e.matchesSelector||e.mozMatchesSelector||e.webkitMatchesSelector||e.msMatchesSelector;if(bS){var bU=!bS.call(av.createElement("div"),"div"),bR=false;try{bS.call(av.documentElement,"[test!='']:sizzle")}catch(bT){bR=true}by.matchesSelector=function(bW,bY){bY=bY.replace(/\=\s*([^'"\]]*)\s*\]/g,"='$1']");if(!by.isXML(bW)){try{if(bR||!bE.match.PSEUDO.test(bY)&&!/!=/.test(bY)){var bV=bS.call(bW,bY);if(bV||!bU||bW.document&&bW.document.nodeType!==11){return bV}}}catch(bX){}}return by(bY,null,null,[bW]).length>0}}})();(function(){var e=av.createElement("div");e.innerHTML="
";if(!e.getElementsByClassName||e.getElementsByClassName("e").length===0){return}e.lastChild.className="e";if(e.getElementsByClassName("e").length===1){return}bE.order.splice(1,0,"CLASS");bE.find.CLASS=function(bR,bS,bT){if(typeof bS.getElementsByClassName!=="undefined"&&!bT){return bS.getElementsByClassName(bR[1])}};e=null})();function bv(bR,bW,bV,bZ,bX,bY){for(var bT=0,bS=bZ.length;bT0){bU=e;break}}}e=e[bR]}bZ[bT]=bU}}}if(av.documentElement.contains){by.contains=function(bR,e){return bR!==e&&(bR.contains?bR.contains(e):true)}}else{if(av.documentElement.compareDocumentPosition){by.contains=function(bR,e){return !!(bR.compareDocumentPosition(e)&16)}}else{by.contains=function(){return false}}}by.isXML=function(e){var bR=(e?e.ownerDocument||e:0).documentElement;return bR?bR.nodeName!=="HTML":false};var bM=function(bS,e,bW){var bV,bX=[],bU="",bY=e.nodeType?[e]:e;while((bV=bE.match.PSEUDO.exec(bS))){bU+=bV[0];bS=bS.replace(bE.match.PSEUDO,"")}bS=bE.relative[bS]?bS+"*":bS;for(var bT=0,bR=bY.length;bT0){for(bB=bA;bB=0:b.filter(e,this).length>0:this.filter(e).length>0)},closest:function(by,bx){var bv=[],bw,e,bz=this[0];if(b.isArray(by)){var bB=1;while(bz&&bz.ownerDocument&&bz!==bx){for(bw=0;bw-1:b.find.matchesSelector(bz,by)){bv.push(bz);break}else{bz=bz.parentNode;if(!bz||!bz.ownerDocument||bz===bx||bz.nodeType===11){break}}}}bv=bv.length>1?b.unique(bv):bv;return this.pushStack(bv,"closest",by)},index:function(e){if(!e){return(this[0]&&this[0].parentNode)?this.prevAll().length:-1}if(typeof e==="string"){return b.inArray(this[0],b(e))}return b.inArray(e.jquery?e[0]:e,this)},add:function(e,bv){var bx=typeof e==="string"?b(e,bv):b.makeArray(e&&e.nodeType?[e]:e),bw=b.merge(this.get(),bx);return this.pushStack(C(bx[0])||C(bw[0])?bw:b.unique(bw))},andSelf:function(){return this.add(this.prevObject)}});function C(e){return !e||!e.parentNode||e.parentNode.nodeType===11}b.each({parent:function(bv){var e=bv.parentNode;return e&&e.nodeType!==11?e:null},parents:function(e){return b.dir(e,"parentNode")},parentsUntil:function(bv,e,bw){return b.dir(bv,"parentNode",bw)},next:function(e){return b.nth(e,2,"nextSibling")},prev:function(e){return b.nth(e,2,"previousSibling")},nextAll:function(e){return b.dir(e,"nextSibling")},prevAll:function(e){return b.dir(e,"previousSibling")},nextUntil:function(bv,e,bw){return b.dir(bv,"nextSibling",bw)},prevUntil:function(bv,e,bw){return b.dir(bv,"previousSibling",bw)},siblings:function(e){return b.sibling(e.parentNode.firstChild,e)},children:function(e){return b.sibling(e.firstChild)},contents:function(e){return b.nodeName(e,"iframe")?e.contentDocument||e.contentWindow.document:b.makeArray(e.childNodes)}},function(e,bv){b.fn[e]=function(by,bw){var bx=b.map(this,bv,by);if(!ab.test(e)){bw=by}if(bw&&typeof bw==="string"){bx=b.filter(bw,bx)}bx=this.length>1&&!ay[e]?b.unique(bx):bx;if((this.length>1||a9.test(bw))&&aq.test(e)){bx=bx.reverse()}return this.pushStack(bx,e,P.call(arguments).join(","))}});b.extend({filter:function(bw,e,bv){if(bv){bw=":not("+bw+")"}return e.length===1?b.find.matchesSelector(e[0],bw)?[e[0]]:[]:b.find.matches(bw,e)},dir:function(bw,bv,by){var e=[],bx=bw[bv];while(bx&&bx.nodeType!==9&&(by===L||bx.nodeType!==1||!b(bx).is(by))){if(bx.nodeType===1){e.push(bx)}bx=bx[bv]}return e},nth:function(by,e,bw,bx){e=e||1;var bv=0;for(;by;by=by[bw]){if(by.nodeType===1&&++bv===e){break}}return by},sibling:function(bw,bv){var e=[];for(;bw;bw=bw.nextSibling){if(bw.nodeType===1&&bw!==bv){e.push(bw)}}return e}});function aG(bx,bw,e){bw=bw||0;if(b.isFunction(bw)){return b.grep(bx,function(bz,by){var bA=!!bw.call(bz,by,bz);return bA===e})}else{if(bw.nodeType){return b.grep(bx,function(bz,by){return(bz===bw)===e})}else{if(typeof bw==="string"){var bv=b.grep(bx,function(by){return by.nodeType===1});if(bp.test(bw)){return b.filter(bw,bv,!e)}else{bw=b.filter(bw,bv)}}}}return b.grep(bx,function(bz,by){return(b.inArray(bz,bw)>=0)===e})}function a(e){var bw=aR.split("|"),bv=e.createDocumentFragment();if(bv.createElement){while(bw.length){bv.createElement(bw.pop())}}return bv}var aR="abbr|article|aside|audio|canvas|datalist|details|figcaption|figure|footer|header|hgroup|mark|meter|nav|output|progress|section|summary|time|video",ag=/ jQuery\d+="(?:\d+|null)"/g,ar=/^\s+/,R=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/ig,d=/<([\w:]+)/,w=/",""],legend:[1,"
","
"],thead:[1,"","
"],tr:[2,"","
"],td:[3,"","
"],col:[2,"","
"],area:[1,"",""],_default:[0,"",""]},ac=a(av);ax.optgroup=ax.option;ax.tbody=ax.tfoot=ax.colgroup=ax.caption=ax.thead;ax.th=ax.td;if(!b.support.htmlSerialize){ax._default=[1,"div
","
"]}b.fn.extend({text:function(e){if(b.isFunction(e)){return this.each(function(bw){var bv=b(this);bv.text(e.call(this,bw,bv.text()))})}if(typeof e!=="object"&&e!==L){return this.empty().append((this[0]&&this[0].ownerDocument||av).createTextNode(e))}return b.text(this)},wrapAll:function(e){if(b.isFunction(e)){return this.each(function(bw){b(this).wrapAll(e.call(this,bw))})}if(this[0]){var bv=b(e,this[0].ownerDocument).eq(0).clone(true);if(this[0].parentNode){bv.insertBefore(this[0])}bv.map(function(){var bw=this;while(bw.firstChild&&bw.firstChild.nodeType===1){bw=bw.firstChild}return bw}).append(this)}return this},wrapInner:function(e){if(b.isFunction(e)){return this.each(function(bv){b(this).wrapInner(e.call(this,bv))})}return this.each(function(){var bv=b(this),bw=bv.contents();if(bw.length){bw.wrapAll(e)}else{bv.append(e)}})},wrap:function(e){var bv=b.isFunction(e);return this.each(function(bw){b(this).wrapAll(bv?e.call(this,bw):e)})},unwrap:function(){return this.parent().each(function(){if(!b.nodeName(this,"body")){b(this).replaceWith(this.childNodes)}}).end()},append:function(){return this.domManip(arguments,true,function(e){if(this.nodeType===1){this.appendChild(e)}})},prepend:function(){return this.domManip(arguments,true,function(e){if(this.nodeType===1){this.insertBefore(e,this.firstChild)}})},before:function(){if(this[0]&&this[0].parentNode){return this.domManip(arguments,false,function(bv){this.parentNode.insertBefore(bv,this)})}else{if(arguments.length){var e=b.clean(arguments);e.push.apply(e,this.toArray());return this.pushStack(e,"before",arguments)}}},after:function(){if(this[0]&&this[0].parentNode){return this.domManip(arguments,false,function(bv){this.parentNode.insertBefore(bv,this.nextSibling)})}else{if(arguments.length){var e=this.pushStack(this,"after",arguments);e.push.apply(e,b.clean(arguments));return e}}},remove:function(e,bx){for(var bv=0,bw;(bw=this[bv])!=null;bv++){if(!e||b.filter(e,[bw]).length){if(!bx&&bw.nodeType===1){b.cleanData(bw.getElementsByTagName("*"));b.cleanData([bw])}if(bw.parentNode){bw.parentNode.removeChild(bw)}}}return this},empty:function(){for(var e=0,bv;(bv=this[e])!=null;e++){if(bv.nodeType===1){b.cleanData(bv.getElementsByTagName("*"))}while(bv.firstChild){bv.removeChild(bv.firstChild)}}return this},clone:function(bv,e){bv=bv==null?false:bv;e=e==null?bv:e;return this.map(function(){return b.clone(this,bv,e)})},html:function(bx){if(bx===L){return this[0]&&this[0].nodeType===1?this[0].innerHTML.replace(ag,""):null}else{if(typeof bx==="string"&&!ae.test(bx)&&(b.support.leadingWhitespace||!ar.test(bx))&&!ax[(d.exec(bx)||["",""])[1].toLowerCase()]){bx=bx.replace(R,"<$1>");try{for(var bw=0,bv=this.length;bw1&&bw0?this.clone(true):this).get();b(bC[bA])[bv](by);bz=bz.concat(by)}return this.pushStack(bz,e,bC.selector)}}});function bg(e){if(typeof e.getElementsByTagName!=="undefined"){return e.getElementsByTagName("*")}else{if(typeof e.querySelectorAll!=="undefined"){return e.querySelectorAll("*")}else{return[]}}}function az(e){if(e.type==="checkbox"||e.type==="radio"){e.defaultChecked=e.checked}}function E(e){var bv=(e.nodeName||"").toLowerCase();if(bv==="input"){az(e)}else{if(bv!=="script"&&typeof e.getElementsByTagName!=="undefined"){b.grep(e.getElementsByTagName("input"),az)}}}function al(e){var bv=av.createElement("div");ac.appendChild(bv);bv.innerHTML=e.outerHTML;return bv.firstChild}b.extend({clone:function(by,bA,bw){var e,bv,bx,bz=b.support.html5Clone||!ah.test("<"+by.nodeName)?by.cloneNode(true):al(by);if((!b.support.noCloneEvent||!b.support.noCloneChecked)&&(by.nodeType===1||by.nodeType===11)&&!b.isXMLDoc(by)){ai(by,bz);e=bg(by);bv=bg(bz);for(bx=0;e[bx];++bx){if(bv[bx]){ai(e[bx],bv[bx])}}}if(bA){t(by,bz);if(bw){e=bg(by);bv=bg(bz);for(bx=0;e[bx];++bx){t(e[bx],bv[bx])}}}e=bv=null;return bz},clean:function(bw,by,bH,bA){var bF;by=by||av;if(typeof by.createElement==="undefined"){by=by.ownerDocument||by[0]&&by[0].ownerDocument||av}var bI=[],bB;for(var bE=0,bz;(bz=bw[bE])!=null;bE++){if(typeof bz==="number"){bz+=""}if(!bz){continue}if(typeof bz==="string"){if(!W.test(bz)){bz=by.createTextNode(bz)}else{bz=bz.replace(R,"<$1>");var bK=(d.exec(bz)||["",""])[1].toLowerCase(),bx=ax[bK]||ax._default,bD=bx[0],bv=by.createElement("div");if(by===av){ac.appendChild(bv)}else{a(by).appendChild(bv)}bv.innerHTML=bx[1]+bz+bx[2];while(bD--){bv=bv.lastChild}if(!b.support.tbody){var e=w.test(bz),bC=bK==="table"&&!e?bv.firstChild&&bv.firstChild.childNodes:bx[1]===""&&!e?bv.childNodes:[];for(bB=bC.length-1;bB>=0;--bB){if(b.nodeName(bC[bB],"tbody")&&!bC[bB].childNodes.length){bC[bB].parentNode.removeChild(bC[bB])}}}if(!b.support.leadingWhitespace&&ar.test(bz)){bv.insertBefore(by.createTextNode(ar.exec(bz)[0]),bv.firstChild)}bz=bv.childNodes}}var bG;if(!b.support.appendChecked){if(bz[0]&&typeof(bG=bz.length)==="number"){for(bB=0;bB=0){return bx+"px"}}else{return bx}}}});if(!b.support.opacity){b.cssHooks.opacity={get:function(bv,e){return au.test((e&&bv.currentStyle?bv.currentStyle.filter:bv.style.filter)||"")?(parseFloat(RegExp.$1)/100)+"":e?"1":""},set:function(by,bz){var bx=by.style,bv=by.currentStyle,e=b.isNumeric(bz)?"alpha(opacity="+bz*100+")":"",bw=bv&&bv.filter||bx.filter||"";bx.zoom=1;if(bz>=1&&b.trim(bw.replace(ak,""))===""){bx.removeAttribute("filter");if(bv&&!bv.filter){return}}bx.filter=ak.test(bw)?bw.replace(ak,e):bw+" "+e}}}b(function(){if(!b.support.reliableMarginRight){b.cssHooks.marginRight={get:function(bw,bv){var e;b.swap(bw,{display:"inline-block"},function(){if(bv){e=Z(bw,"margin-right","marginRight")}else{e=bw.style.marginRight}});return e}}}});if(av.defaultView&&av.defaultView.getComputedStyle){aI=function(by,bw){var bv,bx,e;bw=bw.replace(z,"-$1").toLowerCase();if((bx=by.ownerDocument.defaultView)&&(e=bx.getComputedStyle(by,null))){bv=e.getPropertyValue(bw);if(bv===""&&!b.contains(by.ownerDocument.documentElement,by)){bv=b.style(by,bw)}}return bv}}if(av.documentElement.currentStyle){aX=function(bz,bw){var bA,e,by,bv=bz.currentStyle&&bz.currentStyle[bw],bx=bz.style;if(bv===null&&bx&&(by=bx[bw])){bv=by}if(!bc.test(bv)&&bn.test(bv)){bA=bx.left;e=bz.runtimeStyle&&bz.runtimeStyle.left;if(e){bz.runtimeStyle.left=bz.currentStyle.left}bx.left=bw==="fontSize"?"1em":(bv||0);bv=bx.pixelLeft+"px";bx.left=bA;if(e){bz.runtimeStyle.left=e}}return bv===""?"auto":bv}}Z=aI||aX;function p(by,bw,bv){var bA=bw==="width"?by.offsetWidth:by.offsetHeight,bz=bw==="width"?an:a1,bx=0,e=bz.length;if(bA>0){if(bv!=="border"){for(;bx)<[^<]*)*<\/script>/gi,q=/^(?:select|textarea)/i,h=/\s+/,br=/([?&])_=[^&]*/,K=/^([\w\+\.\-]+:)(?:\/\/([^\/?#:]*)(?::(\d+))?)?/,A=b.fn.load,aa={},r={},aE,s,aV=["*/"]+["*"];try{aE=bl.href}catch(aw){aE=av.createElement("a");aE.href="";aE=aE.href}s=K.exec(aE.toLowerCase())||[];function f(e){return function(by,bA){if(typeof by!=="string"){bA=by;by="*"}if(b.isFunction(bA)){var bx=by.toLowerCase().split(h),bw=0,bz=bx.length,bv,bB,bC;for(;bw=0){var e=bw.slice(by,bw.length);bw=bw.slice(0,by)}var bx="GET";if(bz){if(b.isFunction(bz)){bA=bz;bz=L}else{if(typeof bz==="object"){bz=b.param(bz,b.ajaxSettings.traditional);bx="POST"}}}var bv=this;b.ajax({url:bw,type:bx,dataType:"html",data:bz,complete:function(bC,bB,bD){bD=bC.responseText;if(bC.isResolved()){bC.done(function(bE){bD=bE});bv.html(e?b("
").append(bD.replace(a6,"")).find(e):bD)}if(bA){bv.each(bA,[bD,bB,bC])}}});return this},serialize:function(){return b.param(this.serializeArray())},serializeArray:function(){return this.map(function(){return this.elements?b.makeArray(this.elements):this}).filter(function(){return this.name&&!this.disabled&&(this.checked||q.test(this.nodeName)||aZ.test(this.type))}).map(function(e,bv){var bw=b(this).val();return bw==null?null:b.isArray(bw)?b.map(bw,function(by,bx){return{name:bv.name,value:by.replace(bs,"\r\n")}}):{name:bv.name,value:bw.replace(bs,"\r\n")}}).get()}});b.each("ajaxStart ajaxStop ajaxComplete ajaxError ajaxSuccess ajaxSend".split(" "),function(e,bv){b.fn[bv]=function(bw){return this.on(bv,bw)}});b.each(["get","post"],function(e,bv){b[bv]=function(bw,by,bz,bx){if(b.isFunction(by)){bx=bx||bz;bz=by;by=L}return b.ajax({type:bv,url:bw,data:by,success:bz,dataType:bx})}});b.extend({getScript:function(e,bv){return b.get(e,L,bv,"script")},getJSON:function(e,bv,bw){return b.get(e,bv,bw,"json")},ajaxSetup:function(bv,e){if(e){am(bv,b.ajaxSettings)}else{e=bv;bv=b.ajaxSettings}am(bv,e);return bv},ajaxSettings:{url:aE,isLocal:aM.test(s[1]),global:true,type:"GET",contentType:"application/x-www-form-urlencoded",processData:true,async:true,accepts:{xml:"application/xml, text/xml",html:"text/html",text:"text/plain",json:"application/json, text/javascript","*":aV},contents:{xml:/xml/,html:/html/,json:/json/},responseFields:{xml:"responseXML",text:"responseText"},converters:{"* text":bb.String,"text html":true,"text json":b.parseJSON,"text xml":b.parseXML},flatOptions:{context:true,url:true}},ajaxPrefilter:f(aa),ajaxTransport:f(r),ajax:function(bz,bx){if(typeof bz==="object"){bx=bz;bz=L}bx=bx||{};var bD=b.ajaxSetup({},bx),bS=bD.context||bD,bG=bS!==bD&&(bS.nodeType||bS instanceof b)?b(bS):b.event,bR=b.Deferred(),bN=b.Callbacks("once memory"),bB=bD.statusCode||{},bC,bH={},bO={},bQ,by,bL,bE,bI,bA=0,bw,bK,bJ={readyState:0,setRequestHeader:function(bT,bU){if(!bA){var e=bT.toLowerCase();bT=bO[e]=bO[e]||bT;bH[bT]=bU}return this},getAllResponseHeaders:function(){return bA===2?bQ:null},getResponseHeader:function(bT){var e;if(bA===2){if(!by){by={};while((e=aD.exec(bQ))){by[e[1].toLowerCase()]=e[2]}}e=by[bT.toLowerCase()]}return e===L?null:e},overrideMimeType:function(e){if(!bA){bD.mimeType=e}return this},abort:function(e){e=e||"abort";if(bL){bL.abort(e)}bF(0,e);return this}};function bF(bZ,bU,b0,bW){if(bA===2){return}bA=2;if(bE){clearTimeout(bE)}bL=L;bQ=bW||"";bJ.readyState=bZ>0?4:0;var bT,b4,b3,bX=bU,bY=b0?bj(bD,bJ,b0):L,bV,b2;if(bZ>=200&&bZ<300||bZ===304){if(bD.ifModified){if((bV=bJ.getResponseHeader("Last-Modified"))){b.lastModified[bC]=bV}if((b2=bJ.getResponseHeader("Etag"))){b.etag[bC]=b2}}if(bZ===304){bX="notmodified";bT=true}else{try{b4=G(bD,bY);bX="success";bT=true}catch(b1){bX="parsererror";b3=b1}}}else{b3=bX;if(!bX||bZ){bX="error";if(bZ<0){bZ=0}}}bJ.status=bZ;bJ.statusText=""+(bU||bX);if(bT){bR.resolveWith(bS,[b4,bX,bJ])}else{bR.rejectWith(bS,[bJ,bX,b3])}bJ.statusCode(bB);bB=L;if(bw){bG.trigger("ajax"+(bT?"Success":"Error"),[bJ,bD,bT?b4:b3])}bN.fireWith(bS,[bJ,bX]);if(bw){bG.trigger("ajaxComplete",[bJ,bD]);if(!(--b.active)){b.event.trigger("ajaxStop")}}}bR.promise(bJ);bJ.success=bJ.done;bJ.error=bJ.fail;bJ.complete=bN.add;bJ.statusCode=function(bT){if(bT){var e;if(bA<2){for(e in bT){bB[e]=[bB[e],bT[e]]}}else{e=bT[bJ.status];bJ.then(e,e)}}return this};bD.url=((bz||bD.url)+"").replace(bq,"").replace(c,s[1]+"//");bD.dataTypes=b.trim(bD.dataType||"*").toLowerCase().split(h);if(bD.crossDomain==null){bI=K.exec(bD.url.toLowerCase());bD.crossDomain=!!(bI&&(bI[1]!=s[1]||bI[2]!=s[2]||(bI[3]||(bI[1]==="http:"?80:443))!=(s[3]||(s[1]==="http:"?80:443))))}if(bD.data&&bD.processData&&typeof bD.data!=="string"){bD.data=b.param(bD.data,bD.traditional)}aW(aa,bD,bx,bJ);if(bA===2){return false}bw=bD.global;bD.type=bD.type.toUpperCase();bD.hasContent=!aQ.test(bD.type);if(bw&&b.active++===0){b.event.trigger("ajaxStart")}if(!bD.hasContent){if(bD.data){bD.url+=(M.test(bD.url)?"&":"?")+bD.data;delete bD.data}bC=bD.url;if(bD.cache===false){var bv=b.now(),bP=bD.url.replace(br,"$1_="+bv);bD.url=bP+((bP===bD.url)?(M.test(bD.url)?"&":"?")+"_="+bv:"")}}if(bD.data&&bD.hasContent&&bD.contentType!==false||bx.contentType){bJ.setRequestHeader("Content-Type",bD.contentType)}if(bD.ifModified){bC=bC||bD.url;if(b.lastModified[bC]){bJ.setRequestHeader("If-Modified-Since",b.lastModified[bC])}if(b.etag[bC]){bJ.setRequestHeader("If-None-Match",b.etag[bC])}}bJ.setRequestHeader("Accept",bD.dataTypes[0]&&bD.accepts[bD.dataTypes[0]]?bD.accepts[bD.dataTypes[0]]+(bD.dataTypes[0]!=="*"?", "+aV+"; q=0.01":""):bD.accepts["*"]);for(bK in bD.headers){bJ.setRequestHeader(bK,bD.headers[bK])}if(bD.beforeSend&&(bD.beforeSend.call(bS,bJ,bD)===false||bA===2)){bJ.abort();return false}for(bK in {success:1,error:1,complete:1}){bJ[bK](bD[bK])}bL=aW(r,bD,bx,bJ);if(!bL){bF(-1,"No Transport")}else{bJ.readyState=1;if(bw){bG.trigger("ajaxSend",[bJ,bD])}if(bD.async&&bD.timeout>0){bE=setTimeout(function(){bJ.abort("timeout")},bD.timeout)}try{bA=1;bL.send(bH,bF)}catch(bM){if(bA<2){bF(-1,bM)}else{throw bM}}}return bJ},param:function(e,bw){var bv=[],by=function(bz,bA){bA=b.isFunction(bA)?bA():bA;bv[bv.length]=encodeURIComponent(bz)+"="+encodeURIComponent(bA)};if(bw===L){bw=b.ajaxSettings.traditional}if(b.isArray(e)||(e.jquery&&!b.isPlainObject(e))){b.each(e,function(){by(this.name,this.value)})}else{for(var bx in e){v(bx,e[bx],bw,by)}}return bv.join("&").replace(k,"+")}});function v(bw,by,bv,bx){if(b.isArray(by)){b.each(by,function(bA,bz){if(bv||ap.test(bw)){bx(bw,bz)}else{v(bw+"["+(typeof bz==="object"||b.isArray(bz)?bA:"")+"]",bz,bv,bx)}})}else{if(!bv&&by!=null&&typeof by==="object"){for(var e in by){v(bw+"["+e+"]",by[e],bv,bx)}}else{bx(bw,by)}}}b.extend({active:0,lastModified:{},etag:{}});function bj(bD,bC,bz){var bv=bD.contents,bB=bD.dataTypes,bw=bD.responseFields,by,bA,bx,e;for(bA in bw){if(bA in bz){bC[bw[bA]]=bz[bA]}}while(bB[0]==="*"){bB.shift();if(by===L){by=bD.mimeType||bC.getResponseHeader("content-type")}}if(by){for(bA in bv){if(bv[bA]&&bv[bA].test(by)){bB.unshift(bA);break}}}if(bB[0] in bz){bx=bB[0]}else{for(bA in bz){if(!bB[0]||bD.converters[bA+" "+bB[0]]){bx=bA;break}if(!e){e=bA}}bx=bx||e}if(bx){if(bx!==bB[0]){bB.unshift(bx)}return bz[bx]}}function G(bH,bz){if(bH.dataFilter){bz=bH.dataFilter(bz,bH.dataType)}var bD=bH.dataTypes,bG={},bA,bE,bw=bD.length,bB,bC=bD[0],bx,by,bF,bv,e;for(bA=1;bA=bw.duration+this.startTime){this.now=this.end;this.pos=this.state=1;this.update();bw.animatedProperties[this.prop]=true;for(bA in bw.animatedProperties){if(bw.animatedProperties[bA]!==true){e=false}}if(e){if(bw.overflow!=null&&!b.support.shrinkWrapBlocks){b.each(["","X","Y"],function(bC,bD){bz.style["overflow"+bD]=bw.overflow[bC]})}if(bw.hide){b(bz).hide()}if(bw.hide||bw.show){for(bA in bw.animatedProperties){b.style(bz,bA,bw.orig[bA]);b.removeData(bz,"fxshow"+bA,true);b.removeData(bz,"toggle"+bA,true)}}bv=bw.complete;if(bv){bw.complete=false;bv.call(bz)}}return false}else{if(bw.duration==Infinity){this.now=bx}else{bB=bx-this.startTime;this.state=bB/bw.duration;this.pos=b.easing[bw.animatedProperties[this.prop]](this.state,bB,0,1,bw.duration);this.now=this.start+((this.end-this.start)*this.pos)}this.update()}return true}};b.extend(b.fx,{tick:function(){var bw,bv=b.timers,e=0;for(;e").appendTo(e),bw=bv.css("display");bv.remove();if(bw==="none"||bw===""){if(!a8){a8=av.createElement("iframe");a8.frameBorder=a8.width=a8.height=0}e.appendChild(a8);if(!m||!a8.createElement){m=(a8.contentWindow||a8.contentDocument).document;m.write((av.compatMode==="CSS1Compat"?"":"")+"");m.close()}bv=m.createElement(bx);m.body.appendChild(bv);bw=b.css(bv,"display");e.removeChild(a8)}Q[bx]=bw}return Q[bx]}var V=/^t(?:able|d|h)$/i,ad=/^(?:body|html)$/i;if("getBoundingClientRect" in av.documentElement){b.fn.offset=function(bI){var by=this[0],bB;if(bI){return this.each(function(e){b.offset.setOffset(this,bI,e)})}if(!by||!by.ownerDocument){return null}if(by===by.ownerDocument.body){return b.offset.bodyOffset(by)}try{bB=by.getBoundingClientRect()}catch(bF){}var bH=by.ownerDocument,bw=bH.documentElement;if(!bB||!b.contains(bw,by)){return bB?{top:bB.top,left:bB.left}:{top:0,left:0}}var bC=bH.body,bD=aK(bH),bA=bw.clientTop||bC.clientTop||0,bE=bw.clientLeft||bC.clientLeft||0,bv=bD.pageYOffset||b.support.boxModel&&bw.scrollTop||bC.scrollTop,bz=bD.pageXOffset||b.support.boxModel&&bw.scrollLeft||bC.scrollLeft,bG=bB.top+bv-bA,bx=bB.left+bz-bE;return{top:bG,left:bx}}}else{b.fn.offset=function(bF){var bz=this[0];if(bF){return this.each(function(bG){b.offset.setOffset(this,bF,bG)})}if(!bz||!bz.ownerDocument){return null}if(bz===bz.ownerDocument.body){return b.offset.bodyOffset(bz)}var bC,bw=bz.offsetParent,bv=bz,bE=bz.ownerDocument,bx=bE.documentElement,bA=bE.body,bB=bE.defaultView,e=bB?bB.getComputedStyle(bz,null):bz.currentStyle,bD=bz.offsetTop,by=bz.offsetLeft;while((bz=bz.parentNode)&&bz!==bA&&bz!==bx){if(b.support.fixedPosition&&e.position==="fixed"){break}bC=bB?bB.getComputedStyle(bz,null):bz.currentStyle;bD-=bz.scrollTop;by-=bz.scrollLeft;if(bz===bw){bD+=bz.offsetTop;by+=bz.offsetLeft;if(b.support.doesNotAddBorder&&!(b.support.doesAddBorderForTableAndCells&&V.test(bz.nodeName))){bD+=parseFloat(bC.borderTopWidth)||0;by+=parseFloat(bC.borderLeftWidth)||0}bv=bw;bw=bz.offsetParent}if(b.support.subtractsBorderForOverflowNotVisible&&bC.overflow!=="visible"){bD+=parseFloat(bC.borderTopWidth)||0;by+=parseFloat(bC.borderLeftWidth)||0}e=bC}if(e.position==="relative"||e.position==="static"){bD+=bA.offsetTop;by+=bA.offsetLeft}if(b.support.fixedPosition&&e.position==="fixed"){bD+=Math.max(bx.scrollTop,bA.scrollTop);by+=Math.max(bx.scrollLeft,bA.scrollLeft)}return{top:bD,left:by}}}b.offset={bodyOffset:function(e){var bw=e.offsetTop,bv=e.offsetLeft;if(b.support.doesNotIncludeMarginInBodyOffset){bw+=parseFloat(b.css(e,"marginTop"))||0;bv+=parseFloat(b.css(e,"marginLeft"))||0}return{top:bw,left:bv}},setOffset:function(bx,bG,bA){var bB=b.css(bx,"position");if(bB==="static"){bx.style.position="relative"}var bz=b(bx),bv=bz.offset(),e=b.css(bx,"top"),bE=b.css(bx,"left"),bF=(bB==="absolute"||bB==="fixed")&&b.inArray("auto",[e,bE])>-1,bD={},bC={},bw,by;if(bF){bC=bz.position();bw=bC.top;by=bC.left}else{bw=parseFloat(e)||0;by=parseFloat(bE)||0}if(b.isFunction(bG)){bG=bG.call(bx,bA,bv)}if(bG.top!=null){bD.top=(bG.top-bv.top)+bw}if(bG.left!=null){bD.left=(bG.left-bv.left)+by}if("using" in bG){bG.using.call(bx,bD)}else{bz.css(bD)}}};b.fn.extend({position:function(){if(!this[0]){return null}var bw=this[0],bv=this.offsetParent(),bx=this.offset(),e=ad.test(bv[0].nodeName)?{top:0,left:0}:bv.offset();bx.top-=parseFloat(b.css(bw,"marginTop"))||0;bx.left-=parseFloat(b.css(bw,"marginLeft"))||0;e.top+=parseFloat(b.css(bv[0],"borderTopWidth"))||0;e.left+=parseFloat(b.css(bv[0],"borderLeftWidth"))||0;return{top:bx.top-e.top,left:bx.left-e.left}},offsetParent:function(){return this.map(function(){var e=this.offsetParent||av.body;while(e&&(!ad.test(e.nodeName)&&b.css(e,"position")==="static")){e=e.offsetParent}return e})}});b.each(["Left","Top"],function(bv,e){var bw="scroll"+e;b.fn[bw]=function(bz){var bx,by;if(bz===L){bx=this[0];if(!bx){return null}by=aK(bx);return by?("pageXOffset" in by)?by[bv?"pageYOffset":"pageXOffset"]:b.support.boxModel&&by.document.documentElement[bw]||by.document.body[bw]:bx[bw]}return this.each(function(){by=aK(this);if(by){by.scrollTo(!bv?bz:b(by).scrollLeft(),bv?bz:b(by).scrollTop())}else{this[bw]=bz}})}});function aK(e){return b.isWindow(e)?e:e.nodeType===9?e.defaultView||e.parentWindow:false}b.each(["Height","Width"],function(bv,e){var bw=e.toLowerCase();b.fn["inner"+e]=function(){var bx=this[0];return bx?bx.style?parseFloat(b.css(bx,bw,"padding")):this[bw]():null};b.fn["outer"+e]=function(by){var bx=this[0];return bx?bx.style?parseFloat(b.css(bx,bw,by?"margin":"border")):this[bw]():null};b.fn[bw]=function(bz){var bA=this[0];if(!bA){return bz==null?null:this}if(b.isFunction(bz)){return this.each(function(bE){var bD=b(this);bD[bw](bz.call(this,bE,bD[bw]()))})}if(b.isWindow(bA)){var bB=bA.document.documentElement["client"+e],bx=bA.document.body;return bA.document.compatMode==="CSS1Compat"&&bB||bx&&bx["client"+e]||bB}else{if(bA.nodeType===9){return Math.max(bA.documentElement["client"+e],bA.body["scroll"+e],bA.documentElement["scroll"+e],bA.body["offset"+e],bA.documentElement["offset"+e])}else{if(bz===L){var bC=b.css(bA,bw),by=parseFloat(bC);return b.isNumeric(by)?by:bC}else{return this.css(bw,typeof bz==="string"?bz:bz+"px")}}}}});bb.jQuery=bb.$=b;if(typeof define==="function"&&define.amd&&define.amd.jQuery){define("jquery",[],function(){return b})}})(window);/*! * jQuery UI 1.8.18 * * Copyright 2011, AUTHORS.txt (http://jqueryui.com/about) * Dual licensed under the MIT or GPL Version 2 licenses. * http://jquery.org/license * * http://docs.jquery.com/UI */ (function(a,d){a.ui=a.ui||{};if(a.ui.version){return}a.extend(a.ui,{version:"1.8.18",keyCode:{ALT:18,BACKSPACE:8,CAPS_LOCK:20,COMMA:188,COMMAND:91,COMMAND_LEFT:91,COMMAND_RIGHT:93,CONTROL:17,DELETE:46,DOWN:40,END:35,ENTER:13,ESCAPE:27,HOME:36,INSERT:45,LEFT:37,MENU:93,NUMPAD_ADD:107,NUMPAD_DECIMAL:110,NUMPAD_DIVIDE:111,NUMPAD_ENTER:108,NUMPAD_MULTIPLY:106,NUMPAD_SUBTRACT:109,PAGE_DOWN:34,PAGE_UP:33,PERIOD:190,RIGHT:39,SHIFT:16,SPACE:32,TAB:9,UP:38,WINDOWS:91}});a.fn.extend({propAttr:a.fn.prop||a.fn.attr,_focus:a.fn.focus,focus:function(e,f){return typeof e==="number"?this.each(function(){var g=this;setTimeout(function(){a(g).focus();if(f){f.call(g)}},e)}):this._focus.apply(this,arguments)},scrollParent:function(){var e;if((a.browser.msie&&(/(static|relative)/).test(this.css("position")))||(/absolute/).test(this.css("position"))){e=this.parents().filter(function(){return(/(relative|absolute|fixed)/).test(a.curCSS(this,"position",1))&&(/(auto|scroll)/).test(a.curCSS(this,"overflow",1)+a.curCSS(this,"overflow-y",1)+a.curCSS(this,"overflow-x",1))}).eq(0)}else{e=this.parents().filter(function(){return(/(auto|scroll)/).test(a.curCSS(this,"overflow",1)+a.curCSS(this,"overflow-y",1)+a.curCSS(this,"overflow-x",1))}).eq(0)}return(/fixed/).test(this.css("position"))||!e.length?a(document):e},zIndex:function(h){if(h!==d){return this.css("zIndex",h)}if(this.length){var f=a(this[0]),e,g;while(f.length&&f[0]!==document){e=f.css("position");if(e==="absolute"||e==="relative"||e==="fixed"){g=parseInt(f.css("zIndex"),10);if(!isNaN(g)&&g!==0){return g}}f=f.parent()}}return 0},disableSelection:function(){return this.bind((a.support.selectstart?"selectstart":"mousedown")+".ui-disableSelection",function(e){e.preventDefault()})},enableSelection:function(){return this.unbind(".ui-disableSelection")}});a.each(["Width","Height"],function(g,e){var f=e==="Width"?["Left","Right"]:["Top","Bottom"],h=e.toLowerCase(),k={innerWidth:a.fn.innerWidth,innerHeight:a.fn.innerHeight,outerWidth:a.fn.outerWidth,outerHeight:a.fn.outerHeight};function j(m,l,i,n){a.each(f,function(){l-=parseFloat(a.curCSS(m,"padding"+this,true))||0;if(i){l-=parseFloat(a.curCSS(m,"border"+this+"Width",true))||0}if(n){l-=parseFloat(a.curCSS(m,"margin"+this,true))||0}});return l}a.fn["inner"+e]=function(i){if(i===d){return k["inner"+e].call(this)}return this.each(function(){a(this).css(h,j(this,i)+"px")})};a.fn["outer"+e]=function(i,l){if(typeof i!=="number"){return k["outer"+e].call(this,i)}return this.each(function(){a(this).css(h,j(this,i,true,l)+"px")})}});function c(g,e){var j=g.nodeName.toLowerCase();if("area"===j){var i=g.parentNode,h=i.name,f;if(!g.href||!h||i.nodeName.toLowerCase()!=="map"){return false}f=a("img[usemap=#"+h+"]")[0];return !!f&&b(f)}return(/input|select|textarea|button|object/.test(j)?!g.disabled:"a"==j?g.href||e:e)&&b(g)}function b(e){return !a(e).parents().andSelf().filter(function(){return a.curCSS(this,"visibility")==="hidden"||a.expr.filters.hidden(this)}).length}a.extend(a.expr[":"],{data:function(g,f,e){return !!a.data(g,e[3])},focusable:function(e){return c(e,!isNaN(a.attr(e,"tabindex")))},tabbable:function(g){var e=a.attr(g,"tabindex"),f=isNaN(e);return(f||e>=0)&&c(g,!f)}});a(function(){var e=document.body,f=e.appendChild(f=document.createElement("div"));f.offsetHeight;a.extend(f.style,{minHeight:"100px",height:"auto",padding:0,borderWidth:0});a.support.minHeight=f.offsetHeight===100;a.support.selectstart="onselectstart" in f;e.removeChild(f).style.display="none"});a.extend(a.ui,{plugin:{add:function(f,g,j){var h=a.ui[f].prototype;for(var e in j){h.plugins[e]=h.plugins[e]||[];h.plugins[e].push([g,j[e]])}},call:function(e,g,f){var j=e.plugins[g];if(!j||!e.element[0].parentNode){return}for(var h=0;h0){return true}h[e]=1;g=(h[e]>0);h[e]=0;return g},isOverAxis:function(f,e,g){return(f>e)&&(f<(e+g))},isOver:function(j,f,i,h,e,g){return a.ui.isOverAxis(j,i,e)&&a.ui.isOverAxis(f,h,g)}})})(jQuery);/*! * jQuery UI Widget 1.8.18 * * Copyright 2011, AUTHORS.txt (http://jqueryui.com/about) * Dual licensed under the MIT or GPL Version 2 licenses. * http://jquery.org/license * * http://docs.jquery.com/UI/Widget */ (function(b,d){if(b.cleanData){var c=b.cleanData;b.cleanData=function(f){for(var g=0,h;(h=f[g])!=null;g++){try{b(h).triggerHandler("remove")}catch(j){}}c(f)}}else{var a=b.fn.remove;b.fn.remove=function(e,f){return this.each(function(){if(!f){if(!e||b.filter(e,[this]).length){b("*",this).add([this]).each(function(){try{b(this).triggerHandler("remove")}catch(g){}})}}return a.call(b(this),e,f)})}}b.widget=function(f,h,e){var g=f.split(".")[0],j;f=f.split(".")[1];j=g+"-"+f;if(!e){e=h;h=b.Widget}b.expr[":"][j]=function(k){return !!b.data(k,f)};b[g]=b[g]||{};b[g][f]=function(k,l){if(arguments.length){this._createWidget(k,l)}};var i=new h();i.options=b.extend(true,{},i.options);b[g][f].prototype=b.extend(true,i,{namespace:g,widgetName:f,widgetEventPrefix:b[g][f].prototype.widgetEventPrefix||f,widgetBaseClass:j},e);b.widget.bridge(f,b[g][f])};b.widget.bridge=function(f,e){b.fn[f]=function(i){var g=typeof i==="string",h=Array.prototype.slice.call(arguments,1),j=this;i=!g&&h.length?b.extend.apply(null,[true,i].concat(h)):i;if(g&&i.charAt(0)==="_"){return j}if(g){this.each(function(){var k=b.data(this,f),l=k&&b.isFunction(k[i])?k[i].apply(k,h):k;if(l!==k&&l!==d){j=l;return false}})}else{this.each(function(){var k=b.data(this,f);if(k){k.option(i||{})._init()}else{b.data(this,f,new e(i,this))}})}return j}};b.Widget=function(e,f){if(arguments.length){this._createWidget(e,f)}};b.Widget.prototype={widgetName:"widget",widgetEventPrefix:"",options:{disabled:false},_createWidget:function(f,g){b.data(g,this.widgetName,this);this.element=b(g);this.options=b.extend(true,{},this.options,this._getCreateOptions(),f);var e=this;this.element.bind("remove."+this.widgetName,function(){e.destroy()});this._create();this._trigger("create");this._init()},_getCreateOptions:function(){return b.metadata&&b.metadata.get(this.element[0])[this.widgetName]},_create:function(){},_init:function(){},destroy:function(){this.element.unbind("."+this.widgetName).removeData(this.widgetName);this.widget().unbind("."+this.widgetName).removeAttr("aria-disabled").removeClass(this.widgetBaseClass+"-disabled ui-state-disabled")},widget:function(){return this.element},option:function(f,g){var e=f;if(arguments.length===0){return b.extend({},this.options)}if(typeof f==="string"){if(g===d){return this.options[f]}e={};e[f]=g}this._setOptions(e);return this},_setOptions:function(f){var e=this;b.each(f,function(g,h){e._setOption(g,h)});return this},_setOption:function(e,f){this.options[e]=f;if(e==="disabled"){this.widget()[f?"addClass":"removeClass"](this.widgetBaseClass+"-disabled ui-state-disabled").attr("aria-disabled",f)}return this},enable:function(){return this._setOption("disabled",false)},disable:function(){return this._setOption("disabled",true)},_trigger:function(e,f,g){var j,i,h=this.options[e];g=g||{};f=b.Event(f);f.type=(e===this.widgetEventPrefix?e:this.widgetEventPrefix+e).toLowerCase();f.target=this.element[0];i=f.originalEvent;if(i){for(j in i){if(!(j in f)){f[j]=i[j]}}}this.element.trigger(f,g);return !(b.isFunction(h)&&h.call(this.element[0],f,g)===false||f.isDefaultPrevented())}}})(jQuery);/*! * jQuery UI Mouse 1.8.18 * * Copyright 2011, AUTHORS.txt (http://jqueryui.com/about) * Dual licensed under the MIT or GPL Version 2 licenses. * http://jquery.org/license * * http://docs.jquery.com/UI/Mouse * * Depends: * jquery.ui.widget.js */ (function(b,c){var a=false;b(document).mouseup(function(d){a=false});b.widget("ui.mouse",{options:{cancel:":input,option",distance:1,delay:0},_mouseInit:function(){var d=this;this.element.bind("mousedown."+this.widgetName,function(e){return d._mouseDown(e)}).bind("click."+this.widgetName,function(e){if(true===b.data(e.target,d.widgetName+".preventClickEvent")){b.removeData(e.target,d.widgetName+".preventClickEvent");e.stopImmediatePropagation();return false}});this.started=false},_mouseDestroy:function(){this.element.unbind("."+this.widgetName)},_mouseDown:function(f){if(a){return}(this._mouseStarted&&this._mouseUp(f));this._mouseDownEvent=f;var e=this,g=(f.which==1),d=(typeof this.options.cancel=="string"&&f.target.nodeName?b(f.target).closest(this.options.cancel).length:false);if(!g||d||!this._mouseCapture(f)){return true}this.mouseDelayMet=!this.options.delay;if(!this.mouseDelayMet){this._mouseDelayTimer=setTimeout(function(){e.mouseDelayMet=true},this.options.delay)}if(this._mouseDistanceMet(f)&&this._mouseDelayMet(f)){this._mouseStarted=(this._mouseStart(f)!==false);if(!this._mouseStarted){f.preventDefault();return true}}if(true===b.data(f.target,this.widgetName+".preventClickEvent")){b.removeData(f.target,this.widgetName+".preventClickEvent")}this._mouseMoveDelegate=function(h){return e._mouseMove(h)};this._mouseUpDelegate=function(h){return e._mouseUp(h)};b(document).bind("mousemove."+this.widgetName,this._mouseMoveDelegate).bind("mouseup."+this.widgetName,this._mouseUpDelegate);f.preventDefault();a=true;return true},_mouseMove:function(d){if(b.browser.msie&&!(document.documentMode>=9)&&!d.button){return this._mouseUp(d)}if(this._mouseStarted){this._mouseDrag(d);return d.preventDefault()}if(this._mouseDistanceMet(d)&&this._mouseDelayMet(d)){this._mouseStarted=(this._mouseStart(this._mouseDownEvent,d)!==false);(this._mouseStarted?this._mouseDrag(d):this._mouseUp(d))}return !this._mouseStarted},_mouseUp:function(d){b(document).unbind("mousemove."+this.widgetName,this._mouseMoveDelegate).unbind("mouseup."+this.widgetName,this._mouseUpDelegate);if(this._mouseStarted){this._mouseStarted=false;if(d.target==this._mouseDownEvent.target){b.data(d.target,this.widgetName+".preventClickEvent",true)}this._mouseStop(d)}return false},_mouseDistanceMet:function(d){return(Math.max(Math.abs(this._mouseDownEvent.pageX-d.pageX),Math.abs(this._mouseDownEvent.pageY-d.pageY))>=this.options.distance)},_mouseDelayMet:function(d){return this.mouseDelayMet},_mouseStart:function(d){},_mouseDrag:function(d){},_mouseStop:function(d){},_mouseCapture:function(d){return true}})})(jQuery);(function(c,d){c.widget("ui.resizable",c.ui.mouse,{widgetEventPrefix:"resize",options:{alsoResize:false,animate:false,animateDuration:"slow",animateEasing:"swing",aspectRatio:false,autoHide:false,containment:false,ghost:false,grid:false,handles:"e,s,se",helper:false,maxHeight:null,maxWidth:null,minHeight:10,minWidth:10,zIndex:1000},_create:function(){var f=this,k=this.options;this.element.addClass("ui-resizable");c.extend(this,{_aspectRatio:!!(k.aspectRatio),aspectRatio:k.aspectRatio,originalElement:this.element,_proportionallyResizeElements:[],_helper:k.helper||k.ghost||k.animate?k.helper||"ui-resizable-helper":null});if(this.element[0].nodeName.match(/canvas|textarea|input|select|button|img/i)){this.element.wrap(c('
').css({position:this.element.css("position"),width:this.element.outerWidth(),height:this.element.outerHeight(),top:this.element.css("top"),left:this.element.css("left")}));this.element=this.element.parent().data("resizable",this.element.data("resizable"));this.elementIsWrapper=true;this.element.css({marginLeft:this.originalElement.css("marginLeft"),marginTop:this.originalElement.css("marginTop"),marginRight:this.originalElement.css("marginRight"),marginBottom:this.originalElement.css("marginBottom")});this.originalElement.css({marginLeft:0,marginTop:0,marginRight:0,marginBottom:0});this.originalResizeStyle=this.originalElement.css("resize");this.originalElement.css("resize","none");this._proportionallyResizeElements.push(this.originalElement.css({position:"static",zoom:1,display:"block"}));this.originalElement.css({margin:this.originalElement.css("margin")});this._proportionallyResize()}this.handles=k.handles||(!c(".ui-resizable-handle",this.element).length?"e,s,se":{n:".ui-resizable-n",e:".ui-resizable-e",s:".ui-resizable-s",w:".ui-resizable-w",se:".ui-resizable-se",sw:".ui-resizable-sw",ne:".ui-resizable-ne",nw:".ui-resizable-nw"});if(this.handles.constructor==String){if(this.handles=="all"){this.handles="n,e,s,w,se,sw,ne,nw"}var l=this.handles.split(",");this.handles={};for(var g=0;g
');if(/sw|se|ne|nw/.test(j)){h.css({zIndex:++k.zIndex})}if("se"==j){h.addClass("ui-icon ui-icon-gripsmall-diagonal-se")}this.handles[j]=".ui-resizable-"+j;this.element.append(h)}}this._renderAxis=function(q){q=q||this.element;for(var n in this.handles){if(this.handles[n].constructor==String){this.handles[n]=c(this.handles[n],this.element).show()}if(this.elementIsWrapper&&this.originalElement[0].nodeName.match(/textarea|input|select|button/i)){var o=c(this.handles[n],this.element),p=0;p=/sw|ne|nw|se|n|s/.test(n)?o.outerHeight():o.outerWidth();var m=["padding",/ne|nw|n/.test(n)?"Top":/se|sw|s/.test(n)?"Bottom":/^e$/.test(n)?"Right":"Left"].join("");q.css(m,p);this._proportionallyResize()}if(!c(this.handles[n]).length){continue}}};this._renderAxis(this.element);this._handles=c(".ui-resizable-handle",this.element).disableSelection();this._handles.mouseover(function(){if(!f.resizing){if(this.className){var i=this.className.match(/ui-resizable-(se|sw|ne|nw|n|e|s|w)/i)}f.axis=i&&i[1]?i[1]:"se"}});if(k.autoHide){this._handles.hide();c(this.element).addClass("ui-resizable-autohide").hover(function(){if(k.disabled){return}c(this).removeClass("ui-resizable-autohide");f._handles.show()},function(){if(k.disabled){return}if(!f.resizing){c(this).addClass("ui-resizable-autohide");f._handles.hide()}})}this._mouseInit()},destroy:function(){this._mouseDestroy();var e=function(g){c(g).removeClass("ui-resizable ui-resizable-disabled ui-resizable-resizing").removeData("resizable").unbind(".resizable").find(".ui-resizable-handle").remove()};if(this.elementIsWrapper){e(this.element);var f=this.element;f.after(this.originalElement.css({position:f.css("position"),width:f.outerWidth(),height:f.outerHeight(),top:f.css("top"),left:f.css("left")})).remove()}this.originalElement.css("resize",this.originalResizeStyle);e(this.originalElement);return this},_mouseCapture:function(f){var g=false;for(var e in this.handles){if(c(this.handles[e])[0]==f.target){g=true}}return !this.options.disabled&&g},_mouseStart:function(g){var j=this.options,f=this.element.position(),e=this.element;this.resizing=true;this.documentScroll={top:c(document).scrollTop(),left:c(document).scrollLeft()};if(e.is(".ui-draggable")||(/absolute/).test(e.css("position"))){e.css({position:"absolute",top:f.top,left:f.left})}this._renderProxy();var k=b(this.helper.css("left")),h=b(this.helper.css("top"));if(j.containment){k+=c(j.containment).scrollLeft()||0;h+=c(j.containment).scrollTop()||0}this.offset=this.helper.offset();this.position={left:k,top:h};this.size=this._helper?{width:e.outerWidth(),height:e.outerHeight()}:{width:e.width(),height:e.height()};this.originalSize=this._helper?{width:e.outerWidth(),height:e.outerHeight()}:{width:e.width(),height:e.height()};this.originalPosition={left:k,top:h};this.sizeDiff={width:e.outerWidth()-e.width(),height:e.outerHeight()-e.height()};this.originalMousePosition={left:g.pageX,top:g.pageY};this.aspectRatio=(typeof j.aspectRatio=="number")?j.aspectRatio:((this.originalSize.width/this.originalSize.height)||1);var i=c(".ui-resizable-"+this.axis).css("cursor");c("body").css("cursor",i=="auto"?this.axis+"-resize":i);e.addClass("ui-resizable-resizing");this._propagate("start",g);return true},_mouseDrag:function(e){var h=this.helper,g=this.options,m={},q=this,j=this.originalMousePosition,n=this.axis;var r=(e.pageX-j.left)||0,p=(e.pageY-j.top)||0;var i=this._change[n];if(!i){return false}var l=i.apply(this,[e,r,p]),k=c.browser.msie&&c.browser.version<7,f=this.sizeDiff;this._updateVirtualBoundaries(e.shiftKey);if(this._aspectRatio||e.shiftKey){l=this._updateRatio(l,e)}l=this._respectSize(l,e);this._propagate("resize",e);h.css({top:this.position.top+"px",left:this.position.left+"px",width:this.size.width+"px",height:this.size.height+"px"});if(!this._helper&&this._proportionallyResizeElements.length){this._proportionallyResize()}this._updateCache(l);this._trigger("resize",e,this.ui());return false},_mouseStop:function(h){this.resizing=false;var i=this.options,m=this;if(this._helper){var g=this._proportionallyResizeElements,e=g.length&&(/textarea/i).test(g[0].nodeName),f=e&&c.ui.hasScroll(g[0],"left")?0:m.sizeDiff.height,k=e?0:m.sizeDiff.width;var n={width:(m.helper.width()-k),height:(m.helper.height()-f)},j=(parseInt(m.element.css("left"),10)+(m.position.left-m.originalPosition.left))||null,l=(parseInt(m.element.css("top"),10)+(m.position.top-m.originalPosition.top))||null;if(!i.animate){this.element.css(c.extend(n,{top:l,left:j}))}m.helper.height(m.size.height);m.helper.width(m.size.width);if(this._helper&&!i.animate){this._proportionallyResize()}}c("body").css("cursor","auto");this.element.removeClass("ui-resizable-resizing");this._propagate("stop",h);if(this._helper){this.helper.remove()}return false},_updateVirtualBoundaries:function(g){var j=this.options,i,h,f,k,e;e={minWidth:a(j.minWidth)?j.minWidth:0,maxWidth:a(j.maxWidth)?j.maxWidth:Infinity,minHeight:a(j.minHeight)?j.minHeight:0,maxHeight:a(j.maxHeight)?j.maxHeight:Infinity};if(this._aspectRatio||g){i=e.minHeight*this.aspectRatio;f=e.minWidth/this.aspectRatio;h=e.maxHeight*this.aspectRatio;k=e.maxWidth/this.aspectRatio;if(i>e.minWidth){e.minWidth=i}if(f>e.minHeight){e.minHeight=f}if(hl.width),s=a(l.height)&&i.minHeight&&(i.minHeight>l.height);if(h){l.width=i.minWidth}if(s){l.height=i.minHeight}if(t){l.width=i.maxWidth}if(m){l.height=i.maxHeight}var f=this.originalPosition.left+this.originalSize.width,p=this.position.top+this.size.height;var k=/sw|nw|w/.test(q),e=/nw|ne|n/.test(q);if(h&&k){l.left=f-i.minWidth}if(t&&k){l.left=f-i.maxWidth}if(s&&e){l.top=p-i.minHeight}if(m&&e){l.top=p-i.maxHeight}var n=!l.width&&!l.height;if(n&&!l.left&&l.top){l.top=null}else{if(n&&!l.top&&l.left){l.left=null}}return l},_proportionallyResize:function(){var k=this.options;if(!this._proportionallyResizeElements.length){return}var g=this.helper||this.element;for(var f=0;f');var e=c.browser.msie&&c.browser.version<7,g=(e?1:0),h=(e?2:-1);this.helper.addClass(this._helper).css({width:this.element.outerWidth()+h,height:this.element.outerHeight()+h,position:"absolute",left:this.elementOffset.left-g+"px",top:this.elementOffset.top-g+"px",zIndex:++i.zIndex});this.helper.appendTo("body").disableSelection()}else{this.helper=this.element}},_change:{e:function(g,f,e){return{width:this.originalSize.width+f}},w:function(h,f,e){var j=this.options,g=this.originalSize,i=this.originalPosition;return{left:i.left+f,width:g.width-f}},n:function(h,f,e){var j=this.options,g=this.originalSize,i=this.originalPosition;return{top:i.top+e,height:g.height-e}},s:function(g,f,e){return{height:this.originalSize.height+e}},se:function(g,f,e){return c.extend(this._change.s.apply(this,arguments),this._change.e.apply(this,[g,f,e]))},sw:function(g,f,e){return c.extend(this._change.s.apply(this,arguments),this._change.w.apply(this,[g,f,e]))},ne:function(g,f,e){return c.extend(this._change.n.apply(this,arguments),this._change.e.apply(this,[g,f,e]))},nw:function(g,f,e){return c.extend(this._change.n.apply(this,arguments),this._change.w.apply(this,[g,f,e]))}},_propagate:function(f,e){c.ui.plugin.call(this,f,[e,this.ui()]);(f!="resize"&&this._trigger(f,e,this.ui()))},plugins:{},ui:function(){return{originalElement:this.originalElement,element:this.element,helper:this.helper,position:this.position,size:this.size,originalSize:this.originalSize,originalPosition:this.originalPosition}}});c.extend(c.ui.resizable,{version:"1.8.18"});c.ui.plugin.add("resizable","alsoResize",{start:function(f,g){var e=c(this).data("resizable"),i=e.options;var h=function(j){c(j).each(function(){var k=c(this);k.data("resizable-alsoresize",{width:parseInt(k.width(),10),height:parseInt(k.height(),10),left:parseInt(k.css("left"),10),top:parseInt(k.css("top"),10)})})};if(typeof(i.alsoResize)=="object"&&!i.alsoResize.parentNode){if(i.alsoResize.length){i.alsoResize=i.alsoResize[0];h(i.alsoResize)}else{c.each(i.alsoResize,function(j){h(j)})}}else{h(i.alsoResize)}},resize:function(g,i){var f=c(this).data("resizable"),j=f.options,h=f.originalSize,l=f.originalPosition;var k={height:(f.size.height-h.height)||0,width:(f.size.width-h.width)||0,top:(f.position.top-l.top)||0,left:(f.position.left-l.left)||0},e=function(m,n){c(m).each(function(){var q=c(this),r=c(this).data("resizable-alsoresize"),p={},o=n&&n.length?n:q.parents(i.originalElement[0]).length?["width","height"]:["width","height","top","left"];c.each(o,function(s,u){var t=(r[u]||0)+(k[u]||0);if(t&&t>=0){p[u]=t||null}});q.css(p)})};if(typeof(j.alsoResize)=="object"&&!j.alsoResize.nodeType){c.each(j.alsoResize,function(m,n){e(m,n)})}else{e(j.alsoResize)}},stop:function(e,f){c(this).removeData("resizable-alsoresize")}});c.ui.plugin.add("resizable","animate",{stop:function(i,n){var p=c(this).data("resizable"),j=p.options;var h=p._proportionallyResizeElements,e=h.length&&(/textarea/i).test(h[0].nodeName),f=e&&c.ui.hasScroll(h[0],"left")?0:p.sizeDiff.height,l=e?0:p.sizeDiff.width;var g={width:(p.size.width-l),height:(p.size.height-f)},k=(parseInt(p.element.css("left"),10)+(p.position.left-p.originalPosition.left))||null,m=(parseInt(p.element.css("top"),10)+(p.position.top-p.originalPosition.top))||null;p.element.animate(c.extend(g,m&&k?{top:m,left:k}:{}),{duration:j.animateDuration,easing:j.animateEasing,step:function(){var o={width:parseInt(p.element.css("width"),10),height:parseInt(p.element.css("height"),10),top:parseInt(p.element.css("top"),10),left:parseInt(p.element.css("left"),10)};if(h&&h.length){c(h[0]).css({width:o.width,height:o.height})}p._updateCache(o);p._propagate("resize",i)}})}});c.ui.plugin.add("resizable","containment",{start:function(f,r){var t=c(this).data("resizable"),j=t.options,l=t.element;var g=j.containment,k=(g instanceof c)?g.get(0):(/parent/.test(g))?l.parent().get(0):g;if(!k){return}t.containerElement=c(k);if(/document/.test(g)||g==document){t.containerOffset={left:0,top:0};t.containerPosition={left:0,top:0};t.parentData={element:c(document),left:0,top:0,width:c(document).width(),height:c(document).height()||document.body.parentNode.scrollHeight}}else{var n=c(k),i=[];c(["Top","Right","Left","Bottom"]).each(function(p,o){i[p]=b(n.css("padding"+o))});t.containerOffset=n.offset();t.containerPosition=n.position();t.containerSize={height:(n.innerHeight()-i[3]),width:(n.innerWidth()-i[1])};var q=t.containerOffset,e=t.containerSize.height,m=t.containerSize.width,h=(c.ui.hasScroll(k,"left")?k.scrollWidth:m),s=(c.ui.hasScroll(k)?k.scrollHeight:e);t.parentData={element:k,left:q.left,top:q.top,width:h,height:s}}},resize:function(g,q){var t=c(this).data("resizable"),i=t.options,f=t.containerSize,p=t.containerOffset,m=t.size,n=t.position,r=t._aspectRatio||g.shiftKey,e={top:0,left:0},h=t.containerElement;if(h[0]!=document&&(/static/).test(h.css("position"))){e=p}if(n.left<(t._helper?p.left:0)){t.size.width=t.size.width+(t._helper?(t.position.left-p.left):(t.position.left-e.left));if(r){t.size.height=t.size.width/i.aspectRatio}t.position.left=i.helper?p.left:0}if(n.top<(t._helper?p.top:0)){t.size.height=t.size.height+(t._helper?(t.position.top-p.top):t.position.top);if(r){t.size.width=t.size.height*i.aspectRatio}t.position.top=t._helper?p.top:0}t.offset.left=t.parentData.left+t.position.left;t.offset.top=t.parentData.top+t.position.top;var l=Math.abs((t._helper?t.offset.left-e.left:(t.offset.left-e.left))+t.sizeDiff.width),s=Math.abs((t._helper?t.offset.top-e.top:(t.offset.top-p.top))+t.sizeDiff.height);var k=t.containerElement.get(0)==t.element.parent().get(0),j=/relative|absolute/.test(t.containerElement.css("position"));if(k&&j){l-=t.parentData.left}if(l+t.size.width>=t.parentData.width){t.size.width=t.parentData.width-l;if(r){t.size.height=t.size.width/t.aspectRatio}}if(s+t.size.height>=t.parentData.height){t.size.height=t.parentData.height-s;if(r){t.size.width=t.size.height*t.aspectRatio}}},stop:function(f,n){var q=c(this).data("resizable"),g=q.options,l=q.position,m=q.containerOffset,e=q.containerPosition,i=q.containerElement;var j=c(q.helper),r=j.offset(),p=j.outerWidth()-q.sizeDiff.width,k=j.outerHeight()-q.sizeDiff.height;if(q._helper&&!g.animate&&(/relative/).test(i.css("position"))){c(this).css({left:r.left-e.left-m.left,width:p,height:k})}if(q._helper&&!g.animate&&(/static/).test(i.css("position"))){c(this).css({left:r.left-e.left-m.left,width:p,height:k})}}});c.ui.plugin.add("resizable","ghost",{start:function(g,h){var e=c(this).data("resizable"),i=e.options,f=e.size;e.ghost=e.originalElement.clone();e.ghost.css({opacity:0.25,display:"block",position:"relative",height:f.height,width:f.width,margin:0,left:0,top:0}).addClass("ui-resizable-ghost").addClass(typeof i.ghost=="string"?i.ghost:"");e.ghost.appendTo(e.helper)},resize:function(f,g){var e=c(this).data("resizable"),h=e.options;if(e.ghost){e.ghost.css({position:"relative",height:e.size.height,width:e.size.width})}},stop:function(f,g){var e=c(this).data("resizable"),h=e.options;if(e.ghost&&e.helper){e.helper.get(0).removeChild(e.ghost.get(0))}}});c.ui.plugin.add("resizable","grid",{resize:function(e,m){var p=c(this).data("resizable"),h=p.options,k=p.size,i=p.originalSize,j=p.originalPosition,n=p.axis,l=h._aspectRatio||e.shiftKey;h.grid=typeof h.grid=="number"?[h.grid,h.grid]:h.grid;var g=Math.round((k.width-i.width)/(h.grid[0]||1))*(h.grid[0]||1),f=Math.round((k.height-i.height)/(h.grid[1]||1))*(h.grid[1]||1);if(/^(se|s|e)$/.test(n)){p.size.width=i.width+g;p.size.height=i.height+f}else{if(/^(ne)$/.test(n)){p.size.width=i.width+g;p.size.height=i.height+f;p.position.top=j.top-f}else{if(/^(sw)$/.test(n)){p.size.width=i.width+g;p.size.height=i.height+f;p.position.left=j.left-g}else{p.size.width=i.width+g;p.size.height=i.height+f;p.position.top=j.top-f;p.position.left=j.left-g}}}}});var b=function(e){return parseInt(e,10)||0};var a=function(e){return !isNaN(parseInt(e,10))}})(jQuery);/*! * jQuery hashchange event - v1.3 - 7/21/2010 * http://benalman.com/projects/jquery-hashchange-plugin/ * * Copyright (c) 2010 "Cowboy" Ben Alman * Dual licensed under the MIT and GPL licenses. * http://benalman.com/about/license/ */ (function($,e,b){var c="hashchange",h=document,f,g=$.event.special,i=h.documentMode,d="on"+c in e&&(i===b||i>7);function a(j){j=j||location.href;return"#"+j.replace(/^[^#]*#?(.*)$/,"$1")}$.fn[c]=function(j){return j?this.bind(c,j):this.trigger(c)};$.fn[c].delay=50;g[c]=$.extend(g[c],{setup:function(){if(d){return false}$(f.start)},teardown:function(){if(d){return false}$(f.stop)}});f=(function(){var j={},p,m=a(),k=function(q){return q},l=k,o=k;j.start=function(){p||n()};j.stop=function(){p&&clearTimeout(p);p=b};function n(){var r=a(),q=o(m);if(r!==m){l(m=r,q);$(e).trigger(c)}else{if(q!==m){location.href=location.href.replace(/#.*/,"")+q}}p=setTimeout(n,$.fn[c].delay)}$.browser.msie&&!d&&(function(){var q,r;j.start=function(){if(!q){r=$.fn[c].src;r=r&&r+a();q=$('