Ejemplo n.º 1
0
function if_article_section($atts, $thing)
{
    global $thisarticle;
    assert_article();
    extract(lAtts(array('name' => ''), $atts));
    $section = $thisarticle['section'];
    return parse(EvalElse($thing, in_list($section, $name)));
}
Ejemplo n.º 2
0
/**
 * Checks if a user has privileges to the given resource.
 *
 * @param   string $res  The resource
 * @param   string $user The user. If no user name is supplied, assume the current logged in user
 * @return  bool
 * @package User
 * @example
 * add_privs('my_privilege_resource', '1,2,3');
 * if (has_privs('my_privilege_resource', 'username'))
 * {
 *     echo "'username' has privileges to 'my_privilege_resource'.";
 * }
 */
function has_privs($res, $user = '')
{
    global $txp_user, $txp_permissions;
    static $privs;
    $user = (string) $user;
    if ($user === '') {
        $user = (string) $txp_user;
    }
    if ($user !== '') {
        if (!isset($privs[$user])) {
            $privs[$user] = safe_field("privs", "txp_users", "name = '" . doSlash($user) . "'");
        }
        if (isset($txp_permissions[$res]) && $privs[$user] && $txp_permissions[$res]) {
            return in_list($privs[$user], $txp_permissions[$res]);
        }
    }
    return false;
}
/**
Plugin: ob1_pagination
URL: http://rise.lewander.com/textpattern/ob1-pagination
Released under the Creative Commons Attribution-Share Alike 3.0 Unported, http://creativecommons.org/licenses/by-sa/3.0/
*/
function ob1_pagination($atts)
{
    global $thispage, $q, $prefs, $pretext;
    extract($pretext);
    if (is_array($thispage)) {
        extract($thispage);
    }
    extract($prefs);
    if (!isset($pg)) {
        $pg = 1;
    }
    $numberOfTabs = empty($thispage) ? 1 : $numPages;
    if (defined('L10N_DEBUG_URLREWRITE') && L10N_DEBUG_URLREWRITE) {
        dmp('$pretext as seen by ob1_pagination_mlp...');
        dmp($pretext);
    }
    extract(lAtts(array('maximumtabs' => '11', 'firsttext' => '«', 'firsttexttitle' => 'First', 'previoustext' => '‹', 'previoustexttitle' => 'Previous', 'lasttext' => '»', 'lasttexttitle' => 'Last', 'nexttext' => '›', 'nexttexttitle' => 'Next', 'pagetext' => 'Page', 'ulid' => '', 'ulclass' => '', 'liclass' => '', 'liselected' => '', 'liselectedtext' => '', 'liempty' => '', 'linkcurrent' => '0', 'outputlastfirst' => '1', 'outputnextprevious' => '1', 'reversenumberorder' => '0', 'moretabsdisplay' => '', 'moretabstext' => '...', 'wraptag' => '', 'mode' => 'relative'), $atts));
    $url = '';
    if (defined('L10N_SNIPPET_IO_HEADER') || $mode === 'full') {
        $url = hu . ltrim($req, '/');
        $cn_qs = strlen($qs);
        if ($cn_qs > 0) {
            $cn_qs += 1;
        }
        $cn_req = strlen($url);
        $url = substr($url, 0, $cn_req - $cn_qs);
    }
    if (defined('L10N_DEBUG_URLREWRITE') && L10N_DEBUG_URLREWRITE) {
        dmp($url);
    }
    $ulid = empty($ulid) ? '' : ' id="' . $ulid . '"';
    $ulclass = empty($ulclass) ? '' : ' class="' . $ulclass . '"';
    $addToURL = $permlink_mode == 'messy' ? '&s=' . $s : '';
    $addToURL .= $c ? '&c=' . $c : '';
    # if we got tabs, start the outputting
    if ($numberOfTabs > 1) {
        if ($maximumtabs == 1) {
            $maximumtabs = 11;
        }
        # using just one tab is folly! folly i say
        # this is for the search
        if ($q and is_callable(@ob1_advanced_search)) {
            # if you're using ob1_advanced_search [v1.0b and above], add some stuff to the URL
            $ob1ASGet = array('rpp', 'wh', 'ww', 'oc', 'ad', 'sd', 'ed', 'bts');
            foreach ($ob1ASGet as $val) {
                ${$val} = !empty($_GET[$val]) ? '&' . $val . '=' . urlencode($_GET[$val]) : '';
            }
            $addToURL .= '&q=' . urlencode($q) . $rpp . $wh . $ww . $oc . $ad . $sd . $ed . $bts;
            unset($ob1ASGet, $rpp, $wh, $ww, $oc, $ad, $sd, $ed, $bts);
        } elseif ($q) {
            $addToURL .= '&q=' . urlencode($q);
        }
        if ($numberOfTabs > $maximumtabs) {
            $loopStart = $pg - floor($maximumtabs / 2);
            $loopEnd = $loopStart + $maximumtabs;
            if ($loopStart < 1) {
                $loopStart = 1;
                $loopEnd = $maximumtabs + 1;
            }
            if ($loopEnd > $numberOfTabs) {
                $loopEnd = $numberOfTabs + 1;
                $loopStart = $loopEnd - $maximumtabs;
                if ($loopStart < 1) {
                    $loopStart = 1;
                }
            }
        } else {
            $loopStart = 1;
            $loopEnd = $maximumtabs + 1;
        }
        if ($loopEnd > $numberOfTabs) {
            $loopEnd = $numberOfTabs + 1;
        }
        $out = array();
        if ($pg > 1) {
            $out[] = $outputlastfirst ? '<li class="' . $liclass . '"><a href="' . $url . '?pg=1' . $addToURL . '" title="' . $firsttexttitle . '">' . $firsttext . '</a></li>' . n : '';
            $out[] = $outputnextprevious ? '<li class="' . $liclass . '"><a href="' . $url . '?pg=' . ($pg - 1) . $addToURL . '" title="' . $previoustexttitle . '">' . $previoustext . '</a></li>' . n : '';
        } else {
            $out[] = $outputlastfirst ? '<li class="' . $liempty . ' ' . $liclass . '">' . $firsttext . '</li>' . n : '';
            $out[] = $outputnextprevious ? '<li class="' . $liempty . ' ' . $liclass . '">' . $previoustext . '</li>' . n : '';
        }
        if (in_list('before', $moretabsdisplay) and $loopStart > 1) {
            $out[] = '<li class="' . $liclass . ' ' . $liempty . '">' . $moretabstext . '</li>';
        }
        for ($i = $loopStart; $i < $loopEnd; $i++) {
            if ($i == $pg) {
                $out[] = '<li class="' . $liselected . ' ' . $liclass;
                $out[] = $linkcurrent ? '">' : ' ' . $liempty . '">';
                $out[] = $linkcurrent ? '<a href="' . $url . '?pg=' . $i . $addToURL . '" title="' . $pagetext : '';
                if ($reversenumberorder) {
                    $out[] = $linkcurrent ? ' ' . ($numberOfTabs - $i + 1) . '">' : '';
                    $out[] = $liselectedtext ? $liselectedtext : $numberOfTabs - $i + 1;
                } else {
                    $out[] = $linkcurrent ? ' ' . $i . '">' : '';
                    $out[] = $liselectedtext ? $liselectedtext : $i;
                }
                $out[] = $linkcurrent ? '</a>' : '';
                $out[] = '</li>' . n;
            } else {
                $out[] = '<li class="' . $liclass . '"><a href="' . $url . '?pg=' . $i . $addToURL . '" title="' . $pagetext;
                $out[] = $reversenumberorder ? ' ' . ($numberOfTabs - $i + 1) . '">' . ($numberOfTabs - $i + 1) : ' ' . $i . '">' . $i;
                $out[] = '</a></li>' . n;
            }
        }
        if (in_list('after', $moretabsdisplay) and $loopEnd <= $numberOfTabs) {
            $out[] = '<li class="' . $liclass . ' ' . $liempty . '">' . $moretabstext . '</li>';
        }
        if ($pg == $numberOfTabs) {
            $out[] = $outputnextprevious ? '<li class="' . $liempty . ' ' . $liclass . '">' . $nexttext . '</li>' . n : '';
            $out[] = $outputlastfirst ? '<li class="' . $liempty . ' ' . $liclass . '">' . $lasttext . '</li>' . n : '';
        } else {
            $out[] = $outputnextprevious ? '<li class="' . $liclass . '"><a href="' . $url . '?pg=' . ($pg + 1) . $addToURL . '" title="' . $nexttexttitle . '">' . $nexttext . '</a></li>' . n : '';
            $out[] = $outputlastfirst ? '<li class="' . $liclass . '"><a href="' . $url . '?pg=' . $numberOfTabs . $addToURL . '" title="' . $lasttexttitle . '">' . $lasttext . '</a></li>' . n : '';
        }
        return $wraptag ? tag('<ul' . $ulclass . $ulid . '>' . n . join('', $out) . '</ul>', $wraptag) : '<ul' . $ulclass . $ulid . '>' . n . join('', $out) . '</ul>';
    } else {
        return false;
    }
}
Ejemplo n.º 4
0
function if_section($atts, $thing)
{
    global $pretext;
    extract($pretext);
    extract(lAtts(array('name' => ''), $atts));
    $section = $s == 'default' ? '' : $s;
    return parse(EvalElse($thing, in_list($section, $name)));
}
Ejemplo n.º 5
0
 protected function andor($join = 'and')
 {
     $join = strtolower($join);
     return count($this->where) ? in_list($join, 'and,or') ? $join : 'and' : '';
 }
Ejemplo n.º 6
0
function smd_ebook_create()
{
    global $smd_ebook_prefs, $img_dir;
    @(include_once txpath . '/lib/classTextile.php');
    @(include_once txpath . '/publish.php');
    // for parse()
    $textile = new Textile();
    $template = smd_ebook_templates();
    $msg = '';
    $report = $toc = $ncx = $reps = $sheets = $lfout = array();
    // Generate a temporary folder name to store all files in.
    // It's based on the passed params so if you're regenerating the same book
    // and don't alter the POST payload, you'll overwrite stuff in the previous
    // folder for this book. Just keeps the clutter down..
    $ebook_folder = 'smd_ebook_' . substr(md5(serialize($_POST)), 0, 12);
    $ebook_path = get_pref('tempdir') . DS . $ebook_folder . DS;
    if (!is_readable($ebook_path)) {
        mkdir($ebook_path);
    }
    // Store the current type for next time this user creates a book
    $bType = ps('smd_ebook_type');
    set_pref('smd_ebook_type', doSlash($bType), 'smd_ebook', PREF_HIDDEN, 'text_input', 0, PREF_PRIVATE);
    $is_mobi = $bType === 'mobi';
    $is_epub = $bType === 'zip';
    $outfile = trim(ps('smd_ebook_pubfile'));
    // If used, it's without extension
    // Get Textile and encoding options
    $encoding = get_pref('smd_ebook_encoding', $smd_ebook_prefs['smd_ebook_encoding']['default']);
    $which = get_pref('smd_ebook_textile', $smd_ebook_prefs['smd_ebook_textile']['default']);
    $txt_description = in_list('description', $which);
    $txt_authornote = in_list('authornote', $which);
    // Build up a giant replacement table which is then substituted into
    // the various templates before passing to the generator
    // Set up the TOC wrappers
    $toc_wrap = get_pref('smd_ebook_toc_wraptag', $smd_ebook_prefs['smd_ebook_toc_wraptag']['default']);
    $toc_class = get_pref('smd_ebook_toc_class', $smd_ebook_prefs['smd_ebook_toc_class']['default']);
    $wrapit = $toc_wrap === 'ol' ? '#' : '*';
    $article_cnt = $ncx_cnt = $elem_cnt = $img_cnt = 0;
    $article_refs = $article_spines = $guide_refs = $landmarks = $master_image_refs = array();
    // Page break, stylesheets and heading references
    $pbr = get_pref('smd_ebook_page_break', $smd_ebook_prefs['smd_ebook_page_break']['default']);
    $css = get_pref('smd_ebook_stylesheet', $smd_ebook_prefs['smd_ebook_stylesheet']['default']);
    $hdg = get_pref('smd_ebook_heading_level', $smd_ebook_prefs['smd_ebook_heading_level']['default']);
    if ($css) {
        $css_list = quote_list(do_list($css));
        $sheets = $css_list ? safe_rows('name, css', 'txp_css', "name IN (" . join(',', $css_list) . ")") : array();
    }
    $sheetlist = $sheetcontent = array();
    $sheet_count = 0;
    foreach ($sheets as $stylething) {
        $content = trim($stylething['css']);
        if ($is_mobi && $content) {
            // Inline style tags
            $sheetlist[] = '<style type="text/css">' . $content . '</style>';
        } elseif ($is_epub && $content) {
            // External stylesheet references
            $sheetname = $stylething['name'] . '.css';
            $sheetlist[] = '<link rel="stylesheet" media="screen" href="' . $sheetname . '" />';
            $sheetcontent[$stylething['name']] = $content;
            // Add them to the manifest and listfile
            $article_refs[] = '<item id="smd_ebook_style_' . $sheet_count . '" media-type="text/css" href="' . $sheetname . '" />';
            $lfout[] = $sheetname;
        }
        $sheet_count++;
    }
    $sheet = join(n, $sheetlist);
    // The values used in the 'doc' template
    $html_from = array('{smd_ebook_doctype}', '{smd_ebook_namespace}', '{smd_ebook_charset}', '{smd_ebook_encoding}', '{smd_ebook_title}', '{smd_ebook_chaptitle}', '{smd_ebook_stylesheet}', '{smd_ebook_contents}');
    // Loop for each article in the collection
    foreach (ps('smd_ebook_articles') as $artid) {
        $article_cnt++;
        $id = str_replace('smd_ebook_article_', '', $artid);
        $row = safe_row('*, UNIX_TIMESTAMP(Posted) AS uPosted, UNIX_TIMESTAMP(LastMod) AS uModified', 'textpattern', "ID = '" . doSlash($id) . "'");
        if ($row) {
            // Initialize a few things
            $note_content = '';
            $image_list = array();
            $reps['{smd_ebook_file_name}'] = $cur_file = $row['url_title'] . '.html';
            $reps['{smd_ebook_encoding}'] = $encoding;
            // Each of the items starting !isset() are only ever loaded _once_ from the
            // first article in which they are found.
            // Begin by setting up the file names
            if (!isset($firstfile)) {
                $firstfile = $row['url_title'] . '.html';
                $filebase = sanitizeForFile($outfile === '' ? $row['url_title'] : $outfile);
                $listfile = $filebase . '.smd';
                $notefile = $filebase . '_notes.html';
                $toc_file = $filebase . '_toc.html';
                $ncx_file = $filebase . '.ncx';
                $end_file = $filebase . '_end.html';
                $opf_file = $filebase . '.opf';
                $lmk_file = $filebase . '_landmark.html';
                $cover_file = 'cover.html';
                $container_file = 'container.xml';
                $mimetype_file = 'mimetype';
                $toc_ref = 'toc';
            }
            // Populate the unique ID entries direcly into the .opf template,
            // as they're only used once each
            if (!isset($reps['{smd_ebook_uid_ref}'])) {
                $val = ps('smd_ebook_fld_uid');
                if (strpos($val, 'SMD_FLD_') !== false) {
                    $valfld = str_replace('SMD_FLD_', '', $val);
                    $val = isset($row[$valfld]) ? $row[$valfld] : '';
                }
                $uid = trim($val) === '' ? smd_ebook_uid() : $val;
                $is_isbn = smd_ebook_is_isbn($uid);
                $is_uuid = preg_match('/^[0-9a-f]{8,8}\\-[0-9a-f]{4,4}\\-[0-9a-f]{4,4}\\-[0-9a-f]{4,4}\\-[0-9a-f]{12,12}$/i', $uid) === 1;
                $full_uid = $reps['{smd_ebook_uid_ref}'] = $is_uuid ? 'urn:uuid:' . $uid : ($is_isbn ? 'urn:isbn:' . $uid : $uid);
                $template['opf'] = str_replace('{smd_ebook_uid_ref}', $uid ? ' unique-identifier="uid"' : '', $template['opf']);
                $template['opf'] = str_replace('{smd_ebook_md_uid}', $uid ? '<dc:identifier id="uid">' . $full_uid . '</dc:identifier>' : '', $template['opf']);
                $template['ncx'] = str_replace('{smd_ebook_dtb_uid}', $uid ? '<meta name="dtb:uid" content="' . $full_uid . '" />' : '', $template['ncx']);
            }
            // Language
            if (!isset($reps['{smd_ebook_md_lang}'])) {
                $lang = get_pref('language');
                $reps['{smd_ebook_md_lang}'] = '<dc:language>' . $lang . '</dc:language>';
                $reps['{smd_ebook_lang}'] = $lang;
            }
            // Author can come from:
            //  1) an article field
            //  2) the current logged in user
            //  3) user-supplied at book creation time
            //  4) hard-coded in plugin settings
            if (!isset($reps['{smd_ebook_md_creator}'])) {
                $val = ps('smd_ebook_fld_author');
                if (strpos($val, 'SMD_FLD_') !== false) {
                    $valfld = str_replace('SMD_FLD_', '', $val);
                    $val = isset($row[$valfld]) ? $valfld === 'AuthorID' ? get_author_name($row[$valfld]) : $row[$valfld] : '';
                }
                if ($val) {
                    $reps['{smd_ebook_md_creator}'] = '<dc:creator>' . $val . '</dc:creator>';
                    $reps['{smd_ebook_creator}'] = $val;
                }
            }
            // Doctype, namespace and charset
            if (!isset($reps['{smd_ebook_doctype}'])) {
                if ($is_mobi) {
                    $reps['{smd_ebook_doctype}'] = '';
                    $reps['{smd_ebook_namespace}'] = '';
                    $reps['{smd_ebook_charset}'] = '<meta http-equiv="Content-Type" content="text/html; charset=' . $encoding . '">';
                } elseif ($is_epub) {
                    $reps['{smd_ebook_doctype}'] = '<?xml version="1.0" encoding="' . $encoding . '"?>' . n . '<!DOCTYPE html>';
                    $reps['{smd_ebook_namespace}'] = ' xmlns="http://www.w3.org/1999/xhtml"';
                    $reps['{smd_ebook_charset}'] = '<meta charset="' . $encoding . '" />';
                }
            }
            // Publication / modification date
            if (!isset($reps['{smd_ebook_md_date}'])) {
                $reps['{smd_ebook_md_date}'] = '<dc:date>' . strftime('%Y-%m-%dT%H:%M:%SZ', $row['uPosted']) . '</dc:date>';
            }
            if (!isset($reps['{smd_ebook_md_modified}'])) {
                $reps['{smd_ebook_md_modified}'] = '<meta property="dcterms:modified">' . strftime('%Y-%m-%dT%H:%M:%SZ', $row['uModified']) . '</meta>';
            }
            // Cover image
            if (!isset($reps['{smd_ebook_md_cover}'])) {
                if (isset($row['Image'])) {
                    $img = safe_row('*', 'txp_image', "id='" . intval($row['Image']) . "'");
                    // Only GIFs, JPGs or PNGs need apply
                    if ($img) {
                        $mime_type = $img['ext'] === '.jpg' || $img['ext'] === '.jpeg' ? 'image/jpeg' : ($img['ext'] === '.gif' ? 'image/gif' : ($img['ext'] === '.png' ? 'image/png' : ''));
                        if ($mime_type) {
                            $img_file = $img['id'] . $img['ext'];
                            $reps['{smd_ebook_md_cover}'] = '<meta name="cover" content="cover-image" />';
                            if ($is_epub) {
                                $img_dest = 'cover' . $img['ext'];
                                $ret = copy(get_pref('path_to_site') . DS . $img_dir . DS . $img_file, $ebook_path . $img_dest);
                                if ($ret) {
                                    // Write the cover image HTML
                                    $fp = fopen($ebook_path . $cover_file, "wb");
                                    $from = array('{smd_ebook_image_link}', '{smd_ebook_image_alt}');
                                    $to = array($img_dest, $img['alt']);
                                    fwrite($fp, str_replace($from, $to, $template['cov']));
                                    fclose($fp);
                                    $reps['{smd_ebook_manifest_cover}'] = '<item id="cover" media-type="application/xhtml+xml" href="cover.html" />' . n . t . t . '<item id="cover-image" properties="cover-image" media-type="' . $mime_type . '" href="' . $img_dest . '" />';
                                    $lfout[] = $img_dest;
                                }
                            } else {
                                $reps['{smd_ebook_manifest_cover}'] = '<item id="cover-image" media-type="' . $mime_type . '" href="' . get_pref('path_to_site') . DS . $img_dir . DS . $img_file . '" />';
                            }
                        }
                    }
                }
            }
            // The following values can either come from the given field or be used verbatim
            // Firstly the title, description, subject, publisher and chapter title
            $setMany = array('chaptitle');
            foreach (array('title', 'description', 'subject', 'publisher', 'chaptitle') as $thingy) {
                if (in_array($thingy, $setMany) || !isset($reps['{smd_ebook_md_' . $thingy . '}'])) {
                    $val = ps('smd_ebook_fld_' . $thingy);
                    if (strpos($val, 'SMD_FLD_') !== false) {
                        $valfld = str_replace('SMD_FLD_', '', $val);
                        $val = isset($row[$valfld]) ? $row[$valfld] : '';
                    }
                    if ($val) {
                        // Textile the content?
                        $content = isset($txt_[$thingy]) && $txt_[$thingy] ? trim($textile->TextileThis($val)) : trim($val);
                        if (!in_array($thingy, $setMany)) {
                            $reps['{smd_ebook_md_' . $thingy . '}'] = '<dc:' . $thingy . '>' . $content . '</dc:' . $thingy . '>';
                        }
                        // There are two titles: one for the metadata and one raw so if the title
                        // has just been found, populate the raw title too
                        if ($thingy === 'title') {
                            $reps['{smd_ebook_title}'] = $content;
                        } elseif ($thingy === 'chaptitle') {
                            // Chapter title has an associated heading level
                            $reps['{smd_ebook_chaptitle}'] = '<h' . $hdg . '>' . $content . '</h' . $hdg . '>';
                        }
                    }
                }
            }
            // Price (SRP) can also come from a field but it needs some special jiggery pokery
            if (!isset($reps['{smd_ebook_md_srp}'])) {
                $val = ps('smd_ebook_fld_srp');
                if (strpos($val, 'SMD_FLD_') !== false) {
                    $valfld = str_replace('SMD_FLD_', '', $val);
                    $val = isset($row[$valfld]) ? $row[$valfld] : '';
                }
                if ($val) {
                    $parts = do_list($val, '|');
                    $parts[0] = $parts[0] ? $parts[0] : '0.00';
                    $parts[1] = isset($parts[1]) && $parts[1] ? $parts[1] : get_pref('smd_ebook_currency', $smd_ebook_prefs['smd_ebook_currency']['default']);
                    $reps['{smd_ebook_md_srp}'] = '<SRP Currency="' . $parts[1] . '">' . $parts[0] . '</SRP>';
                }
            }
            // Authornote is slightly different because it needs storing as a file,
            // and needs adding to the .ncx (but not to the ToC)
            if (!isset($reps['{smd_ebook_manifest_authornote}'])) {
                $val = ps('smd_ebook_fld_authornote');
                if (strpos($val, 'SMD_FLD_') !== false) {
                    $valfld = str_replace('SMD_FLD_', '', $val);
                    $val = isset($row[$valfld]) ? $row[$valfld] : '';
                }
                if ($val) {
                    $reps['{smd_ebook_manifest_authornote}'] = '<item id="smd_ebook_notes" media-type="application/xhtml+xml" href="' . $notefile . '" />';
                    $reps['{smd_ebook_spine_authornote}'] = '<itemref idref="smd_ebook_notes" />';
                    $guide_refs['notes'] = '<reference type="notes" title="' . gTxt('smd_ebook_lbl_authornote') . '" href="' . $notefile . '" />';
                    $note_content = '<span id="smd_ebook_notes"></span>' . ($txt_authornote ? $textile->TextileThis($val) : $val);
                    // While it's 99% likely the actual title used for the eventual book has been found,
                    // there's a slim chance it hasn't. In that case, the current row's title is used as a fallback
                    $note_title = isset($reps['{smd_ebook_title}']) ? $reps['{smd_ebook_title}'] : $row['Title'];
                    $note_content = str_replace($html_from, array($reps['{smd_ebook_doctype}'], $reps['{smd_ebook_namespace}'], $reps['{smd_ebook_charset}'], $encoding, $note_title, '', $sheet, $note_content), $template['doc']);
                    $fp = fopen($ebook_path . $notefile, "wb");
                    fwrite($fp, trim($note_content));
                    fclose($fp);
                    $lfout[] = $notefile;
                    // Add it to the .ncx
                    $ncx_cnt++;
                    $from = array('{smd_ebook_file_name}', '{smd_ebook_nav_label}', '{smd_ebook_nav_hash}', '{smd_ebook_nav_idx}');
                    $to = array($notefile, gTxt('smd_ebook_lbl_authornote'), 'smd_ebook_notes', $ncx_cnt);
                    $ncx[] = str_replace($from, $to, $template['nav']);
                }
            }
            // Note:
            //  1) a full (well-formed, hopefully) HTML file (from <html>...</html>) is generated
            //     here so the loadHTML() method is happy. The body will need reinjecting into
            //     the template after the ToC has been generated.
            //  2) The current HTML file's title is used instead of the overall book title.
            //  3) parse() is called twice to simulate secondpass. TODO: fix this
            $chap_title = isset($reps['{smd_ebook_chaptitle}']) ? $reps['{smd_ebook_chaptitle}'] : '';
            article_format_info($row);
            // Load article context
            $html_content = str_replace($html_from, array($reps['{smd_ebook_doctype}'], $reps['{smd_ebook_namespace}'], $reps['{smd_ebook_charset}'], $encoding, $row['Title'], $chap_title, $sheet, parse(parse($row['Body_html']))), $template['doc']);
            // Trawl through the HTML content, either:
            //  a) pulling out the given ToC entries.
            //  b) automatically creating ToC entries if the pref allows.
            //  c) finding images to copy into the ePub file structure.
            $autotoc = get_pref('smd_ebook_auto_toc', $smd_ebook_prefs['smd_ebook_auto_toc']['default']);
            // Convert the list of heading numbers into a string of numbers suitable
            // for using inside square brackets of a regex
            $autohed = get_pref('smd_ebook_auto_toc_headings', $smd_ebook_prefs['smd_ebook_auto_toc_headings']['default']);
            $autohed = join('', do_list($autohed));
            $doc = new DOMDocument();
            // Use UNIX line endings to prevent &#13; appearing in the saved XML
            $html_content = preg_replace('/\\r\\n/', "\n", $html_content);
            $dom_ok = $doc->loadHTML($html_content);
            if ($dom_ok) {
                $items = $doc->getElementsByTagName('*');
                $offset = $toc_cnt = 0;
                foreach ($items as $item) {
                    if ($autotoc && !$item->hasAttribute('id') && preg_match('/h([' . $autohed . '])/i', $item->nodeName, $matches)) {
                        // It's a heading. Make the anchor chain based on the heading level
                        $anchor_parts = array_fill(0, $matches[1], 'sub');
                        $anchor = join('-', $anchor_parts) . ++$elem_cnt;
                        $item->setAttribute('id', $anchor);
                    }
                    if ($item->hasAttribute('id')) {
                        $ncx_cnt++;
                        $toc_cnt++;
                        $hashval = $item->getAttribute('id');
                        if (!isset($guide_refs['text']) && $toc_cnt === 1) {
                            $guide_href = $firstfile . ($hashval && $is_mobi ? '#' . $hashval : '');
                            $guide_refs['text'] = '<reference type="text" title="' . gTxt('smd_ebook_lbl_text') . '" href="' . $guide_href . '" />';
                            $landmarks['bodymatter'] = href(gTxt('smd_ebook_lbl_text'), $guide_href, ' epub:type="bodymatter"');
                        }
                        // mb_convert_encoding() seems to bypass the odd behaviour where apostrophes
                        // would appear in the TOC as ’. This may actually be a band-aid to circumvent
                        // problems with the encoding in DOMDocument: perhaps if appropriate encoding is
                        // used there, this hack won't be necessary
                        //						$node = mb_convert_encoding(trim($item->nodeValue), 'HTML-ENTITIES', 'utf-8');
                        $node = trim($item->nodeValue);
                        $from = array('{smd_ebook_file_name}', '{smd_ebook_nav_label}', '{smd_ebook_nav_hash}', '{smd_ebook_nav_idx}');
                        $to = array($cur_file, $node, $hashval, $ncx_cnt);
                        $ncx[] = str_replace($from, $to, $template['nav']);
                        // Now it's the turn of the HTML TOC. Utilise Textile here to
                        // create the toc list from ul or ol syntax
                        $hashBits = do_list($hashval, '-');
                        $indent = count($hashBits);
                        if ($toc_cnt == 1 && $indent > 1) {
                            // Doesn't start with h1 (begins h2, maybe) so scale back the indent.
                            // Without this, Textile produces invalid markup.
                            $offset = $indent - 1;
                        }
                        $toc_cls = $toc_cnt == 1 && $toc_class ? '(' . $toc_class . ')' : '';
                        $toc[] = str_pad('', max(1, $indent - $offset), $wrapit) . $toc_cls . ' ' . href($node, $cur_file . '#' . $hashval);
                    }
                    // For ePub books, images need to be extracted separately
                    if ($is_epub && $item->nodeName === 'img') {
                        $src = $item->getAttribute('src');
                        $bits = pathinfo($src);
                        $mime_type = $bits['extension'] === 'jpg' || $bits['extension'] === 'jpeg' ? 'image/jpeg' : ($bits['extension'] === 'gif' ? 'image/gif' : ($bits['extension'] === 'png' ? 'image/png' : ''));
                        if ($mime_type) {
                            $img = safe_row('*', 'txp_image', "id='" . intval($bits['filename']) . "'");
                            $img['name'] = trim($img['name']);
                            if ($img) {
                                $ret = copy(get_pref('path_to_site') . DS . $img_dir . DS . $bits['basename'], $ebook_path . $bits['basename']);
                                if ($ret) {
                                    if (!in_array($bits['basename'], $master_image_refs)) {
                                        $from = array('{smd_ebook_image_link}', '{smd_ebook_image_type}', '{smd_ebook_image_id}');
                                        $to = array('images' . DS . $bits['basename'], $mime_type, 'image-' . $img_cnt);
                                        $article_refs[] = str_replace($from, $to, $template['img']);
                                        $master_image_refs[] = $bits['basename'];
                                        $img_cnt++;
                                    }
                                    // Add the file to the list of inline images, destined for the .smd file.
                                    // This list of images is merged with $lfout _after_ the chapter HTML
                                    // content, so a list of images in the chapter appear below it
                                    if (!in_array($bits['basename'], $image_list)) {
                                        $image_list[] = $bits['basename'];
                                    }
                                }
                            }
                        }
                    }
                }
                // Grab any changes just made to the DOM tree in case anchors have been added.
                // Note _only_ the <body> is extracted since the XML headers that come with a full
                // saveXML() get in the way. Also note that saveHTML() is not being used because its
                // 'node' parameter wasn't added until PHP 5.3.6 which would affect the plugin's
                // base requirements.
                // Hackish: remove the body tag wrapper with substr() so when the html_content
                // is shoved back into the template (which has a body tag already) there's no
                // tag duplication
                $html_content = substr($doc->saveXML($doc->getElementsByTagName('body')->item(0)), 6, -7);
                // Swap out any line break placeholders. Note that the line break is replaced twice:
                // once to get rid of any surrounding <p> tags that Textile may have introduced around
                // the marker, and again in case a few of them didn't get paragraph tags.
                $html_content = str_replace('<p>' . $pbr . '</p>', '<mbp:pagebreak />', $html_content);
                $html_content = str_replace($pbr, '<mbp:pagebreak />', $html_content);
                // Pass the extracted <body> tree into the doc template again so it regenerates
                // the full <html>...</html> document.
                $html_content = str_replace($html_from, array($reps['{smd_ebook_doctype}'], $reps['{smd_ebook_namespace}'], $reps['{smd_ebook_charset}'], $encoding, $row['Title'], '', $sheet, $html_content), $template['doc']);
            } else {
                trigger_error(gTxt('smd_ebook_malformed'), E_WARNING);
            }
            $ebook_item = 'smd_ebook_item_' . $article_cnt;
            // Guide items require special dispensation and can override built-in items
            // such as 'text' (a.k.a. bodymatter / start page / welcome / start) and 'toc',
            // but not cover image or notes.
            $valid_guide_refs = array('acknowledgments', 'appendix', 'afterword', 'bibliography', 'bodymatter', 'colophon', 'conclusion', 'contributors', 'copyright-page', 'dedication', 'epigraph', 'epilogue', 'errata', 'foreword', 'glossary', 'imprint', 'index', 'introduction', 'loi', 'lot', 'other-credits', 'preamble', 'preface', 'prologue', 'titlepage', 'toc');
            $val = 'custom_' . get_pref('smd_ebook_fld_guide');
            $val = isset($row[$val]) ? $row[$val] : '';
            $guides = do_list($val);
            foreach ($guides as $guide_ref) {
                $guide_name = do_list($guide_ref, '|');
                $guide_hash = do_list($guide_name[0], '#');
                $guide_ref = $lmk_ref = strtolower($guide_hash[0]);
                if ($guide_ref && in_array($guide_ref, $valid_guide_refs)) {
                    switch ($guide_ref) {
                        case 'bodymatter':
                            $guide_ref = 'text';
                            break;
                        case 'toc':
                            $toc_file = $cur_file;
                            $toc_ref = $ebook_item;
                            break;
                    }
                    $guide_title = isset($guide_name[1]) ? $guide_name[1] : gTxt('smd_ebook_lbl_' . str_replace('-', '_', $guide_ref));
                    $guide_href = $cur_file . (isset($guide_hash[1]) ? '#' . $guide_hash[1] : '');
                    $guide_refs[$guide_ref] = '<reference type="' . $guide_ref . '" title="' . $guide_title . '" href="' . $guide_href . '" />';
                    $landmarks[$lmk_ref] = href($guide_title, $guide_href, ' epub:type="' . $lmk_ref . '"');
                }
            }
            // Write the final HTML document to the file system
            $fp = fopen($ebook_path . $cur_file, "wb");
            fwrite($fp, trim($html_content));
            fclose($fp);
            $lfout[] = $cur_file;
            $lfout = array_merge($lfout, $image_list);
            $article_refs[] = '<item id="' . $ebook_item . '" media-type="application/xhtml+xml" href="' . $row['url_title'] . '.html" />';
            $article_spines[] = '<itemref idref="' . $ebook_item . '" />';
        }
    }
    // Ensure any NULL replacements are cleared or throw errors
    $reps['{smd_ebook_opf_file}'] = !isset($reps['{smd_ebook_opf_file}']) ? '' : $reps['{smd_ebook_opf_file}'];
    $reps['{smd_ebook_doctype}'] = !isset($reps['{smd_ebook_doctype}']) ? '' : $reps['{smd_ebook_doctype}'];
    $reps['{smd_ebook_namespace}'] = !isset($reps['{smd_ebook_namespace}']) ? '' : $reps['{smd_ebook_namespace}'];
    $reps['{smd_ebook_charset}'] = !isset($reps['{smd_ebook_charset}']) ? '' : $reps['{smd_ebook_charset}'];
    $reps['{smd_ebook_chaptitle}'] = !isset($reps['{smd_ebook_chaptitle}']) ? '' : $reps['{smd_ebook_chaptitle}'];
    $reps['{smd_ebook_creator}'] = !isset($reps['{smd_ebook_creator}']) ? '' : $reps['{smd_ebook_creator}'];
    $reps['{smd_ebook_md_creator}'] = !isset($reps['{smd_ebook_md_creator}']) ? '' : $reps['{smd_ebook_md_creator}'];
    $reps['{smd_ebook_md_description}'] = !isset($reps['{smd_ebook_md_description}']) ? '' : $reps['{smd_ebook_md_description}'];
    $reps['{smd_ebook_md_subject}'] = !isset($reps['{smd_ebook_md_subject}']) ? '' : $reps['{smd_ebook_md_subject}'];
    $reps['{smd_ebook_md_publisher}'] = !isset($reps['{smd_ebook_md_publisher}']) ? '' : $reps['{smd_ebook_md_publisher}'];
    $reps['{smd_ebook_md_srp}'] = !isset($reps['{smd_ebook_md_srp}']) ? '' : $reps['{smd_ebook_md_srp}'];
    if (!isset($reps['{smd_ebook_md_cover}'])) {
        $reps['{smd_ebook_md_cover}'] = '';
        $reps['{smd_ebook_manifest_cover}'] = '';
    }
    if (!isset($reps['{smd_ebook_manifest_authornote}'])) {
        $reps['{smd_ebook_manifest_authornote}'] = '';
        $reps['{smd_ebook_spine_authornote}'] = '';
    }
    // All the replacements are set up so prepare for book generation
    // First, create the TOC and write it to the filesystem
    if ($toc_cnt > 0) {
        $reps['{smd_ebook_spine_toc}'] = '<itemref idref="' . $toc_ref . '" />';
        if (!isset($guide_refs['toc'])) {
            $reps['{smd_ebook_manifest_toc}'] = '<item id="' . $toc_ref . '" media-type="application/xhtml+xml" href="' . $toc_file . '" />';
            $guide_refs['toc'] = '<reference type="toc" title="' . gTxt('smd_ebook_lbl_toc') . '" href="' . $toc_file . '" />';
            $landmarks['toc'] = href(gTxt('smd_ebook_lbl_toc'), $toc_file, ' epub:type="toc"');
            $html_toc = $textile->TextileThis(join(n, $toc));
            $final_toc = str_replace(array('{smd_ebook_toc_list}', '{smd_ebook_stylesheet}', '{smd_ebook_toc}'), array($html_toc, $sheet, gTxt('smd_ebook_lbl_toc')), $template['toc']);
            $fp = fopen($ebook_path . $toc_file, "wb");
            fwrite($fp, trim($final_toc));
            fclose($fp);
            $lfout[] = $toc_file;
        } else {
            $reps['{smd_ebook_manifest_toc}'] = '';
        }
    } else {
        $reps['{smd_ebook_manifest_toc}'] = '';
        $reps['{smd_ebook_spine_toc}'] = '';
    }
    // Add the ncx waypoints to the reps array and generate the .ncx file
    if ($ncx_cnt > 0) {
        $reps['{smd_ebook_ncx_doctype}'] = $is_mobi ? '<!DOCTYPE ncx PUBLIC "-//NISO//DTD ncx 2005-1//EN" "http://www.daisy.org/z3986/2005/ncx-2005-1.dtd">' : '';
        $reps['{smd_ebook_ncx_map}'] = join(n, $ncx);
        $reps['{smd_ebook_manifest_ncx}'] = '<item id="ncx" media-type="application/x-dtbncx+xml" href="' . $ncx_file . '" />';
        //		$reps['{smd_ebook_spine_ncx}'] = '<itemref idref="ncx" />';
        $reps['{smd_ebook_spine_ncx_ref}'] = 'toc="ncx"';
        $ncx_file_content = trim(strtr($template['ncx'], $reps));
        $fp = fopen($ebook_path . $ncx_file, "wb");
        fwrite($fp, $ncx_file_content);
        fclose($fp);
        $lfout[] = $ncx_file;
    } else {
        $reps['{smd_ebook_manifest_ncx}'] = '';
        //		$reps['{smd_ebook_spine_ncx}'] = '';
        $reps['{smd_ebook_spine_ncx_ref}'] = '';
    }
    if ($is_epub) {
        // Create supplemental files for ePub format
        // First the mimetype
        $fp = fopen($ebook_path . $mimetype_file, "wb");
        fwrite($fp, 'application/epub+zip');
        fclose($fp);
        // Then the container
        $fp = fopen($ebook_path . $container_file, "wb");
        $from = array('{smd_ebook_opf_file}');
        $to = array($opf_file);
        fwrite($fp, str_replace($from, $to, $template['inf']));
        fclose($fp);
        // Then the landmarks
        $lmk_list = array();
        foreach ($landmarks as $type => $landmark) {
            $lmk_list[] = tag($landmark, 'li');
        }
        $fp = fopen($ebook_path . $lmk_file, "wb");
        $from = array('{smd_ebook_guide}', '{smd_ebook_encoding}', '{smd_ebook_lang}', '{smd_ebook_landmarks}');
        $to = array(gTxt('smd_ebook_guide'), $encoding, $lang, join(n . t, $lmk_list));
        fwrite($fp, str_replace($from, $to, $template['lmk']));
        fclose($fp);
        $article_refs[] = '<item id="landmarks" media-type="application/xhtml+xml" href="' . $lmk_file . '" />';
        $lfout[] = $lmk_file;
        // Then any stylesheets
        foreach ($sheetcontent as $sheet => $content) {
            $fp = fopen($ebook_path . $sheet . '.css', "wb");
            fwrite($fp, $content);
            fclose($fp);
        }
        // Transform .ncx to .end, if necessary, and generate manifest + spine entries.
        // END (Epub Navigation Document) supersedes the deprecated NCX in ePub3.
        if ($ncx_cnt > 0) {
            if (class_exists('XSLTProcessor')) {
                $xslt = new XSLTProcessor();
                $xslt->importStylesheet(new SimpleXMLElement($template['ncx2end']));
                $ebook_end = $xslt->transformToXml(new SimpleXMLElement($ncx_file_content));
            } else {
                $ebook_end = str_replace(array('{smd_ebook_toc_list}', '{smd_ebook_toc}'), array($html_toc, gTxt('smd_ebook_lbl_toc')), $template['end']);
            }
            $fp = fopen($ebook_path . $end_file, "wb");
            fwrite($fp, trim($ebook_end));
            fclose($fp);
            $lfout[] = $end_file;
        }
        $reps['{smd_ebook_md_x}'] = '';
        $reps['{smd_ebook_guide_cover}'] = '<reference type="cover" title="Cover" href="cover.html" />';
        $reps['{smd_ebook_spine_cover}'] = '<itemref idref="cover" linear="no" />';
        $reps['{smd_ebook_manifest_end}'] = '<item id="end" properties="nav" href="' . $end_file . '" media-type="application/xhtml+xml" />';
    } elseif ($is_mobi) {
        $reps['{smd_ebook_md_x}'] = str_replace(array('{smd_ebook_encoding}', '{smd_ebook_md_srp}'), array($encoding, $reps['{smd_ebook_md_srp}']), $template['xmd']);
        $reps['{smd_ebook_guide_cover}'] = '';
        $reps['{smd_ebook_spine_cover}'] = '';
        $reps['{smd_ebook_manifest_end}'] = '';
        $reps['{smd_ebook_landmark_nav}'] = '';
    }
    // Build the remaining manifest replacements and generate the OPF
    $reps['{smd_ebook_guide_extras}'] = $guide_refs ? join(n . t . t, $guide_refs) : '';
    $reps['{smd_ebook_manifest_items}'] = join(n . t . t, $article_refs);
    $reps['{smd_ebook_spine_items}'] = join(n, $article_spines);
    $opf_file_content = strtr($template['opf'], $reps);
    $fp = fopen($ebook_path . $opf_file, "wb");
    fwrite($fp, trim($opf_file_content));
    fclose($fp);
    $lfout[] = $opf_file;
    // Write the listfile, which contains a list of all the files used in this stage
    $fp = fopen($ebook_path . $listfile, "wb");
    fwrite($fp, join(n, $lfout));
    fclose($fp);
    // Hand off to Stage 2 to do the deed
    smd_ebook_generate($listfile, $opf_file, $bType, $ebook_folder);
}
function oui_dailymotion($atts, $thing)
{
    global $thisarticle;
    extract(lAtts(array('video' => '', 'custom' => 'dailymotion ID', 'width' => '0', 'height' => '0', 'ratio' => '4:3', 'api' => '', 'autoplay' => '0', 'chromeless' => '0', 'highlight' => 'ffcc33', 'html' => '0', 'playerid' => '', 'info' => '1', 'logo' => '1', 'network' => '', 'origin' => '', 'quality' => '', 'related' => '1', 'start' => '0', 'startscreen' => '', 'syndication' => '', 'wmode' => 'transparent', 'label' => '', 'labeltag' => '', 'wraptag' => '', 'class' => __FUNCTION__), $atts));
    $custom = strtolower($custom);
    if (!$video && isset($thisarticle[$custom])) {
        $video = $thisarticle[$custom];
    }
    /*
     * Check for dailymotion video ID or dailymotion URL to extract ID from
     */
    $match = _oui_dailymotion($video);
    if ($match) {
        $video = $match;
    } elseif (empty($video)) {
        return '';
    }
    $src = '//www.dailymotion.com/embed/video/' . $video;
    /*
     * Attributes.
     */
    $qAtts = array('highlight' => $highlight, 'id' => $playerid, 'origin' => $origin, 'start' => $start, 'syndication' => $syndication, 'autoplay' => array($autoplay => '0, 1'), 'chromeless' => array($chromeless => '0, 1'), 'html' => array($html => '0, 1'), 'info' => array($info => '0, 1'), 'logo' => array($logo => '0, 1'), 'related' => array($related => '0, 1'), 'api' => array($api => 'postMessage, fragment, location'), 'network' => array($network => 'dsl, cellular'), 'quality' => array($quality => '240, 380, 480, 720, 1080, 1440, 2160'), 'startscreen' => array($startscreen => 'flash, html'), 'wmode' => array($wmode => 'transparent, opaque'));
    $qString = array();
    foreach ($qAtts as $att => $value) {
        if ($value) {
            if (!is_array($value)) {
                $qString[] = $att . '=' . $value;
            } else {
                foreach ($value as $val => $valid) {
                    if ($val) {
                        if (in_list($val, $valid)) {
                            $qString[] = $att . '=' . $val;
                        } else {
                            trigger_error("unknown attribute value; oui_dailymotion " . $att . " attribute accepts the following values: " . $valid);
                            return;
                        }
                    }
                }
            }
        }
    }
    /*
     * Check if we need to append a query string to the video src.
     */
    if (!empty($qString)) {
        $src .= '?' . implode('&amp;', $qString);
    }
    /*
     * If the width and/or height has not been set we want to calculate new
     * ones using the aspect ratio.
     */
    if (!$width || !$height) {
        $toolbarHeight = 25;
        // Work out the aspect ratio.
        preg_match("/(\\d+):(\\d+)/", $ratio, $matches);
        if ($matches[0] && $matches[1] != 0 && $matches[2] != 0) {
            $aspect = $matches[1] / $matches[2];
        } else {
            $aspect = 1.333;
        }
        // Calcuate the new width/height.
        if ($width) {
            $height = $width / $aspect + $toolbarHeight;
        } elseif ($height) {
            $width = ($height - $toolbarHeight) * $aspect;
        } else {
            $width = 425;
            $height = 344;
        }
    }
    $out = '<iframe width="' . $width . '" height="' . $height . '" src="' . $src . '" frameborder="0" allowfullscreen></iframe>';
    return doLabel($label, $labeltag) . ($wraptag ? doTag($out, $wraptag, $class) : $out);
}