0

The documentation says:

(org-set-property PROPERTY VALUE)

When called interactively, this will prompt for a property name, offering
completion on existing and default properties.  And then it will prompt
for a value, offering completion either on allowed values (via an inherited
xxx_ALL property) or on existing values in other instances of this property
in the current file.

And indeed, if I omit the value, it prompts me upon invoking the mapping (defined via map! from doom):

(map! :desc "Set ID property" "lI"
      '(lambda ()
         (interactive)
         (org-set-property "ID")))

prompt

But if I supply a value, it takes it directly and does not open the prompt for customization:

(map! :desc "Set ID property" "lI"
      '(lambda ()
         (interactive)
         (org-set-property "ID" "default-value")))

Can I pass a default value that can still be interactively adjusted?

6
  • There's never any need to quote a lambda form. But in this case it sounds like you want to modify the code in the lambda body. In that case, you can use a backquote and a comma to insert whatever value you want to into the body.
    – Drew
    May 16 at 19:04
  • No, you are not calling anything interactively.
    – Drew
    May 16 at 19:05
  • 1
    Does this answer your question? How to evaluate the variables before adding them to a list?
    – Drew
    May 16 at 19:06
  • Your question really seems to be about injecting a value into a quoted list, in this case, into a list that's a lambda form. There are multiple duplicates of this question. If that's not what you're asking then the question is unclear to me.
    – Drew
    May 16 at 19:07
  • no, sorry, I was unsure how to word it properly, maybe now?
    – xeruf
    May 16 at 19:39

1 Answer 1

1

No. org-set-property does exactly what the documentation says: it only prompts for a value if no value is specified as an argument. Because it says nothing about specifying a default value for that prompt, there is no default value for that prompt.

However, you could modify it fairly easily to support your use–case. If you look in org.el, you will find how it deals with the value argument:

(let ((value (or value (org-read-property-value property)))
      …)
  …)

As you can see, if value is nil then it calls org-read-property-value. If you look at the documentation for org-read-property-value, you will see that it does take an extra argument that specifies the default value for the input:

(org-read-property-value PROPERTY &optional POM DEFAULT)

Documentation
Read value for PROPERTY, as a string.

When optional argument POM is non-nil, completion uses additional
information, i.e., allowed or existing values at point or marker
POM.
Optional argument DEFAULT provides a default value for PROPERTY.

So you could change the argument list of org-set-property to (property value &optional default-value), then pass that information along like this:

(let ((value (or value (org-read-property-value property nil default-value)))
      …)
  …)

Note that you don’t actually need to modify org.el; you can instead use advice to override the definition of this function. See chapter 13.11 Advising Emacs Lisp Functions for more information about how to do this.

Edit:

Oh, and as a commenter mentioned, you don’t need a quote ' in front of a lambda expression. Write your keybinding like this instead:

(map! :desc "Set ID property" "lI"
      (lambda ()
        (interactive)
        (org-set-property "ID")))

Of course, that has nothing to do with your question. It’s just that the quote prevents the Elisp compiler from optimizing your code. It is unlikely that you would notice a performance different though.

6
  • thank you very much, this is undoubtedly insightful! But somehow the DEFAULT parameter does not work, if I invoke the following: (org-read-property-value "id" nil "test") I still get an empty prompt.
    – xeruf
    May 16 at 20:03
  • Oh, interesting. If you look at the code for org-read-property-value, it only uses the supplied default value if it can compute a list of allowed values for the property. Otherwise it supplies a list of all existing values for completion, with the default value being the current property value if any. In that case the initial-text of the prompt is left empty, so that the user can change the value without deleting that text first.
    – db48x
    May 16 at 20:19
  • So if you were doing this for the TODO property, your default value would be respected since it has a well–defined list of allowable TODO keywords for every org file. But that doesn’t apply to the ID property, which can be anything the user wants.
    – db48x
    May 16 at 20:21
  • maybe I can temporarily set the xxx_ALL property mentioned in the docs?
    – xeruf
    May 16 at 20:33
  • aha, setting (add-to-list 'org-global-properties-fixed '("ID_ALL" . "test")) globally fixes it - the value does not matter, it simply needs to be there :)
    – xeruf
    May 16 at 20:53

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.