emacs-orgmode@gnu.org archives
 help / color / mirror / code / Atom feed
From: Max Nikulin <manikulin@gmail.com>
To: emacs-orgmode@gnu.org
Subject: Re: Links & images with different attributes in the same paragraph
Date: Tue, 12 Dec 2023 18:08:49 +0700	[thread overview]
Message-ID: <ul9f02$ttc$1@ciao.gmane.io> (raw)
In-Reply-To: <87lea8vk1i.fsf@localhost>

On 05/12/2023 20:46, Ihor Radchenko wrote:
> 
> We definitely need something to fine-tune export properties inline.
> However, I am skeptical about using links for this purpose in Org
> proper, not individual user configs.

Sometimes links are really links, however some links require some 
tuning. Global style or custom export backend that modifies all links is 
not always suitable.

Perhaps special :href values may be added to allow just decorations 
without hyperlinks.

> I believe that the right way to go here is what we previously discussed
> as inline special block equivalent. That way, we will not need to create
> workarounds with special link type.

It is limitation of top-down parser that object of the same time can not 
be nested, so I am unsure if special blocks would be solution in all cases.

I have added a hack to allow definitions of links or their attributes 
outside of paragraphs. Noweb and source code blocks allow it. Perhaps is 
should be implemented as a filter to avoid tricks to get noexport source 
blocks

---- 8< ----
A link defined in a source block
[[wrap:<<org-mode>> :attr_html ":class org"][Org mode]]

#+name: org-mode
#+begin_src elisp :exports none
:href "https://orgmode.org"
:attr_html ":title Org Mode — Your life in plain text"
#+end_src
---- >8 ----

(defun nm/org-link-wrap-path-to-props (path &optional info)
   (let* ((with-broken-links (plist-get info :with-broken-links))
	 (org-babel-noweb-error-all-langs
	  (if (not with-broken-links)
	      t
	    ;; TODO Handle `mark', currently errors are ignored.
	    org-babel-noweb-error-all-langs))
	 (expanded
	  (org-babel-expand-noweb-references
	   (list "elisp" path '(:noweb-prefix "no"))
	   ;; Allow noweb references to code blocks
	   ;; having ":exports none".
	   (plist-get info :input-buffer))))
     (read(concat "(" expanded ")"))))

(defun nm/org-link-wrap-assert-href (props path)
   (let ((href (plist-get props :href)))
     (pcase href
       ((pred null) (signal
		    'org-link-broken
		    (list (format "no :href property in `%s'" path))))
       ((pred stringp) href)
       ((pred symbolp) (symbol-name href))
       (_ (signal
	  'org-link-broken
	  (list (format "Invalid :href type in `%s'" path)))))))

(defun nm/org-link-wrap-copy-props (props link)
   (while props
     (let ((name (pop props))
	  (value (pop props))
	  (case-fold-search t))
       (org-element-put-property
        link
        name
        ;; `org-element--collect-affiliated-keywords'
        (if (string-match-p "\\`:attr_" (symbol-name name))
	   (append (org-element-property name link) (list value))
	 value)))))

(defun nm/org-link-wrap-export
     (path description backend info)
   (let* ((props-all (nm/org-link-wrap-path-to-props path info))
	 (href (nm/org-link-wrap-assert-href props-all path))
	 ;; `org-plist-delete' removes other duplicated keys as well.
	 (props (map-delete props-all :href))
	 ;; Taken from `org-link-open-from-string'.
	 (link (with-temp-buffer
		 (let ((org-inhibit-startup nil))
		   (insert "[[" (org-link-escape href) "]]")
		   (org-mode)
		   (goto-char (point-min))
		   (org-element-link-parser)))))
     (nm/org-link-wrap-copy-props props link)
     (when description
       (org-element-set-contents link description))
     (org-no-properties
      (org-export-data-with-backend link backend info))))

(defun nm/org-link-wrap-follow (path arg)
   (let* ((props (nm/org-link-wrap-path-to-props path))
	 (href (nm/org-link-wrap-assert-href props path)))
     (org-link-open-from-string
      (concat "[[" (org-link-escape href) "]]")
      arg)))

(org-link-set-parameters
  "wrap"
  :follow #'nm/org-link-wrap-follow
  :export #'nm/org-link-wrap-export)




  reply	other threads:[~2023-12-12 11:09 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-11-11 15:54 Links & images with different attributes in the same paragraph Max Nikulin
2023-12-05 13:46 ` Ihor Radchenko
2023-12-12 11:08   ` Max Nikulin [this message]
2023-12-12 13:18     ` Ihor Radchenko
2023-12-13 11:50       ` Max Nikulin
2023-12-14 15:23         ` Ihor Radchenko
2023-12-16  8:06           ` Max Nikulin
2023-12-16 14:44             ` Ihor Radchenko
2023-12-19 14:39               ` Max Nikulin
2023-12-21 14:03                 ` Ihor Radchenko

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: https://www.orgmode.org/

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to='ul9f02$ttc$1@ciao.gmane.io' \
    --to=manikulin@gmail.com \
    --cc=emacs-orgmode@gnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs/org-mode.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).